1d012387afef0ba02185ebe27bc6bb15551912e92Havoc Pennington/* -*- mode: C; c-file-style: "gnu"; indent-tabs-mode: nil; -*- */
2a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington/* dbus-pending-call.c Object representing a call in progress.
3a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington *
4a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington * Copyright (C) 2002, 2003 Red Hat Inc.
5a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington *
643605a6f4e78a8c28afb4b1e924dff0301e0e95cHavoc Pennington * Licensed under the Academic Free License version 2.1
7a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington *
8a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington * This program is free software; you can redistribute it and/or modify
9a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington * it under the terms of the GNU General Public License as published by
10a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington * the Free Software Foundation; either version 2 of the License, or
11a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington * (at your option) any later version.
12a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington *
13a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington * This program is distributed in the hope that it will be useful,
14a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington * but WITHOUT ANY WARRANTY; without even the implied warranty of
15a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
16a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington * GNU General Public License for more details.
17a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington *
18a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington * You should have received a copy of the GNU General Public License
19a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington * along with this program; if not, write to the Free Software
205baf2f856a9c6625993234855b07680da1c8916fTobias Mueller * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301  USA
21a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington *
22a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington */
23a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington
24dbecdeabb20e0ce11121819c63373f0afba57c58Marcus Brinkmann#include <config.h>
25a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington#include "dbus-internals.h"
26ef614207fc4f03e5cc02faeb109f739eb1ccdf31Havoc Pennington#include "dbus-connection-internal.h"
27e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J#include "dbus-pending-call-internal.h"
28ef614207fc4f03e5cc02faeb109f739eb1ccdf31Havoc Pennington#include "dbus-pending-call.h"
29a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington#include "dbus-list.h"
30a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington#include "dbus-threads.h"
31a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington#include "dbus-test.h"
32a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington
33a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington/**
34a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington * @defgroup DBusPendingCallInternals DBusPendingCall implementation details
35a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington * @ingroup DBusInternals
36a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington * @brief DBusPendingCall private implementation details.
37a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington *
38a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington * The guts of DBusPendingCall and its methods.
39a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington *
40a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington * @{
41a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington */
42a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington
43e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J/**
44e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J * @brief Internals of DBusPendingCall
45e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J *
46e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J * Opaque object representing a reply message that we're waiting for.
47e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J */
4815ef0ef6fbba7827453b7973e62b6c1853576601Havoc Pennington
4915ef0ef6fbba7827453b7973e62b6c1853576601Havoc Pennington/**
5015ef0ef6fbba7827453b7973e62b6c1853576601Havoc Pennington * shorter and more visible way to write _dbus_connection_lock()
5115ef0ef6fbba7827453b7973e62b6c1853576601Havoc Pennington */
52222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J#define CONNECTION_LOCK(connection)   _dbus_connection_lock(connection)
5315ef0ef6fbba7827453b7973e62b6c1853576601Havoc Pennington/**
5415ef0ef6fbba7827453b7973e62b6c1853576601Havoc Pennington * shorter and more visible way to write _dbus_connection_unlock()
5515ef0ef6fbba7827453b7973e62b6c1853576601Havoc Pennington */
56222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J#define CONNECTION_UNLOCK(connection) _dbus_connection_unlock(connection)
57222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J
582a895edf6b1cad3915f5ca9e8b41f4bba780b2e0Havoc Pennington/**
592a895edf6b1cad3915f5ca9e8b41f4bba780b2e0Havoc Pennington * Implementation details of #DBusPendingCall - all fields are private.
602a895edf6b1cad3915f5ca9e8b41f4bba780b2e0Havoc Pennington */
61e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (Jstruct DBusPendingCall
62e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J{
63e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J  DBusAtomic refcount;                            /**< reference count */
64e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J
65e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J  DBusDataSlotList slot_list;                     /**< Data stored by allocated integer ID */
66e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J
67e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J  DBusPendingCallNotifyFunction function;         /**< Notifier when reply arrives. */
68e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J
69e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J  DBusConnection *connection;                     /**< Connections we're associated with */
70e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J  DBusMessage *reply;                             /**< Reply (after we've received it) */
71e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J  DBusTimeout *timeout;                           /**< Timeout */
72e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J
73e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J  DBusList *timeout_link;                         /**< Preallocated timeout response */
74e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J
75e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J  dbus_uint32_t reply_serial;                     /**< Expected serial of reply */
76e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J
77e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J  unsigned int completed : 1;                     /**< TRUE if completed */
78e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J  unsigned int timeout_added : 1;                 /**< Have added the timeout */
79e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J};
80e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J
81583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Penningtonstatic dbus_int32_t notify_user_data_slot = -1;
82583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington
83a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington/**
84a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington * Creates a new pending reply object.
85a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington *
86a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington * @param connection connection where reply will arrive
8792dd55c903b440bc423f1f8f9aeb0bbbbcc11bacScott James Remnant * @param timeout_milliseconds length of timeout, -1 for default, INT_MAX for no timeout
88ef614207fc4f03e5cc02faeb109f739eb1ccdf31Havoc Pennington * @param timeout_handler timeout handler, takes pending call as data
89a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington * @returns a new #DBusPendingCall or #NULL if no memory.
90a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington */
91a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc PenningtonDBusPendingCall*
92222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J_dbus_pending_call_new_unlocked (DBusConnection    *connection,
93222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J                                 int                timeout_milliseconds,
94222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J                                 DBusTimeoutHandler timeout_handler)
95a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington{
96a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington  DBusPendingCall *pending;
97ef614207fc4f03e5cc02faeb109f739eb1ccdf31Havoc Pennington  DBusTimeout *timeout;
98a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington
99aad6fa897f85486386b030847151cb09943c97c0Havoc Pennington  _dbus_assert (timeout_milliseconds >= 0 || timeout_milliseconds == -1);
1005efe8e7f1d97931710558495a951e0b35afbfb72John (J
101ef614207fc4f03e5cc02faeb109f739eb1ccdf31Havoc Pennington  if (timeout_milliseconds == -1)
102ef614207fc4f03e5cc02faeb109f739eb1ccdf31Havoc Pennington    timeout_milliseconds = _DBUS_DEFAULT_TIMEOUT_VALUE;
103583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington
104583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington  if (!dbus_pending_call_allocate_data_slot (&notify_user_data_slot))
105583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington    return NULL;
106ef614207fc4f03e5cc02faeb109f739eb1ccdf31Havoc Pennington
1074097e94af3d2fb1eb865343e3f76ca3949e7c69bHavoc Pennington  pending = dbus_new0 (DBusPendingCall, 1);
108a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington
109a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington  if (pending == NULL)
110583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington    {
111583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington      dbus_pending_call_free_data_slot (&notify_user_data_slot);
112583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington      return NULL;
113583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington    }
114a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington
11592dd55c903b440bc423f1f8f9aeb0bbbbcc11bacScott James Remnant  if (timeout_milliseconds != _DBUS_INT_MAX)
116ef614207fc4f03e5cc02faeb109f739eb1ccdf31Havoc Pennington    {
11792dd55c903b440bc423f1f8f9aeb0bbbbcc11bacScott James Remnant      timeout = _dbus_timeout_new (timeout_milliseconds,
11892dd55c903b440bc423f1f8f9aeb0bbbbcc11bacScott James Remnant                                   timeout_handler,
11992dd55c903b440bc423f1f8f9aeb0bbbbcc11bacScott James Remnant                                   pending, NULL);
12092dd55c903b440bc423f1f8f9aeb0bbbbcc11bacScott James Remnant
12192dd55c903b440bc423f1f8f9aeb0bbbbcc11bacScott James Remnant      if (timeout == NULL)
12292dd55c903b440bc423f1f8f9aeb0bbbbcc11bacScott James Remnant        {
12392dd55c903b440bc423f1f8f9aeb0bbbbcc11bacScott James Remnant          dbus_pending_call_free_data_slot (&notify_user_data_slot);
12492dd55c903b440bc423f1f8f9aeb0bbbbcc11bacScott James Remnant          dbus_free (pending);
12592dd55c903b440bc423f1f8f9aeb0bbbbcc11bacScott James Remnant          return NULL;
12692dd55c903b440bc423f1f8f9aeb0bbbbcc11bacScott James Remnant        }
12792dd55c903b440bc423f1f8f9aeb0bbbbcc11bacScott James Remnant
12892dd55c903b440bc423f1f8f9aeb0bbbbcc11bacScott James Remnant      pending->timeout = timeout;
129ef614207fc4f03e5cc02faeb109f739eb1ccdf31Havoc Pennington    }
13092dd55c903b440bc423f1f8f9aeb0bbbbcc11bacScott James Remnant  else
13192dd55c903b440bc423f1f8f9aeb0bbbbcc11bacScott James Remnant    {
13292dd55c903b440bc423f1f8f9aeb0bbbbcc11bacScott James Remnant      pending->timeout = NULL;
13392dd55c903b440bc423f1f8f9aeb0bbbbcc11bacScott James Remnant    }
1347cb8a08c84438d6646f33496d82bb9d7ff1309faSimon McVittie
1357cb8a08c84438d6646f33496d82bb9d7ff1309faSimon McVittie  _dbus_atomic_inc (&pending->refcount);
136a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington  pending->connection = connection;
137a549de8b7a744ec52e514d1e38ac9f2370b5f8b6John (J  _dbus_connection_ref_unlocked (pending->connection);
1385efe8e7f1d97931710558495a951e0b35afbfb72John (J
139583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington  _dbus_data_slot_list_init (&pending->slot_list);
140ef614207fc4f03e5cc02faeb109f739eb1ccdf31Havoc Pennington
141a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington  return pending;
142a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington}
143a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington
144ef614207fc4f03e5cc02faeb109f739eb1ccdf31Havoc Pennington/**
145e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J * Sets the reply of a pending call with the given message,
146e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J * or if the message is #NULL, by timing out the pending call.
147e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J *
148e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J * @param pending the pending call
149e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J * @param message the message to complete the call with, or #NULL
150e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J *  to time out the call
151e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J */
152e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (Jvoid
153222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J_dbus_pending_call_set_reply_unlocked (DBusPendingCall *pending,
154222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J                                       DBusMessage     *message)
155e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J{
156e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J  if (message == NULL)
157e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J    {
158e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J      message = pending->timeout_link->data;
159e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J      _dbus_list_clear (&pending->timeout_link);
160e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J    }
161e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J  else
162e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J    dbus_message_ref (message);
163e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J
164e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J  _dbus_verbose ("  handing message %p (%s) to pending call serial %u\n",
165e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J                 message,
166e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J                 dbus_message_get_type (message) == DBUS_MESSAGE_TYPE_METHOD_RETURN ?
167e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J                 "method return" :
168e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J                 dbus_message_get_type (message) == DBUS_MESSAGE_TYPE_ERROR ?
169e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J                 "error" : "other type",
170e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J                 pending->reply_serial);
171e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J
172e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J  _dbus_assert (pending->reply == NULL);
173e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J  _dbus_assert (pending->reply_serial == dbus_message_get_reply_serial (message));
174e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J  pending->reply = message;
175e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J}
176e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J
177e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J/**
178ef614207fc4f03e5cc02faeb109f739eb1ccdf31Havoc Pennington * Calls notifier function for the pending call
179ef614207fc4f03e5cc02faeb109f739eb1ccdf31Havoc Pennington * and sets the call to completed.
180ef614207fc4f03e5cc02faeb109f739eb1ccdf31Havoc Pennington *
181ef614207fc4f03e5cc02faeb109f739eb1ccdf31Havoc Pennington * @param pending the pending call
182ef614207fc4f03e5cc02faeb109f739eb1ccdf31Havoc Pennington *
183ef614207fc4f03e5cc02faeb109f739eb1ccdf31Havoc Pennington */
184ef614207fc4f03e5cc02faeb109f739eb1ccdf31Havoc Penningtonvoid
185e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J_dbus_pending_call_complete (DBusPendingCall *pending)
186ef614207fc4f03e5cc02faeb109f739eb1ccdf31Havoc Pennington{
1879e4450872a6861bd93a01dabe14d2d16f6c84d3fHavoc Pennington  _dbus_assert (!pending->completed);
1889e4450872a6861bd93a01dabe14d2d16f6c84d3fHavoc Pennington
189ef614207fc4f03e5cc02faeb109f739eb1ccdf31Havoc Pennington  pending->completed = TRUE;
190ef614207fc4f03e5cc02faeb109f739eb1ccdf31Havoc Pennington
191ef614207fc4f03e5cc02faeb109f739eb1ccdf31Havoc Pennington  if (pending->function)
192583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington    {
193583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington      void *user_data;
194583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington      user_data = dbus_pending_call_get_data (pending,
195583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington                                              notify_user_data_slot);
196583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington
197583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington      (* pending->function) (pending, user_data);
198583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington    }
199ef614207fc4f03e5cc02faeb109f739eb1ccdf31Havoc Pennington}
200ef614207fc4f03e5cc02faeb109f739eb1ccdf31Havoc Pennington
20115ef0ef6fbba7827453b7973e62b6c1853576601Havoc Pennington/**
20215ef0ef6fbba7827453b7973e62b6c1853576601Havoc Pennington * If the pending call hasn't been timed out, add its timeout
20315ef0ef6fbba7827453b7973e62b6c1853576601Havoc Pennington * error reply to the connection's incoming message queue.
20415ef0ef6fbba7827453b7973e62b6c1853576601Havoc Pennington *
20515ef0ef6fbba7827453b7973e62b6c1853576601Havoc Pennington * @param pending the pending call
20615ef0ef6fbba7827453b7973e62b6c1853576601Havoc Pennington * @param connection the connection the call was sent to
20715ef0ef6fbba7827453b7973e62b6c1853576601Havoc Pennington */
208e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (Jvoid
209222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J_dbus_pending_call_queue_timeout_error_unlocked (DBusPendingCall *pending,
210222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J                                                 DBusConnection  *connection)
211e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J{
212222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J  _dbus_assert (connection == pending->connection);
213222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J
214e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J  if (pending->timeout_link)
215e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J    {
216e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J      _dbus_connection_queue_synthesized_message_link (connection,
217e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J						       pending->timeout_link);
218e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J      pending->timeout_link = NULL;
219e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J    }
220e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J}
221e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J
222e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J/**
223e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J * Checks to see if a timeout has been added
224e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J *
225e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J * @param pending the pending_call
226e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J * @returns #TRUE if there is a timeout or #FALSE if not
227e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J */
228e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (Jdbus_bool_t
229222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J_dbus_pending_call_is_timeout_added_unlocked (DBusPendingCall  *pending)
230e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J{
231e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J  _dbus_assert (pending != NULL);
232e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J
233e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J  return pending->timeout_added;
234e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J}
235e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J
236e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J
237e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J/**
238e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J * Sets wether the timeout has been added
239e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J *
240e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J * @param pending the pending_call
241e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J * @param is_added whether or not a timeout is added
242e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J */
243e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (Jvoid
244222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J_dbus_pending_call_set_timeout_added_unlocked (DBusPendingCall  *pending,
245222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J                                               dbus_bool_t       is_added)
246e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J{
247e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J  _dbus_assert (pending != NULL);
248e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J
249e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J  pending->timeout_added = is_added;
250e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J}
251e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J
252e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J
253e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J/**
254e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J * Retrives the timeout
255e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J *
256e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J * @param pending the pending_call
25792dd55c903b440bc423f1f8f9aeb0bbbbcc11bacScott James Remnant * @returns a timeout object or NULL if call has no timeout
258e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J */
259e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (JDBusTimeout *
260222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J_dbus_pending_call_get_timeout_unlocked (DBusPendingCall  *pending)
261e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J{
262e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J  _dbus_assert (pending != NULL);
263e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J
264e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J  return pending->timeout;
265e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J}
266e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J
267e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J/**
268e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J * Gets the reply's serial number
269e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J *
270e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J * @param pending the pending_call
271e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J * @returns a serial number for the reply or 0
272e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J */
273e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (Jdbus_uint32_t
274222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J_dbus_pending_call_get_reply_serial_unlocked (DBusPendingCall  *pending)
275e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J{
276e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J  _dbus_assert (pending != NULL);
277e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J
278e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J  return pending->reply_serial;
279e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J}
280e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J
281e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J/**
282e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J * Sets the reply's serial number
283e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J *
284e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J * @param pending the pending_call
285e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J * @param serial the serial number
286e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J */
287e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (Jvoid
288222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J_dbus_pending_call_set_reply_serial_unlocked  (DBusPendingCall *pending,
289222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J                                               dbus_uint32_t serial)
290e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J{
291e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J  _dbus_assert (pending != NULL);
292e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J  _dbus_assert (pending->reply_serial == 0);
293e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J
294e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J  pending->reply_serial = serial;
295e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J}
296e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J
297e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J/**
298222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J * Gets the connection associated with this pending call.
299222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J *
300222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J * @param pending the pending_call
301222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J * @returns the connection associated with the pending call
302222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J */
303222bd07e9df5e3b5a367d1282b43fd3a827a7552John (JDBusConnection *
304222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J_dbus_pending_call_get_connection_and_lock (DBusPendingCall *pending)
305222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J{
306222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J  _dbus_assert (pending != NULL);
307222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J
308222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J  CONNECTION_LOCK (pending->connection);
309222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J  return pending->connection;
310222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J}
311222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J
312222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J/**
313222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J * Gets the connection associated with this pending call.
314e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J *
315e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J * @param pending the pending_call
316e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J * @returns the connection associated with the pending call
317e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J */
318e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (JDBusConnection *
319222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J_dbus_pending_call_get_connection_unlocked (DBusPendingCall *pending)
320e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J{
321e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J  _dbus_assert (pending != NULL);
322e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J
323222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J  return pending->connection;
324e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J}
325e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J
326e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J/**
327e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J * Sets the reply message associated with the pending call to a timeout error
328e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J *
329e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J * @param pending the pending_call
330e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J * @param message the message we are sending the error reply to
331e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J * @param serial serial number for the reply
332e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J * @return #FALSE on OOM
333e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J */
334e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (Jdbus_bool_t
335222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J_dbus_pending_call_set_timeout_error_unlocked (DBusPendingCall *pending,
336222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J                                               DBusMessage     *message,
337222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J                                               dbus_uint32_t    serial)
338e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J{
339e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J  DBusList *reply_link;
340e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J  DBusMessage *reply;
341e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J
342e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J  reply = dbus_message_new_error (message, DBUS_ERROR_NO_REPLY,
343d330ea7d1c98d29383dff2fc0a48269bde998760Havoc Pennington                                  "Did not receive a reply. Possible causes include: "
344d330ea7d1c98d29383dff2fc0a48269bde998760Havoc Pennington                                  "the remote application did not send a reply, "
345d330ea7d1c98d29383dff2fc0a48269bde998760Havoc Pennington                                  "the message bus security policy blocked the reply, "
346d330ea7d1c98d29383dff2fc0a48269bde998760Havoc Pennington                                  "the reply timeout expired, or "
347d330ea7d1c98d29383dff2fc0a48269bde998760Havoc Pennington                                  "the network connection was broken.");
348e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J  if (reply == NULL)
349e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J    return FALSE;
350e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J
351e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J  reply_link = _dbus_list_alloc_link (reply);
352e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J  if (reply_link == NULL)
353e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J    {
354e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J      dbus_message_unref (reply);
355e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J      return FALSE;
356e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J    }
357e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J
358e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J  pending->timeout_link = reply_link;
359e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J
360222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J  _dbus_pending_call_set_reply_serial_unlocked (pending, serial);
361e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J
362e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J  return TRUE;
363e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J}
364e3dc6e281aae288e995f9d6a2675662ac3d0749fJohn (J
365a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington/**
366222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J * Increments the reference count on a pending call,
367222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J * while the lock on its connection is already held.
368222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J *
369222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J * @param pending the pending call object
370222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J * @returns the pending call object
371222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J */
372222bd07e9df5e3b5a367d1282b43fd3a827a7552John (JDBusPendingCall *
373222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J_dbus_pending_call_ref_unlocked (DBusPendingCall *pending)
374222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J{
3757cb8a08c84438d6646f33496d82bb9d7ff1309faSimon McVittie  _dbus_atomic_inc (&pending->refcount);
3767cb8a08c84438d6646f33496d82bb9d7ff1309faSimon McVittie
377222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J  return pending;
378222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J}
379222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J
380a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington
381222bd07e9df5e3b5a367d1282b43fd3a827a7552John (Jstatic void
382222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J_dbus_pending_call_last_unref (DBusPendingCall *pending)
383222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J{
384222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J  DBusConnection *connection;
385222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J
386222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J  /* If we get here, we should be already detached
387222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J   * from the connection, or never attached.
388222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J   */
389222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J  _dbus_assert (!pending->timeout_added);
390222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J
391222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J  connection = pending->connection;
392222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J
393222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J  /* this assumes we aren't holding connection lock... */
394222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J  _dbus_data_slot_list_free (&pending->slot_list);
395222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J
396222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J  if (pending->timeout != NULL)
397222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J    _dbus_timeout_unref (pending->timeout);
398222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J
399222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J  if (pending->timeout_link)
400222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J    {
401222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J      dbus_message_unref ((DBusMessage *)pending->timeout_link->data);
402222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J      _dbus_list_free_link (pending->timeout_link);
403222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J      pending->timeout_link = NULL;
404222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J    }
405222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J
406222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J  if (pending->reply)
407222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J    {
408222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J      dbus_message_unref (pending->reply);
409222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J      pending->reply = NULL;
410222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J    }
411222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J
412222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J  dbus_free (pending);
413222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J
414222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J  dbus_pending_call_free_data_slot (&notify_user_data_slot);
415222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J
416222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J  /* connection lock should not be held. */
417222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J  /* Free the connection last to avoid a weird state while
418222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J   * calling out to application code where the pending exists
419222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J   * but not the connection.
420222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J   */
421222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J  dbus_connection_unref (connection);
422222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J}
423222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J
424222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J/**
425222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J * Decrements the reference count on a pending call,
426222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J * freeing it if the count reaches 0. Assumes
427222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J * connection lock is already held.
428222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J *
429222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J * @param pending the pending call object
430222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J */
431222bd07e9df5e3b5a367d1282b43fd3a827a7552John (Jvoid
432222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J_dbus_pending_call_unref_and_unlock (DBusPendingCall *pending)
433222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J{
4347cb8a08c84438d6646f33496d82bb9d7ff1309faSimon McVittie  dbus_int32_t old_refcount;
435222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J
4367cb8a08c84438d6646f33496d82bb9d7ff1309faSimon McVittie  old_refcount = _dbus_atomic_dec (&pending->refcount);
4377cb8a08c84438d6646f33496d82bb9d7ff1309faSimon McVittie  _dbus_assert (old_refcount > 0);
438222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J
439222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J  CONNECTION_UNLOCK (pending->connection);
4407cb8a08c84438d6646f33496d82bb9d7ff1309faSimon McVittie
4417cb8a08c84438d6646f33496d82bb9d7ff1309faSimon McVittie  if (old_refcount == 1)
442222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J    _dbus_pending_call_last_unref (pending);
443222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J}
444222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J
445a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington/**
446174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Pennington * Checks whether the pending call has received a reply
447174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Pennington * yet, or not. Assumes connection lock is held.
448174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Pennington *
449174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Pennington * @param pending the pending call
450174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Pennington * @returns #TRUE if a reply has been received
451174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Pennington */
452174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Penningtondbus_bool_t
453174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Pennington_dbus_pending_call_get_completed_unlocked (DBusPendingCall    *pending)
454174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Pennington{
455174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Pennington  return pending->completed;
456174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Pennington}
457174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Pennington
458174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Penningtonstatic DBusDataSlotAllocator slot_allocator;
459174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Pennington_DBUS_DEFINE_GLOBAL_LOCK (pending_call_slots);
460174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Pennington
461174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Pennington/**
462174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Pennington * Stores a pointer on a #DBusPendingCall, along
463174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Pennington * with an optional function to be used for freeing
464174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Pennington * the data when the data is set again, or when
465174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Pennington * the pending call is finalized. The slot number
466174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Pennington * must have been allocated with dbus_pending_call_allocate_data_slot().
467174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Pennington *
468174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Pennington * @param pending the pending_call
469174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Pennington * @param slot the slot number
470174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Pennington * @param data the data to store
471174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Pennington * @param free_data_func finalizer function for the data
472174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Pennington * @returns #TRUE if there was enough memory to store the data
473174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Pennington */
474174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Penningtondbus_bool_t
475174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Pennington_dbus_pending_call_set_data_unlocked (DBusPendingCall  *pending,
476174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Pennington                                     dbus_int32_t      slot,
477174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Pennington                                     void             *data,
478174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Pennington                                     DBusFreeFunction  free_data_func)
479174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Pennington{
480174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Pennington  DBusFreeFunction old_free_func;
481174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Pennington  void *old_data;
482174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Pennington  dbus_bool_t retval;
483174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Pennington
484174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Pennington  retval = _dbus_data_slot_list_set (&slot_allocator,
485174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Pennington                                     &pending->slot_list,
486174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Pennington                                     slot, data, free_data_func,
487174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Pennington                                     &old_free_func, &old_data);
488174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Pennington
489174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Pennington  /* Drop locks to call out to app code */
490174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Pennington  CONNECTION_UNLOCK (pending->connection);
491174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Pennington
492174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Pennington  if (retval)
493174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Pennington    {
494174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Pennington      if (old_free_func)
495174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Pennington        (* old_free_func) (old_data);
496174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Pennington    }
497174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Pennington
498174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Pennington  CONNECTION_LOCK (pending->connection);
499174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Pennington
500174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Pennington  return retval;
501174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Pennington}
502174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Pennington
503174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Pennington/** @} */
504174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Pennington
505174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Pennington/**
506174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Pennington * @defgroup DBusPendingCall DBusPendingCall
507174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Pennington * @ingroup  DBus
508174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Pennington * @brief Pending reply to a method call message
509174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Pennington *
510174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Pennington * A DBusPendingCall is an object representing an
511174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Pennington * expected reply. A #DBusPendingCall can be created
512174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Pennington * when you send a message that should have a reply.
513174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Pennington *
514174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Pennington * @{
515174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Pennington */
516174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Pennington
517174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Pennington/**
518174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Pennington * @typedef DBusPendingCall
519174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Pennington *
520174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Pennington * Opaque data type representing a message pending.
521174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Pennington */
522174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Pennington
523174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Pennington/**
524174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Pennington * Increments the reference count on a pending call.
525174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Pennington *
526174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Pennington * @param pending the pending call object
527174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Pennington * @returns the pending call object
528174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Pennington */
529174c63f176b9074ffe3cca8df016c53d68cafce9Havoc PenningtonDBusPendingCall *
530174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Penningtondbus_pending_call_ref (DBusPendingCall *pending)
531174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Pennington{
532174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Pennington  _dbus_return_val_if_fail (pending != NULL, NULL);
533174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Pennington
534174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Pennington  _dbus_atomic_inc (&pending->refcount);
535174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Pennington
536174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Pennington  return pending;
537174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Pennington}
538174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Pennington
539174c63f176b9074ffe3cca8df016c53d68cafce9Havoc Pennington/**
540a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington * Decrements the reference count on a pending call,
541a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington * freeing it if the count reaches 0.
542a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington *
543a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington * @param pending the pending call object
544a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington */
545a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Penningtonvoid
546a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Penningtondbus_pending_call_unref (DBusPendingCall *pending)
547a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington{
548a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington  dbus_bool_t last_unref;
549a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington
550a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington  _dbus_return_if_fail (pending != NULL);
551a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington
552a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington  last_unref = (_dbus_atomic_dec (&pending->refcount) == 1);
5537cb8a08c84438d6646f33496d82bb9d7ff1309faSimon McVittie
554a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington  if (last_unref)
555222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J    _dbus_pending_call_last_unref(pending);
556a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington}
557a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington
558a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington/**
559a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington * Sets a notification function to be called when the reply is
560a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington * received or the pending call times out.
561a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington *
562a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington * @param pending the pending call
563a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington * @param function notifier function
564a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington * @param user_data data to pass to notifier function
565a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington * @param free_user_data function to free the user data
566583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington * @returns #FALSE if not enough memory
567a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington */
568583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Penningtondbus_bool_t
569a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Penningtondbus_pending_call_set_notify (DBusPendingCall              *pending,
570a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington                              DBusPendingCallNotifyFunction function,
571a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington                              void                         *user_data,
572a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington                              DBusFreeFunction              free_user_data)
573a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington{
574583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington  _dbus_return_val_if_fail (pending != NULL, FALSE);
575a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington
576222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J  CONNECTION_LOCK (pending->connection);
577222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J
578583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington  /* could invoke application code! */
579222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J  if (!_dbus_pending_call_set_data_unlocked (pending, notify_user_data_slot,
580222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J                                             user_data, free_user_data))
581583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington    return FALSE;
582583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington
583a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington  pending->function = function;
584a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington
585222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J  CONNECTION_UNLOCK (pending->connection);
586222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J
587583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington  return TRUE;
588a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington}
589a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington
590ef614207fc4f03e5cc02faeb109f739eb1ccdf31Havoc Pennington/**
5911dcacffc325e50754d4cc3338822d1f03c8b6e45Havoc Pennington * Cancels the pending call, such that any reply or error received
5921dcacffc325e50754d4cc3338822d1f03c8b6e45Havoc Pennington * will just be ignored.  Drops the dbus library's internal reference
5931dcacffc325e50754d4cc3338822d1f03c8b6e45Havoc Pennington * to the #DBusPendingCall so will free the call if nobody else is
594bf172ce4c5856af21f5ee208960bf718a5058ad9Havoc Pennington * holding a reference. However you usually get a reference from
595bf172ce4c5856af21f5ee208960bf718a5058ad9Havoc Pennington * dbus_connection_send_with_reply() so probably your app owns a ref
596bf172ce4c5856af21f5ee208960bf718a5058ad9Havoc Pennington * also.
597bf172ce4c5856af21f5ee208960bf718a5058ad9Havoc Pennington *
598bf172ce4c5856af21f5ee208960bf718a5058ad9Havoc Pennington * Note that canceling a pending call will <em>not</em> simulate a
599bf172ce4c5856af21f5ee208960bf718a5058ad9Havoc Pennington * timed-out call; if a call times out, then a timeout error reply is
600bf172ce4c5856af21f5ee208960bf718a5058ad9Havoc Pennington * received. If you cancel the call, no reply is received unless the
601bf172ce4c5856af21f5ee208960bf718a5058ad9Havoc Pennington * the reply was already received before you canceled.
602ef614207fc4f03e5cc02faeb109f739eb1ccdf31Havoc Pennington *
603ef614207fc4f03e5cc02faeb109f739eb1ccdf31Havoc Pennington * @param pending the pending call
604ef614207fc4f03e5cc02faeb109f739eb1ccdf31Havoc Pennington */
605ef614207fc4f03e5cc02faeb109f739eb1ccdf31Havoc Penningtonvoid
606ef614207fc4f03e5cc02faeb109f739eb1ccdf31Havoc Penningtondbus_pending_call_cancel (DBusPendingCall *pending)
607ef614207fc4f03e5cc02faeb109f739eb1ccdf31Havoc Pennington{
60857657889128dc54069525cce47bce51365dbde0fJohn (J  _dbus_return_if_fail (pending != NULL);
60957657889128dc54069525cce47bce51365dbde0fJohn (J
610222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J  _dbus_connection_remove_pending_call (pending->connection,
611222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J                                        pending);
612ef614207fc4f03e5cc02faeb109f739eb1ccdf31Havoc Pennington}
613a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington
614ef614207fc4f03e5cc02faeb109f739eb1ccdf31Havoc Pennington/**
615ef614207fc4f03e5cc02faeb109f739eb1ccdf31Havoc Pennington * Checks whether the pending call has received a reply
616222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J * yet, or not.
617583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington *
618ef614207fc4f03e5cc02faeb109f739eb1ccdf31Havoc Pennington * @param pending the pending call
619222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J * @returns #TRUE if a reply has been received
620222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J */
621ef614207fc4f03e5cc02faeb109f739eb1ccdf31Havoc Penningtondbus_bool_t
622ef614207fc4f03e5cc02faeb109f739eb1ccdf31Havoc Penningtondbus_pending_call_get_completed (DBusPendingCall *pending)
623a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington{
624222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J  dbus_bool_t completed;
625222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J
62657657889128dc54069525cce47bce51365dbde0fJohn (J  _dbus_return_val_if_fail (pending != NULL, FALSE);
62757657889128dc54069525cce47bce51365dbde0fJohn (J
628222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J  CONNECTION_LOCK (pending->connection);
629222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J  completed = pending->completed;
630222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J  CONNECTION_UNLOCK (pending->connection);
631222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J
632222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J  return completed;
633a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington}
634a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington
635ef614207fc4f03e5cc02faeb109f739eb1ccdf31Havoc Pennington/**
6369e4450872a6861bd93a01dabe14d2d16f6c84d3fHavoc Pennington * Gets the reply, or returns #NULL if none has been received
6379e4450872a6861bd93a01dabe14d2d16f6c84d3fHavoc Pennington * yet. Ownership of the reply message passes to the caller. This
6389e4450872a6861bd93a01dabe14d2d16f6c84d3fHavoc Pennington * function can only be called once per pending call, since the reply
6399e4450872a6861bd93a01dabe14d2d16f6c84d3fHavoc Pennington * message is tranferred to the caller.
640583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington *
641ef614207fc4f03e5cc02faeb109f739eb1ccdf31Havoc Pennington * @param pending the pending call
642ef614207fc4f03e5cc02faeb109f739eb1ccdf31Havoc Pennington * @returns the reply message or #NULL.
643ef614207fc4f03e5cc02faeb109f739eb1ccdf31Havoc Pennington */
644ef614207fc4f03e5cc02faeb109f739eb1ccdf31Havoc PenningtonDBusMessage*
6459e4450872a6861bd93a01dabe14d2d16f6c84d3fHavoc Penningtondbus_pending_call_steal_reply (DBusPendingCall *pending)
646a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington{
6479e4450872a6861bd93a01dabe14d2d16f6c84d3fHavoc Pennington  DBusMessage *message;
6489e4450872a6861bd93a01dabe14d2d16f6c84d3fHavoc Pennington
64957657889128dc54069525cce47bce51365dbde0fJohn (J  _dbus_return_val_if_fail (pending != NULL, NULL);
6509e4450872a6861bd93a01dabe14d2d16f6c84d3fHavoc Pennington  _dbus_return_val_if_fail (pending->completed, NULL);
6519e4450872a6861bd93a01dabe14d2d16f6c84d3fHavoc Pennington  _dbus_return_val_if_fail (pending->reply != NULL, NULL);
652222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J
653222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J  CONNECTION_LOCK (pending->connection);
6549e4450872a6861bd93a01dabe14d2d16f6c84d3fHavoc Pennington
6559e4450872a6861bd93a01dabe14d2d16f6c84d3fHavoc Pennington  message = pending->reply;
6569e4450872a6861bd93a01dabe14d2d16f6c84d3fHavoc Pennington  pending->reply = NULL;
6579e4450872a6861bd93a01dabe14d2d16f6c84d3fHavoc Pennington
658222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J  CONNECTION_UNLOCK (pending->connection);
659222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J
6609e4450872a6861bd93a01dabe14d2d16f6c84d3fHavoc Pennington  return message;
661a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington}
662a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington
663a1b0bd33408f03894987ac32b4e6b46c6a15a594Havoc Pennington/**
664a1b0bd33408f03894987ac32b4e6b46c6a15a594Havoc Pennington * Block until the pending call is completed.  The blocking is as with
665a1b0bd33408f03894987ac32b4e6b46c6a15a594Havoc Pennington * dbus_connection_send_with_reply_and_block(); it does not enter the
666a1b0bd33408f03894987ac32b4e6b46c6a15a594Havoc Pennington * main loop or process other messages, it simply waits for the reply
667a1b0bd33408f03894987ac32b4e6b46c6a15a594Havoc Pennington * in question.
668a1b0bd33408f03894987ac32b4e6b46c6a15a594Havoc Pennington *
669583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington * If the pending call is already completed, this function returns
670583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington * immediately.
671583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington *
67215c60238853f2896738c23b53e574b5d9cae1635John (J * @todo when you start blocking, the timeout is reset, but it should
673a1b0bd33408f03894987ac32b4e6b46c6a15a594Havoc Pennington * really only use time remaining since the pending call was created.
67415c60238853f2896738c23b53e574b5d9cae1635John (J * This requires storing timestamps instead of intervals in the timeout
675a1b0bd33408f03894987ac32b4e6b46c6a15a594Havoc Pennington *
676a1b0bd33408f03894987ac32b4e6b46c6a15a594Havoc Pennington * @param pending the pending call
677a1b0bd33408f03894987ac32b4e6b46c6a15a594Havoc Pennington */
678a1b0bd33408f03894987ac32b4e6b46c6a15a594Havoc Penningtonvoid
679a1b0bd33408f03894987ac32b4e6b46c6a15a594Havoc Penningtondbus_pending_call_block (DBusPendingCall *pending)
680a1b0bd33408f03894987ac32b4e6b46c6a15a594Havoc Pennington{
68157657889128dc54069525cce47bce51365dbde0fJohn (J  _dbus_return_if_fail (pending != NULL);
68257657889128dc54069525cce47bce51365dbde0fJohn (J
6839e4450872a6861bd93a01dabe14d2d16f6c84d3fHavoc Pennington  _dbus_connection_block_pending_call (pending);
684a1b0bd33408f03894987ac32b4e6b46c6a15a594Havoc Pennington}
685a1b0bd33408f03894987ac32b4e6b46c6a15a594Havoc Pennington
686583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington/**
687583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington * Allocates an integer ID to be used for storing application-specific
688583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington * data on any DBusPendingCall. The allocated ID may then be used
689583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington * with dbus_pending_call_set_data() and dbus_pending_call_get_data().
690583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington * The passed-in slot must be initialized to -1, and is filled in
691583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington * with the slot ID. If the passed-in slot is not -1, it's assumed
692583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington * to be already allocated, and its refcount is incremented.
693583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington *
694583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington * The allocated slot is global, i.e. all DBusPendingCall objects will
695583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington * have a slot with the given integer ID reserved.
696583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington *
697583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington * @param slot_p address of a global variable storing the slot
698583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington * @returns #FALSE on failure (no memory)
699583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington */
700583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Penningtondbus_bool_t
701583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Penningtondbus_pending_call_allocate_data_slot (dbus_int32_t *slot_p)
702583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington{
70357657889128dc54069525cce47bce51365dbde0fJohn (J  _dbus_return_val_if_fail (slot_p != NULL, FALSE);
70457657889128dc54069525cce47bce51365dbde0fJohn (J
705583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington  return _dbus_data_slot_allocator_alloc (&slot_allocator,
70614cc7d28a8308060428bbc9b3dd357eaea3a4749John (J                                          &_DBUS_LOCK_NAME (pending_call_slots),
707583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington                                          slot_p);
708583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington}
709583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington
710583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington/**
711583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington * Deallocates a global ID for #DBusPendingCall data slots.
712583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington * dbus_pending_call_get_data() and dbus_pending_call_set_data() may
713583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington * no longer be used with this slot.  Existing data stored on existing
714583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington * DBusPendingCall objects will be freed when the #DBusPendingCall is
715583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington * finalized, but may not be retrieved (and may only be replaced if
716583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington * someone else reallocates the slot).  When the refcount on the
717583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington * passed-in slot reaches 0, it is set to -1.
718583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington *
719583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington * @param slot_p address storing the slot to deallocate
720583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington */
721583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Penningtonvoid
722583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Penningtondbus_pending_call_free_data_slot (dbus_int32_t *slot_p)
723583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington{
72457657889128dc54069525cce47bce51365dbde0fJohn (J  _dbus_return_if_fail (slot_p != NULL);
725583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington  _dbus_return_if_fail (*slot_p >= 0);
726222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J
727583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington  _dbus_data_slot_allocator_free (&slot_allocator, slot_p);
728583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington}
729583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington
730583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington/**
731583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington * Stores a pointer on a #DBusPendingCall, along
732583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington * with an optional function to be used for freeing
733583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington * the data when the data is set again, or when
734583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington * the pending call is finalized. The slot number
735583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington * must have been allocated with dbus_pending_call_allocate_data_slot().
736583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington *
737583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington * @param pending the pending_call
738583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington * @param slot the slot number
739583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington * @param data the data to store
740583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington * @param free_data_func finalizer function for the data
741583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington * @returns #TRUE if there was enough memory to store the data
742583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington */
743583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Penningtondbus_bool_t
744222bd07e9df5e3b5a367d1282b43fd3a827a7552John (Jdbus_pending_call_set_data (DBusPendingCall  *pending,
745222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J                            dbus_int32_t      slot,
746222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J                            void             *data,
747222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J                            DBusFreeFunction  free_data_func)
748222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J{
749222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J  dbus_bool_t retval;
750222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J
751222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J  _dbus_return_val_if_fail (pending != NULL, FALSE);
752222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J  _dbus_return_val_if_fail (slot >= 0, FALSE);
753222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J
754222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J
755222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J  CONNECTION_LOCK (pending->connection);
756222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J  retval = _dbus_pending_call_set_data_unlocked (pending, slot, data, free_data_func);
757222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J  CONNECTION_UNLOCK (pending->connection);
758583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington  return retval;
759583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington}
760583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington
761583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington/**
762583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington * Retrieves data previously set with dbus_pending_call_set_data().
763583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington * The slot must still be allocated (must not have been freed).
764583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington *
765583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington * @param pending the pending_call
766583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington * @param slot the slot to get data from
767583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington * @returns the data, or #NULL if not found
768583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington */
769583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Penningtonvoid*
770583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Penningtondbus_pending_call_get_data (DBusPendingCall   *pending,
771583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington                            dbus_int32_t       slot)
772583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington{
773583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington  void *res;
774583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington
775583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington  _dbus_return_val_if_fail (pending != NULL, NULL);
776583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington
777222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J  CONNECTION_LOCK (pending->connection);
778583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington  res = _dbus_data_slot_list_get (&slot_allocator,
779583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington                                  &pending->slot_list,
780583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington                                  slot);
781222bd07e9df5e3b5a367d1282b43fd3a827a7552John (J  CONNECTION_UNLOCK (pending->connection);
782583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington
783583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington  return res;
784583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington}
785583994cb3b7f5562fb7b8c37b4cb0d5af78e4ce2Havoc Pennington
786ef614207fc4f03e5cc02faeb109f739eb1ccdf31Havoc Pennington/** @} */
787ef614207fc4f03e5cc02faeb109f739eb1ccdf31Havoc Pennington
788ef614207fc4f03e5cc02faeb109f739eb1ccdf31Havoc Pennington#ifdef DBUS_BUILD_TESTS
789ef614207fc4f03e5cc02faeb109f739eb1ccdf31Havoc Pennington
790a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington/**
791a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington * @ingroup DBusPendingCallInternals
792a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington * Unit test for DBusPendingCall.
793a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington *
794a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington * @returns #TRUE on success.
795a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington */
796a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Penningtondbus_bool_t
797a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington_dbus_pending_call_test (const char *test_data_dir)
798a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington{
799a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington
800a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington  return TRUE;
801a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington}
802a6c8a71b1bcba04b63812a61f668e87af0922e5eHavoc Pennington#endif /* DBUS_BUILD_TESTS */
803