dbus-connection.c revision 8027efc97b4bec85f674570f878919cb72456745
1/* -*- mode: C; c-file-style: "gnu" -*- */
2/* dbus-connection.c DBusConnection object
3 *
4 * Copyright (C) 2002, 2003, 2004, 2005  Red Hat Inc.
5 *
6 * Licensed under the Academic Free License version 2.1
7 *
8 * This program is free software; you can redistribute it and/or modify
9 * it under the terms of the GNU General Public License as published by
10 * the Free Software Foundation; either version 2 of the License, or
11 * (at your option) any later version.
12 *
13 * This program is distributed in the hope that it will be useful,
14 * but WITHOUT ANY WARRANTY; without even the implied warranty of
15 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
16 * GNU General Public License for more details.
17 *
18 * You should have received a copy of the GNU General Public License
19 * along with this program; if not, write to the Free Software
20 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
21 *
22 */
23
24#include <config.h>
25#include "dbus-shared.h"
26#include "dbus-connection.h"
27#include "dbus-list.h"
28#include "dbus-timeout.h"
29#include "dbus-transport.h"
30#include "dbus-watch.h"
31#include "dbus-connection-internal.h"
32#include "dbus-pending-call-internal.h"
33#include "dbus-list.h"
34#include "dbus-hash.h"
35#include "dbus-message-internal.h"
36#include "dbus-threads.h"
37#include "dbus-protocol.h"
38#include "dbus-dataslot.h"
39#include "dbus-string.h"
40#include "dbus-pending-call.h"
41#include "dbus-object-tree.h"
42#include "dbus-threads-internal.h"
43#include "dbus-bus.h"
44
45#ifdef DBUS_DISABLE_CHECKS
46#define TOOK_LOCK_CHECK(connection)
47#define RELEASING_LOCK_CHECK(connection)
48#define HAVE_LOCK_CHECK(connection)
49#else
50#define TOOK_LOCK_CHECK(connection) do {                \
51    _dbus_assert (!(connection)->have_connection_lock); \
52    (connection)->have_connection_lock = TRUE;          \
53  } while (0)
54#define RELEASING_LOCK_CHECK(connection) do {            \
55    _dbus_assert ((connection)->have_connection_lock);   \
56    (connection)->have_connection_lock = FALSE;          \
57  } while (0)
58#define HAVE_LOCK_CHECK(connection)        _dbus_assert ((connection)->have_connection_lock)
59/* A "DO_NOT_HAVE_LOCK_CHECK" is impossible since we need the lock to check the flag */
60#endif
61
62#define TRACE_LOCKS 1
63
64#define CONNECTION_LOCK(connection)   do {                                      \
65    if (TRACE_LOCKS) { _dbus_verbose ("  LOCK: %s\n", _DBUS_FUNCTION_NAME); }   \
66    _dbus_mutex_lock ((connection)->mutex);                                      \
67    TOOK_LOCK_CHECK (connection);                                               \
68  } while (0)
69
70#define CONNECTION_UNLOCK(connection) do {                                              \
71    if (TRACE_LOCKS) { _dbus_verbose ("  UNLOCK: %s\n", _DBUS_FUNCTION_NAME);  }        \
72    RELEASING_LOCK_CHECK (connection);                                                  \
73    _dbus_mutex_unlock ((connection)->mutex);                                            \
74  } while (0)
75
76#define DISPATCH_STATUS_NAME(s)                                            \
77                     ((s) == DBUS_DISPATCH_COMPLETE ? "complete" :         \
78                      (s) == DBUS_DISPATCH_DATA_REMAINS ? "data remains" : \
79                      (s) == DBUS_DISPATCH_NEED_MEMORY ? "need memory" :   \
80                      "???")
81
82/**
83 * @defgroup DBusConnection DBusConnection
84 * @ingroup  DBus
85 * @brief Connection to another application
86 *
87 * A DBusConnection represents a connection to another
88 * application. Messages can be sent and received via this connection.
89 * The other application may be a message bus; for convenience, the
90 * function dbus_bus_get() is provided to automatically open a
91 * connection to the well-known message buses.
92 *
93 * In brief a DBusConnection is a message queue associated with some
94 * message transport mechanism such as a socket.  The connection
95 * maintains a queue of incoming messages and a queue of outgoing
96 * messages.
97 *
98 * Incoming messages are normally processed by calling
99 * dbus_connection_dispatch(). dbus_connection_dispatch() runs any
100 * handlers registered for the topmost message in the message queue,
101 * then discards the message, then returns.
102 *
103 * dbus_connection_get_dispatch_status() indicates whether
104 * messages are currently in the queue that need dispatching.
105 * dbus_connection_set_dispatch_status_function() allows
106 * you to set a function to be used to monitor the dispatch status.
107 *
108 * If you're using GLib or Qt add-on libraries for D-Bus, there are
109 * special convenience APIs in those libraries that hide
110 * all the details of dispatch and watch/timeout monitoring.
111 * For example, dbus_connection_setup_with_g_main().
112 *
113 * If you aren't using these add-on libraries, you have to manually
114 * call dbus_connection_set_dispatch_status_function(),
115 * dbus_connection_set_watch_functions(),
116 * dbus_connection_set_timeout_functions() providing appropriate
117 * functions to integrate the connection with your application's main
118 * loop.
119 *
120 * When you use dbus_connection_send() or one of its variants to send
121 * a message, the message is added to the outgoing queue.  It's
122 * actually written to the network later; either in
123 * dbus_watch_handle() invoked by your main loop, or in
124 * dbus_connection_flush() which blocks until it can write out the
125 * entire outgoing queue. The GLib/Qt add-on libraries again
126 * handle the details here for you by setting up watch functions.
127 *
128 * When a connection is disconnected, you are guaranteed to get a
129 * signal "Disconnected" from the interface
130 * #DBUS_INTERFACE_LOCAL, path
131 * #DBUS_PATH_LOCAL.
132 *
133 * You may not drop the last reference to a #DBusConnection
134 * until that connection has been disconnected.
135 *
136 * You may dispatch the unprocessed incoming message queue even if the
137 * connection is disconnected. However, "Disconnected" will always be
138 * the last message in the queue (obviously no messages are received
139 * after disconnection).
140 *
141 * #DBusConnection has thread locks and drops them when invoking user
142 * callbacks, so in general is transparently threadsafe. However,
143 * #DBusMessage does NOT have thread locks; you must not send the same
144 * message to multiple #DBusConnection that will be used from
145 * different threads.
146 */
147
148/**
149 * @defgroup DBusConnectionInternals DBusConnection implementation details
150 * @ingroup  DBusInternals
151 * @brief Implementation details of DBusConnection
152 *
153 * @{
154 */
155
156/**
157 * Internal struct representing a message filter function
158 */
159typedef struct DBusMessageFilter DBusMessageFilter;
160
161/**
162 * Internal struct representing a message filter function
163 */
164struct DBusMessageFilter
165{
166  DBusAtomic refcount; /**< Reference count */
167  DBusHandleMessageFunction function; /**< Function to call to filter */
168  void *user_data; /**< User data for the function */
169  DBusFreeFunction free_user_data_function; /**< Function to free the user data */
170};
171
172
173/**
174 * Internals of DBusPreallocatedSend
175 */
176struct DBusPreallocatedSend
177{
178  DBusConnection *connection; /**< Connection we'd send the message to */
179  DBusList *queue_link;       /**< Preallocated link in the queue */
180  DBusList *counter_link;     /**< Preallocated link in the resource counter */
181};
182
183static dbus_bool_t _dbus_modify_sigpipe = TRUE;
184
185/**
186 * Implementation details of DBusConnection. All fields are private.
187 */
188struct DBusConnection
189{
190  DBusAtomic refcount; /**< Reference count. */
191
192  DBusMutex *mutex; /**< Lock on the entire DBusConnection */
193
194  DBusMutex *dispatch_mutex;     /**< Protects dispatch_acquired */
195  DBusCondVar *dispatch_cond;    /**< Notify when dispatch_acquired is available */
196  DBusMutex *io_path_mutex;      /**< Protects io_path_acquired */
197  DBusCondVar *io_path_cond;     /**< Notify when io_path_acquired is available */
198
199  DBusList *outgoing_messages; /**< Queue of messages we need to send, send the end of the list first. */
200  DBusList *incoming_messages; /**< Queue of messages we have received, end of the list received most recently. */
201
202  DBusMessage *message_borrowed; /**< Filled in if the first incoming message has been borrowed;
203                                  *   dispatch_acquired will be set by the borrower
204                                  */
205
206  int n_outgoing;              /**< Length of outgoing queue. */
207  int n_incoming;              /**< Length of incoming queue. */
208
209  DBusCounter *outgoing_counter; /**< Counts size of outgoing messages. */
210
211  DBusTransport *transport;    /**< Object that sends/receives messages over network. */
212  DBusWatchList *watches;      /**< Stores active watches. */
213  DBusTimeoutList *timeouts;   /**< Stores active timeouts. */
214
215  DBusList *filter_list;        /**< List of filters. */
216
217  DBusDataSlotList slot_list;   /**< Data stored by allocated integer ID */
218
219  DBusHashTable *pending_replies;  /**< Hash of message serials to #DBusPendingCall. */
220
221  dbus_uint32_t client_serial;       /**< Client serial. Increments each time a message is sent  */
222  DBusList *disconnect_message_link; /**< Preallocated list node for queueing the disconnection message */
223
224  DBusWakeupMainFunction wakeup_main_function; /**< Function to wake up the mainloop  */
225  void *wakeup_main_data; /**< Application data for wakeup_main_function */
226  DBusFreeFunction free_wakeup_main_data; /**< free wakeup_main_data */
227
228  DBusDispatchStatusFunction dispatch_status_function; /**< Function on dispatch status changes  */
229  void *dispatch_status_data; /**< Application data for dispatch_status_function */
230  DBusFreeFunction free_dispatch_status_data; /**< free dispatch_status_data */
231
232  DBusDispatchStatus last_dispatch_status; /**< The last dispatch status we reported to the application. */
233
234  DBusList *link_cache; /**< A cache of linked list links to prevent contention
235                         *   for the global linked list mempool lock
236                         */
237  DBusObjectTree *objects; /**< Object path handlers registered with this connection */
238
239  char *server_guid; /**< GUID of server if we are in shared_connections, #NULL if server GUID is unknown or connection is private */
240
241  unsigned int shareable : 1; /**< #TRUE if connection can go in shared_connections once we know the GUID */
242
243  unsigned int shared : 1; /** < #TRUE if connection is shared and we hold a ref to it */
244
245  unsigned int dispatch_acquired : 1; /**< Someone has dispatch path (can drain incoming queue) */
246  unsigned int io_path_acquired : 1;  /**< Someone has transport io path (can use the transport to read/write messages) */
247
248  unsigned int exit_on_disconnect : 1; /**< If #TRUE, exit after handling disconnect signal */
249
250#ifndef DBUS_DISABLE_CHECKS
251  unsigned int have_connection_lock : 1; /**< Used to check locking */
252#endif
253
254#ifndef DBUS_DISABLE_CHECKS
255  int generation; /**< _dbus_current_generation that should correspond to this connection */
256#endif
257};
258
259static DBusDispatchStatus _dbus_connection_get_dispatch_status_unlocked      (DBusConnection     *connection);
260static void               _dbus_connection_update_dispatch_status_and_unlock (DBusConnection     *connection,
261                                                                              DBusDispatchStatus  new_status);
262static void               _dbus_connection_last_unref                        (DBusConnection     *connection);
263static void               _dbus_connection_acquire_dispatch                  (DBusConnection     *connection);
264static void               _dbus_connection_release_dispatch                  (DBusConnection     *connection);
265static DBusDispatchStatus _dbus_connection_flush_unlocked                    (DBusConnection     *connection);
266
267static DBusMessageFilter *
268_dbus_message_filter_ref (DBusMessageFilter *filter)
269{
270  _dbus_assert (filter->refcount.value > 0);
271  _dbus_atomic_inc (&filter->refcount);
272
273  return filter;
274}
275
276static void
277_dbus_message_filter_unref (DBusMessageFilter *filter)
278{
279  _dbus_assert (filter->refcount.value > 0);
280
281  if (_dbus_atomic_dec (&filter->refcount) == 1)
282    {
283      if (filter->free_user_data_function)
284        (* filter->free_user_data_function) (filter->user_data);
285
286      dbus_free (filter);
287    }
288}
289
290/**
291 * Acquires the connection lock.
292 *
293 * @param connection the connection.
294 */
295void
296_dbus_connection_lock (DBusConnection *connection)
297{
298  CONNECTION_LOCK (connection);
299}
300
301/**
302 * Releases the connection lock.
303 *
304 * @param connection the connection.
305 */
306void
307_dbus_connection_unlock (DBusConnection *connection)
308{
309  CONNECTION_UNLOCK (connection);
310}
311
312/**
313 * Wakes up the main loop if it is sleeping
314 * Needed if we're e.g. queueing outgoing messages
315 * on a thread while the mainloop sleeps.
316 *
317 * @param connection the connection.
318 */
319static void
320_dbus_connection_wakeup_mainloop (DBusConnection *connection)
321{
322  if (connection->wakeup_main_function)
323    (*connection->wakeup_main_function) (connection->wakeup_main_data);
324}
325
326#ifdef DBUS_BUILD_TESTS
327/* For now this function isn't used */
328/**
329 * Adds a message to the incoming message queue, returning #FALSE
330 * if there's insufficient memory to queue the message.
331 * Does not take over refcount of the message.
332 *
333 * @param connection the connection.
334 * @param message the message to queue.
335 * @returns #TRUE on success.
336 */
337dbus_bool_t
338_dbus_connection_queue_received_message (DBusConnection *connection,
339                                         DBusMessage    *message)
340{
341  DBusList *link;
342
343  link = _dbus_list_alloc_link (message);
344  if (link == NULL)
345    return FALSE;
346
347  dbus_message_ref (message);
348  _dbus_connection_queue_received_message_link (connection, link);
349
350  return TRUE;
351}
352
353/**
354 * Gets the locks so we can examine them
355 *
356 * @param connection the connection.
357 * @param mutex_loc return for the location of the main mutex pointer
358 * @param dispatch_mutex_loc return location of the dispatch mutex pointer
359 * @param io_path_mutex_loc return location of the io_path mutex pointer
360 * @param dispatch_cond_loc return location of the dispatch conditional
361 *        variable pointer
362 * @param io_path_cond_loc return location of the io_path conditional
363 *        variable pointer
364 */
365void
366_dbus_connection_test_get_locks (DBusConnection *conn,
367                                 DBusMutex **mutex_loc,
368                                 DBusMutex **dispatch_mutex_loc,
369                                 DBusMutex **io_path_mutex_loc,
370                                 DBusCondVar **dispatch_cond_loc,
371                                 DBusCondVar **io_path_cond_loc)
372{
373  *mutex_loc = conn->mutex;
374  *dispatch_mutex_loc = conn->dispatch_mutex;
375  *io_path_mutex_loc = conn->io_path_mutex;
376  *dispatch_cond_loc = conn->dispatch_cond;
377  *io_path_cond_loc = conn->io_path_cond;
378}
379#endif
380
381/**
382 * Adds a message-containing list link to the incoming message queue,
383 * taking ownership of the link and the message's current refcount.
384 * Cannot fail due to lack of memory.
385 *
386 * @param connection the connection.
387 * @param link the message link to queue.
388 */
389void
390_dbus_connection_queue_received_message_link (DBusConnection  *connection,
391                                              DBusList        *link)
392{
393  DBusPendingCall *pending;
394  dbus_int32_t reply_serial;
395  DBusMessage *message;
396
397  _dbus_assert (_dbus_transport_get_is_authenticated (connection->transport));
398
399  _dbus_list_append_link (&connection->incoming_messages,
400                          link);
401  message = link->data;
402
403  /* If this is a reply we're waiting on, remove timeout for it */
404  reply_serial = dbus_message_get_reply_serial (message);
405  if (reply_serial != -1)
406    {
407      pending = _dbus_hash_table_lookup_int (connection->pending_replies,
408                                             reply_serial);
409      if (pending != NULL)
410	{
411	  if (_dbus_pending_call_is_timeout_added_unlocked (pending))
412            _dbus_connection_remove_timeout_unlocked (connection,
413                                                      _dbus_pending_call_get_timeout_unlocked (pending));
414
415	  _dbus_pending_call_set_timeout_added_unlocked (pending, FALSE);
416	}
417    }
418
419
420
421  connection->n_incoming += 1;
422
423  _dbus_connection_wakeup_mainloop (connection);
424
425  _dbus_verbose ("Message %p (%d %s %s %s '%s' reply to %u) added to incoming queue %p, %d incoming\n",
426                 message,
427                 dbus_message_get_type (message),
428                 dbus_message_get_path (message) ?
429                 dbus_message_get_path (message) :
430                 "no path",
431                 dbus_message_get_interface (message) ?
432                 dbus_message_get_interface (message) :
433                 "no interface",
434                 dbus_message_get_member (message) ?
435                 dbus_message_get_member (message) :
436                 "no member",
437                 dbus_message_get_signature (message),
438                 dbus_message_get_reply_serial (message),
439                 connection,
440                 connection->n_incoming);}
441
442/**
443 * Adds a link + message to the incoming message queue.
444 * Can't fail. Takes ownership of both link and message.
445 *
446 * @param connection the connection.
447 * @param link the list node and message to queue.
448 *
449 */
450void
451_dbus_connection_queue_synthesized_message_link (DBusConnection *connection,
452						 DBusList *link)
453{
454  HAVE_LOCK_CHECK (connection);
455
456  _dbus_list_append_link (&connection->incoming_messages, link);
457
458  connection->n_incoming += 1;
459
460  _dbus_connection_wakeup_mainloop (connection);
461
462  _dbus_verbose ("Synthesized message %p added to incoming queue %p, %d incoming\n",
463                 link->data, connection, connection->n_incoming);
464}
465
466
467/**
468 * Checks whether there are messages in the outgoing message queue.
469 * Called with connection lock held.
470 *
471 * @param connection the connection.
472 * @returns #TRUE if the outgoing queue is non-empty.
473 */
474dbus_bool_t
475_dbus_connection_has_messages_to_send_unlocked (DBusConnection *connection)
476{
477  HAVE_LOCK_CHECK (connection);
478  return connection->outgoing_messages != NULL;
479}
480
481/**
482 * Checks whether there are messages in the outgoing message queue.
483 *
484 * @param connection the connection.
485 * @returns #TRUE if the outgoing queue is non-empty.
486 */
487dbus_bool_t
488dbus_connection_has_messages_to_send (DBusConnection *connection)
489{
490  dbus_bool_t v;
491
492  _dbus_return_val_if_fail (connection != NULL, FALSE);
493
494  CONNECTION_LOCK (connection);
495  v = _dbus_connection_has_messages_to_send_unlocked (connection);
496  CONNECTION_UNLOCK (connection);
497
498  return v;
499}
500
501/**
502 * Gets the next outgoing message. The message remains in the
503 * queue, and the caller does not own a reference to it.
504 *
505 * @param connection the connection.
506 * @returns the message to be sent.
507 */
508DBusMessage*
509_dbus_connection_get_message_to_send (DBusConnection *connection)
510{
511  HAVE_LOCK_CHECK (connection);
512
513  return _dbus_list_get_last (&connection->outgoing_messages);
514}
515
516/**
517 * Notifies the connection that a message has been sent, so the
518 * message can be removed from the outgoing queue.
519 * Called with the connection lock held.
520 *
521 * @param connection the connection.
522 * @param message the message that was sent.
523 */
524void
525_dbus_connection_message_sent (DBusConnection *connection,
526                               DBusMessage    *message)
527{
528  DBusList *link;
529
530  HAVE_LOCK_CHECK (connection);
531
532  /* This can be called before we even complete authentication, since
533   * it's called on disconnect to clean up the outgoing queue.
534   * It's also called as we successfully send each message.
535   */
536
537  link = _dbus_list_get_last_link (&connection->outgoing_messages);
538  _dbus_assert (link != NULL);
539  _dbus_assert (link->data == message);
540
541  /* Save this link in the link cache */
542  _dbus_list_unlink (&connection->outgoing_messages,
543                     link);
544  _dbus_list_prepend_link (&connection->link_cache, link);
545
546  connection->n_outgoing -= 1;
547
548  _dbus_verbose ("Message %p (%d %s %s %s '%s') removed from outgoing queue %p, %d left to send\n",
549                 message,
550                 dbus_message_get_type (message),
551                 dbus_message_get_path (message) ?
552                 dbus_message_get_path (message) :
553                 "no path",
554                 dbus_message_get_interface (message) ?
555                 dbus_message_get_interface (message) :
556                 "no interface",
557                 dbus_message_get_member (message) ?
558                 dbus_message_get_member (message) :
559                 "no member",
560                 dbus_message_get_signature (message),
561                 connection, connection->n_outgoing);
562
563  /* Save this link in the link cache also */
564  _dbus_message_remove_size_counter (message, connection->outgoing_counter,
565                                     &link);
566  _dbus_list_prepend_link (&connection->link_cache, link);
567
568  dbus_message_unref (message);
569}
570
571typedef dbus_bool_t (* DBusWatchAddFunction)     (DBusWatchList *list,
572                                                  DBusWatch     *watch);
573typedef void        (* DBusWatchRemoveFunction)  (DBusWatchList *list,
574                                                  DBusWatch     *watch);
575typedef void        (* DBusWatchToggleFunction)  (DBusWatchList *list,
576                                                  DBusWatch     *watch,
577                                                  dbus_bool_t    enabled);
578
579static dbus_bool_t
580protected_change_watch (DBusConnection         *connection,
581                        DBusWatch              *watch,
582                        DBusWatchAddFunction    add_function,
583                        DBusWatchRemoveFunction remove_function,
584                        DBusWatchToggleFunction toggle_function,
585                        dbus_bool_t             enabled)
586{
587  DBusWatchList *watches;
588  dbus_bool_t retval;
589
590  HAVE_LOCK_CHECK (connection);
591
592  /* This isn't really safe or reasonable; a better pattern is the "do everything, then
593   * drop lock and call out" one; but it has to be propagated up through all callers
594   */
595
596  watches = connection->watches;
597  if (watches)
598    {
599      connection->watches = NULL;
600      _dbus_connection_ref_unlocked (connection);
601      CONNECTION_UNLOCK (connection);
602
603      if (add_function)
604        retval = (* add_function) (watches, watch);
605      else if (remove_function)
606        {
607          retval = TRUE;
608          (* remove_function) (watches, watch);
609        }
610      else
611        {
612          retval = TRUE;
613          (* toggle_function) (watches, watch, enabled);
614        }
615
616      CONNECTION_LOCK (connection);
617      connection->watches = watches;
618      _dbus_connection_unref_unlocked (connection);
619
620      return retval;
621    }
622  else
623    return FALSE;
624}
625
626
627/**
628 * Adds a watch using the connection's DBusAddWatchFunction if
629 * available. Otherwise records the watch to be added when said
630 * function is available. Also re-adds the watch if the
631 * DBusAddWatchFunction changes. May fail due to lack of memory.
632 * Connection lock should be held when calling this.
633 *
634 * @param connection the connection.
635 * @param watch the watch to add.
636 * @returns #TRUE on success.
637 */
638dbus_bool_t
639_dbus_connection_add_watch_unlocked (DBusConnection *connection,
640                                     DBusWatch      *watch)
641{
642  return protected_change_watch (connection, watch,
643                                 _dbus_watch_list_add_watch,
644                                 NULL, NULL, FALSE);
645}
646
647/**
648 * Removes a watch using the connection's DBusRemoveWatchFunction
649 * if available. It's an error to call this function on a watch
650 * that was not previously added.
651 * Connection lock should be held when calling this.
652 *
653 * @param connection the connection.
654 * @param watch the watch to remove.
655 */
656void
657_dbus_connection_remove_watch_unlocked (DBusConnection *connection,
658                                        DBusWatch      *watch)
659{
660  protected_change_watch (connection, watch,
661                          NULL,
662                          _dbus_watch_list_remove_watch,
663                          NULL, FALSE);
664}
665
666/**
667 * Toggles a watch and notifies app via connection's
668 * DBusWatchToggledFunction if available. It's an error to call this
669 * function on a watch that was not previously added.
670 * Connection lock should be held when calling this.
671 *
672 * @param connection the connection.
673 * @param watch the watch to toggle.
674 * @param enabled whether to enable or disable
675 */
676void
677_dbus_connection_toggle_watch_unlocked (DBusConnection *connection,
678                                        DBusWatch      *watch,
679                                        dbus_bool_t     enabled)
680{
681  _dbus_assert (watch != NULL);
682
683  protected_change_watch (connection, watch,
684                          NULL, NULL,
685                          _dbus_watch_list_toggle_watch,
686                          enabled);
687}
688
689typedef dbus_bool_t (* DBusTimeoutAddFunction)    (DBusTimeoutList *list,
690                                                   DBusTimeout     *timeout);
691typedef void        (* DBusTimeoutRemoveFunction) (DBusTimeoutList *list,
692                                                   DBusTimeout     *timeout);
693typedef void        (* DBusTimeoutToggleFunction) (DBusTimeoutList *list,
694                                                   DBusTimeout     *timeout,
695                                                   dbus_bool_t      enabled);
696
697static dbus_bool_t
698protected_change_timeout (DBusConnection           *connection,
699                          DBusTimeout              *timeout,
700                          DBusTimeoutAddFunction    add_function,
701                          DBusTimeoutRemoveFunction remove_function,
702                          DBusTimeoutToggleFunction toggle_function,
703                          dbus_bool_t               enabled)
704{
705  DBusTimeoutList *timeouts;
706  dbus_bool_t retval;
707
708  HAVE_LOCK_CHECK (connection);
709
710  /* This isn't really safe or reasonable; a better pattern is the "do everything, then
711   * drop lock and call out" one; but it has to be propagated up through all callers
712   */
713
714  timeouts = connection->timeouts;
715  if (timeouts)
716    {
717      connection->timeouts = NULL;
718      _dbus_connection_ref_unlocked (connection);
719      CONNECTION_UNLOCK (connection);
720
721      if (add_function)
722        retval = (* add_function) (timeouts, timeout);
723      else if (remove_function)
724        {
725          retval = TRUE;
726          (* remove_function) (timeouts, timeout);
727        }
728      else
729        {
730          retval = TRUE;
731          (* toggle_function) (timeouts, timeout, enabled);
732        }
733
734      CONNECTION_LOCK (connection);
735      connection->timeouts = timeouts;
736      _dbus_connection_unref_unlocked (connection);
737
738      return retval;
739    }
740  else
741    return FALSE;
742}
743
744/**
745 * Adds a timeout using the connection's DBusAddTimeoutFunction if
746 * available. Otherwise records the timeout to be added when said
747 * function is available. Also re-adds the timeout if the
748 * DBusAddTimeoutFunction changes. May fail due to lack of memory.
749 * The timeout will fire repeatedly until removed.
750 * Connection lock should be held when calling this.
751 *
752 * @param connection the connection.
753 * @param timeout the timeout to add.
754 * @returns #TRUE on success.
755 */
756dbus_bool_t
757_dbus_connection_add_timeout_unlocked (DBusConnection *connection,
758                                       DBusTimeout    *timeout)
759{
760  return protected_change_timeout (connection, timeout,
761                                   _dbus_timeout_list_add_timeout,
762                                   NULL, NULL, FALSE);
763}
764
765/**
766 * Removes a timeout using the connection's DBusRemoveTimeoutFunction
767 * if available. It's an error to call this function on a timeout
768 * that was not previously added.
769 * Connection lock should be held when calling this.
770 *
771 * @param connection the connection.
772 * @param timeout the timeout to remove.
773 */
774void
775_dbus_connection_remove_timeout_unlocked (DBusConnection *connection,
776                                          DBusTimeout    *timeout)
777{
778  protected_change_timeout (connection, timeout,
779                            NULL,
780                            _dbus_timeout_list_remove_timeout,
781                            NULL, FALSE);
782}
783
784/**
785 * Toggles a timeout and notifies app via connection's
786 * DBusTimeoutToggledFunction if available. It's an error to call this
787 * function on a timeout that was not previously added.
788 * Connection lock should be held when calling this.
789 *
790 * @param connection the connection.
791 * @param timeout the timeout to toggle.
792 * @param enabled whether to enable or disable
793 */
794void
795_dbus_connection_toggle_timeout_unlocked (DBusConnection   *connection,
796                                          DBusTimeout      *timeout,
797                                          dbus_bool_t       enabled)
798{
799  protected_change_timeout (connection, timeout,
800                            NULL, NULL,
801                            _dbus_timeout_list_toggle_timeout,
802                            enabled);
803}
804
805static dbus_bool_t
806_dbus_connection_attach_pending_call_unlocked (DBusConnection  *connection,
807                                               DBusPendingCall *pending)
808{
809  dbus_uint32_t reply_serial;
810  DBusTimeout *timeout;
811
812  HAVE_LOCK_CHECK (connection);
813
814  reply_serial = _dbus_pending_call_get_reply_serial_unlocked (pending);
815
816  _dbus_assert (reply_serial != 0);
817
818  timeout = _dbus_pending_call_get_timeout_unlocked (pending);
819
820  if (!_dbus_connection_add_timeout_unlocked (connection, timeout))
821    return FALSE;
822
823  if (!_dbus_hash_table_insert_int (connection->pending_replies,
824                                    reply_serial,
825                                    pending))
826    {
827      _dbus_connection_remove_timeout_unlocked (connection, timeout);
828
829      _dbus_pending_call_set_timeout_added_unlocked (pending, FALSE);
830      HAVE_LOCK_CHECK (connection);
831      return FALSE;
832    }
833
834  _dbus_pending_call_set_timeout_added_unlocked (pending, TRUE);
835
836  _dbus_pending_call_ref_unlocked (pending);
837
838  HAVE_LOCK_CHECK (connection);
839
840  return TRUE;
841}
842
843static void
844free_pending_call_on_hash_removal (void *data)
845{
846  DBusPendingCall *pending;
847  DBusConnection  *connection;
848
849  if (data == NULL)
850    return;
851
852  pending = data;
853
854  connection = _dbus_pending_call_get_connection_unlocked (pending);
855
856  HAVE_LOCK_CHECK (connection);
857
858  if (_dbus_pending_call_is_timeout_added_unlocked (pending))
859    {
860      _dbus_connection_remove_timeout_unlocked (connection,
861                                                _dbus_pending_call_get_timeout_unlocked (pending));
862
863      _dbus_pending_call_set_timeout_added_unlocked (pending, FALSE);
864    }
865
866  /* FIXME 1.0? this is sort of dangerous and undesirable to drop the lock
867   * here, but the pending call finalizer could in principle call out to
868   * application code so we pretty much have to... some larger code reorg
869   * might be needed.
870   */
871  _dbus_connection_ref_unlocked (connection);
872  _dbus_pending_call_unref_and_unlock (pending);
873  CONNECTION_LOCK (connection);
874  _dbus_connection_unref_unlocked (connection);
875}
876
877static void
878_dbus_connection_detach_pending_call_unlocked (DBusConnection  *connection,
879                                               DBusPendingCall *pending)
880{
881  /* This ends up unlocking to call the pending call finalizer, which is unexpected to
882   * say the least.
883   */
884  _dbus_hash_table_remove_int (connection->pending_replies,
885                               _dbus_pending_call_get_reply_serial_unlocked (pending));
886}
887
888static void
889_dbus_connection_detach_pending_call_and_unlock (DBusConnection  *connection,
890                                                 DBusPendingCall *pending)
891{
892  /* The idea here is to avoid finalizing the pending call
893   * with the lock held, since there's a destroy notifier
894   * in pending call that goes out to application code.
895   *
896   * There's an extra unlock inside the hash table
897   * "free pending call" function FIXME...
898   */
899  _dbus_pending_call_ref_unlocked (pending);
900  _dbus_hash_table_remove_int (connection->pending_replies,
901                               _dbus_pending_call_get_reply_serial_unlocked (pending));
902  _dbus_pending_call_unref_and_unlock (pending);
903}
904
905/**
906 * Removes a pending call from the connection, such that
907 * the pending reply will be ignored. May drop the last
908 * reference to the pending call.
909 *
910 * @param connection the connection
911 * @param pending the pending call
912 */
913void
914_dbus_connection_remove_pending_call (DBusConnection  *connection,
915                                      DBusPendingCall *pending)
916{
917  CONNECTION_LOCK (connection);
918  _dbus_connection_detach_pending_call_and_unlock (connection, pending);
919}
920
921/**
922 * Acquire the transporter I/O path. This must be done before
923 * doing any I/O in the transporter. May sleep and drop the
924 * IO path mutex while waiting for the I/O path.
925 *
926 * @param connection the connection.
927 * @param timeout_milliseconds maximum blocking time, or -1 for no limit.
928 * @returns TRUE if the I/O path was acquired.
929 */
930static dbus_bool_t
931_dbus_connection_acquire_io_path (DBusConnection *connection,
932				  int timeout_milliseconds)
933{
934  dbus_bool_t we_acquired;
935
936  HAVE_LOCK_CHECK (connection);
937
938  /* We don't want the connection to vanish */
939  _dbus_connection_ref_unlocked (connection);
940
941  /* We will only touch io_path_acquired which is protected by our mutex */
942  CONNECTION_UNLOCK (connection);
943
944  _dbus_verbose ("%s locking io_path_mutex\n", _DBUS_FUNCTION_NAME);
945  _dbus_mutex_lock (connection->io_path_mutex);
946
947  _dbus_verbose ("%s start connection->io_path_acquired = %d timeout = %d\n",
948                 _DBUS_FUNCTION_NAME, connection->io_path_acquired, timeout_milliseconds);
949
950  we_acquired = FALSE;
951
952  if (connection->io_path_acquired)
953    {
954      if (timeout_milliseconds != -1)
955        {
956          _dbus_verbose ("%s waiting %d for IO path to be acquirable\n",
957                         _DBUS_FUNCTION_NAME, timeout_milliseconds);
958          _dbus_condvar_wait_timeout (connection->io_path_cond,
959                                      connection->io_path_mutex,
960                                      timeout_milliseconds);
961        }
962      else
963        {
964          while (connection->io_path_acquired)
965            {
966              _dbus_verbose ("%s waiting for IO path to be acquirable\n", _DBUS_FUNCTION_NAME);
967              _dbus_condvar_wait (connection->io_path_cond,
968                                  connection->io_path_mutex);
969            }
970        }
971    }
972
973  if (!connection->io_path_acquired)
974    {
975      we_acquired = TRUE;
976      connection->io_path_acquired = TRUE;
977    }
978
979  _dbus_verbose ("%s end connection->io_path_acquired = %d we_acquired = %d\n",
980                 _DBUS_FUNCTION_NAME, connection->io_path_acquired, we_acquired);
981
982  _dbus_verbose ("%s unlocking io_path_mutex\n", _DBUS_FUNCTION_NAME);
983  _dbus_mutex_unlock (connection->io_path_mutex);
984
985  CONNECTION_LOCK (connection);
986
987  HAVE_LOCK_CHECK (connection);
988
989  _dbus_connection_unref_unlocked (connection);
990
991  return we_acquired;
992}
993
994/**
995 * Release the I/O path when you're done with it. Only call
996 * after you've acquired the I/O. Wakes up at most one thread
997 * currently waiting to acquire the I/O path.
998 *
999 * @param connection the connection.
1000 */
1001static void
1002_dbus_connection_release_io_path (DBusConnection *connection)
1003{
1004  HAVE_LOCK_CHECK (connection);
1005
1006  _dbus_verbose ("%s locking io_path_mutex\n", _DBUS_FUNCTION_NAME);
1007  _dbus_mutex_lock (connection->io_path_mutex);
1008
1009  _dbus_assert (connection->io_path_acquired);
1010
1011  _dbus_verbose ("%s start connection->io_path_acquired = %d\n",
1012                 _DBUS_FUNCTION_NAME, connection->io_path_acquired);
1013
1014  connection->io_path_acquired = FALSE;
1015  _dbus_condvar_wake_one (connection->io_path_cond);
1016
1017  _dbus_verbose ("%s unlocking io_path_mutex\n", _DBUS_FUNCTION_NAME);
1018  _dbus_mutex_unlock (connection->io_path_mutex);
1019}
1020
1021/**
1022 * Queues incoming messages and sends outgoing messages for this
1023 * connection, optionally blocking in the process. Each call to
1024 * _dbus_connection_do_iteration_unlocked() will call select() or poll() one
1025 * time and then read or write data if possible.
1026 *
1027 * The purpose of this function is to be able to flush outgoing
1028 * messages or queue up incoming messages without returning
1029 * control to the application and causing reentrancy weirdness.
1030 *
1031 * The flags parameter allows you to specify whether to
1032 * read incoming messages, write outgoing messages, or both,
1033 * and whether to block if no immediate action is possible.
1034 *
1035 * The timeout_milliseconds parameter does nothing unless the
1036 * iteration is blocking.
1037 *
1038 * If there are no outgoing messages and DBUS_ITERATION_DO_READING
1039 * wasn't specified, then it's impossible to block, even if
1040 * you specify DBUS_ITERATION_BLOCK; in that case the function
1041 * returns immediately.
1042 *
1043 * Called with connection lock held.
1044 *
1045 * @param connection the connection.
1046 * @param flags iteration flags.
1047 * @param timeout_milliseconds maximum blocking time, or -1 for no limit.
1048 */
1049void
1050_dbus_connection_do_iteration_unlocked (DBusConnection *connection,
1051                                        unsigned int    flags,
1052                                        int             timeout_milliseconds)
1053{
1054  _dbus_verbose ("%s start\n", _DBUS_FUNCTION_NAME);
1055
1056  HAVE_LOCK_CHECK (connection);
1057
1058  if (connection->n_outgoing == 0)
1059    flags &= ~DBUS_ITERATION_DO_WRITING;
1060
1061  if (_dbus_connection_acquire_io_path (connection,
1062					(flags & DBUS_ITERATION_BLOCK) ? timeout_milliseconds : 0))
1063    {
1064      HAVE_LOCK_CHECK (connection);
1065
1066      _dbus_transport_do_iteration (connection->transport,
1067				    flags, timeout_milliseconds);
1068      _dbus_connection_release_io_path (connection);
1069    }
1070
1071  HAVE_LOCK_CHECK (connection);
1072
1073  _dbus_verbose ("%s end\n", _DBUS_FUNCTION_NAME);
1074}
1075
1076/**
1077 * Creates a new connection for the given transport.  A transport
1078 * represents a message stream that uses some concrete mechanism, such
1079 * as UNIX domain sockets. May return #NULL if insufficient
1080 * memory exists to create the connection.
1081 *
1082 * @param transport the transport.
1083 * @returns the new connection, or #NULL on failure.
1084 */
1085DBusConnection*
1086_dbus_connection_new_for_transport (DBusTransport *transport)
1087{
1088  DBusConnection *connection;
1089  DBusWatchList *watch_list;
1090  DBusTimeoutList *timeout_list;
1091  DBusHashTable *pending_replies;
1092  DBusList *disconnect_link;
1093  DBusMessage *disconnect_message;
1094  DBusCounter *outgoing_counter;
1095  DBusObjectTree *objects;
1096
1097  watch_list = NULL;
1098  connection = NULL;
1099  pending_replies = NULL;
1100  timeout_list = NULL;
1101  disconnect_link = NULL;
1102  disconnect_message = NULL;
1103  outgoing_counter = NULL;
1104  objects = NULL;
1105
1106  watch_list = _dbus_watch_list_new ();
1107  if (watch_list == NULL)
1108    goto error;
1109
1110  timeout_list = _dbus_timeout_list_new ();
1111  if (timeout_list == NULL)
1112    goto error;
1113
1114  pending_replies =
1115    _dbus_hash_table_new (DBUS_HASH_INT,
1116			  NULL,
1117                          (DBusFreeFunction)free_pending_call_on_hash_removal);
1118  if (pending_replies == NULL)
1119    goto error;
1120
1121  connection = dbus_new0 (DBusConnection, 1);
1122  if (connection == NULL)
1123    goto error;
1124
1125  _dbus_mutex_new_at_location (&connection->mutex);
1126  if (connection->mutex == NULL)
1127    goto error;
1128
1129  _dbus_mutex_new_at_location (&connection->io_path_mutex);
1130  if (connection->io_path_mutex == NULL)
1131    goto error;
1132
1133  _dbus_mutex_new_at_location (&connection->dispatch_mutex);
1134  if (connection->dispatch_mutex == NULL)
1135    goto error;
1136
1137  _dbus_condvar_new_at_location (&connection->dispatch_cond);
1138  if (connection->dispatch_cond == NULL)
1139    goto error;
1140
1141  _dbus_condvar_new_at_location (&connection->io_path_cond);
1142  if (connection->io_path_cond == NULL)
1143    goto error;
1144
1145  disconnect_message = dbus_message_new_signal (DBUS_PATH_LOCAL,
1146                                                DBUS_INTERFACE_LOCAL,
1147                                                "Disconnected");
1148
1149  if (disconnect_message == NULL)
1150    goto error;
1151
1152  disconnect_link = _dbus_list_alloc_link (disconnect_message);
1153  if (disconnect_link == NULL)
1154    goto error;
1155
1156  outgoing_counter = _dbus_counter_new ();
1157  if (outgoing_counter == NULL)
1158    goto error;
1159
1160  objects = _dbus_object_tree_new (connection);
1161  if (objects == NULL)
1162    goto error;
1163
1164  if (_dbus_modify_sigpipe)
1165    _dbus_disable_sigpipe ();
1166
1167  connection->refcount.value = 1;
1168  connection->transport = transport;
1169  connection->watches = watch_list;
1170  connection->timeouts = timeout_list;
1171  connection->pending_replies = pending_replies;
1172  connection->outgoing_counter = outgoing_counter;
1173  connection->filter_list = NULL;
1174  connection->last_dispatch_status = DBUS_DISPATCH_COMPLETE; /* so we're notified first time there's data */
1175  connection->objects = objects;
1176  connection->exit_on_disconnect = FALSE;
1177  connection->shareable = FALSE;
1178#ifndef DBUS_DISABLE_CHECKS
1179  connection->generation = _dbus_current_generation;
1180#endif
1181
1182  _dbus_data_slot_list_init (&connection->slot_list);
1183
1184  connection->client_serial = 1;
1185
1186  connection->disconnect_message_link = disconnect_link;
1187
1188  CONNECTION_LOCK (connection);
1189
1190  if (!_dbus_transport_set_connection (transport, connection))
1191    {
1192      CONNECTION_UNLOCK (connection);
1193
1194      goto error;
1195    }
1196
1197  _dbus_transport_ref (transport);
1198
1199  CONNECTION_UNLOCK (connection);
1200
1201  return connection;
1202
1203 error:
1204  if (disconnect_message != NULL)
1205    dbus_message_unref (disconnect_message);
1206
1207  if (disconnect_link != NULL)
1208    _dbus_list_free_link (disconnect_link);
1209
1210  if (connection != NULL)
1211    {
1212      _dbus_condvar_free_at_location (&connection->io_path_cond);
1213      _dbus_condvar_free_at_location (&connection->dispatch_cond);
1214      _dbus_mutex_free_at_location (&connection->mutex);
1215      _dbus_mutex_free_at_location (&connection->io_path_mutex);
1216      _dbus_mutex_free_at_location (&connection->dispatch_mutex);
1217      dbus_free (connection);
1218    }
1219  if (pending_replies)
1220    _dbus_hash_table_unref (pending_replies);
1221
1222  if (watch_list)
1223    _dbus_watch_list_free (watch_list);
1224
1225  if (timeout_list)
1226    _dbus_timeout_list_free (timeout_list);
1227
1228  if (outgoing_counter)
1229    _dbus_counter_unref (outgoing_counter);
1230
1231  if (objects)
1232    _dbus_object_tree_unref (objects);
1233
1234  return NULL;
1235}
1236
1237/**
1238 * Increments the reference count of a DBusConnection.
1239 * Requires that the caller already holds the connection lock.
1240 *
1241 * @param connection the connection.
1242 * @returns the connection.
1243 */
1244DBusConnection *
1245_dbus_connection_ref_unlocked (DBusConnection *connection)
1246{
1247  _dbus_assert (connection != NULL);
1248  _dbus_assert (connection->generation == _dbus_current_generation);
1249
1250  HAVE_LOCK_CHECK (connection);
1251
1252#ifdef DBUS_HAVE_ATOMIC_INT
1253  _dbus_atomic_inc (&connection->refcount);
1254#else
1255  _dbus_assert (connection->refcount.value > 0);
1256  connection->refcount.value += 1;
1257#endif
1258
1259  return connection;
1260}
1261
1262/**
1263 * Decrements the reference count of a DBusConnection.
1264 * Requires that the caller already holds the connection lock.
1265 *
1266 * @param connection the connection.
1267 */
1268void
1269_dbus_connection_unref_unlocked (DBusConnection *connection)
1270{
1271  dbus_bool_t last_unref;
1272
1273  HAVE_LOCK_CHECK (connection);
1274
1275  _dbus_assert (connection != NULL);
1276
1277  /* The connection lock is better than the global
1278   * lock in the atomic increment fallback
1279   */
1280
1281#ifdef DBUS_HAVE_ATOMIC_INT
1282  last_unref = (_dbus_atomic_dec (&connection->refcount) == 1);
1283#else
1284  _dbus_assert (connection->refcount.value > 0);
1285
1286  connection->refcount.value -= 1;
1287  last_unref = (connection->refcount.value == 0);
1288#if 0
1289  printf ("unref_unlocked() connection %p count = %d\n", connection, connection->refcount.value);
1290#endif
1291#endif
1292
1293  if (last_unref)
1294    _dbus_connection_last_unref (connection);
1295}
1296
1297static dbus_uint32_t
1298_dbus_connection_get_next_client_serial (DBusConnection *connection)
1299{
1300  int serial;
1301
1302  serial = connection->client_serial++;
1303
1304  if (connection->client_serial < 0)
1305    connection->client_serial = 1;
1306
1307  return serial;
1308}
1309
1310/**
1311 * A callback for use with dbus_watch_new() to create a DBusWatch.
1312 *
1313 * @todo This is basically a hack - we could delete _dbus_transport_handle_watch()
1314 * and the virtual handle_watch in DBusTransport if we got rid of it.
1315 * The reason this is some work is threading, see the _dbus_connection_handle_watch()
1316 * implementation.
1317 *
1318 * @param watch the watch.
1319 * @param condition the current condition of the file descriptors being watched.
1320 * @param data must be a pointer to a #DBusConnection
1321 * @returns #FALSE if the IO condition may not have been fully handled due to lack of memory
1322 */
1323dbus_bool_t
1324_dbus_connection_handle_watch (DBusWatch                   *watch,
1325                               unsigned int                 condition,
1326                               void                        *data)
1327{
1328  DBusConnection *connection;
1329  dbus_bool_t retval;
1330  DBusDispatchStatus status;
1331
1332  connection = data;
1333
1334  _dbus_verbose ("%s start\n", _DBUS_FUNCTION_NAME);
1335
1336  CONNECTION_LOCK (connection);
1337  _dbus_connection_acquire_io_path (connection, -1);
1338  HAVE_LOCK_CHECK (connection);
1339  retval = _dbus_transport_handle_watch (connection->transport,
1340                                         watch, condition);
1341
1342  _dbus_connection_release_io_path (connection);
1343
1344  HAVE_LOCK_CHECK (connection);
1345
1346  _dbus_verbose ("%s middle\n", _DBUS_FUNCTION_NAME);
1347
1348  status = _dbus_connection_get_dispatch_status_unlocked (connection);
1349
1350  /* this calls out to user code */
1351  _dbus_connection_update_dispatch_status_and_unlock (connection, status);
1352
1353  _dbus_verbose ("%s end\n", _DBUS_FUNCTION_NAME);
1354
1355  return retval;
1356}
1357
1358_DBUS_DEFINE_GLOBAL_LOCK (shared_connections);
1359static DBusHashTable *shared_connections = NULL;
1360
1361static void
1362shared_connections_shutdown (void *data)
1363{
1364  _DBUS_LOCK (shared_connections);
1365
1366  _dbus_assert (_dbus_hash_table_get_n_entries (shared_connections) == 0);
1367
1368  _dbus_hash_table_unref (shared_connections);
1369  shared_connections = NULL;
1370
1371  _DBUS_UNLOCK (shared_connections);
1372}
1373
1374static dbus_bool_t
1375connection_lookup_shared (DBusAddressEntry  *entry,
1376                          DBusConnection   **result)
1377{
1378  _dbus_verbose ("checking for existing connection\n");
1379
1380  *result = NULL;
1381
1382  _DBUS_LOCK (shared_connections);
1383
1384  if (shared_connections == NULL)
1385    {
1386      _dbus_verbose ("creating shared_connections hash table\n");
1387
1388      shared_connections = _dbus_hash_table_new (DBUS_HASH_STRING,
1389                                                 dbus_free,
1390                                                 NULL);
1391      if (shared_connections == NULL)
1392        {
1393          _DBUS_UNLOCK (shared_connections);
1394          return FALSE;
1395        }
1396
1397      if (!_dbus_register_shutdown_func (shared_connections_shutdown, NULL))
1398        {
1399          _dbus_hash_table_unref (shared_connections);
1400          shared_connections = NULL;
1401          _DBUS_UNLOCK (shared_connections);
1402          return FALSE;
1403        }
1404
1405      _dbus_verbose ("  successfully created shared_connections\n");
1406
1407      _DBUS_UNLOCK (shared_connections);
1408      return TRUE; /* no point looking up in the hash we just made */
1409    }
1410  else
1411    {
1412      const char *guid;
1413
1414      guid = dbus_address_entry_get_value (entry, "guid");
1415
1416      if (guid != NULL)
1417        {
1418          *result = _dbus_hash_table_lookup_string (shared_connections,
1419                                                    guid);
1420
1421          if (*result)
1422            {
1423              /* The DBusConnection can't have been disconnected
1424               * between the lookup and this code, because the
1425               * disconnection will take the shared_connections lock to
1426               * remove the connection. It can't have been finalized
1427               * since you have to disconnect prior to finalize.
1428               *
1429               * Thus it's safe to ref the connection.
1430               */
1431              dbus_connection_ref (*result);
1432
1433              _dbus_verbose ("looked up existing connection to server guid %s\n",
1434                             guid);
1435            }
1436        }
1437
1438      _DBUS_UNLOCK (shared_connections);
1439      return TRUE;
1440    }
1441}
1442
1443static dbus_bool_t
1444connection_record_shared_unlocked (DBusConnection *connection,
1445                                   const char     *guid)
1446{
1447  char *guid_key;
1448  char *guid_in_connection;
1449
1450  /* A separate copy of the key is required in the hash table, because
1451   * we don't have a lock on the connection when we are doing a hash
1452   * lookup.
1453   */
1454
1455  _dbus_assert (connection->server_guid == NULL);
1456  _dbus_assert (connection->shareable);
1457
1458  guid_key = _dbus_strdup (guid);
1459  if (guid_key == NULL)
1460    return FALSE;
1461
1462  guid_in_connection = _dbus_strdup (guid);
1463  if (guid_in_connection == NULL)
1464    {
1465      dbus_free (guid_key);
1466      return FALSE;
1467    }
1468
1469  _DBUS_LOCK (shared_connections);
1470  _dbus_assert (shared_connections != NULL);
1471
1472  if (!_dbus_hash_table_insert_string (shared_connections,
1473                                       guid_key, connection))
1474    {
1475      dbus_free (guid_key);
1476      dbus_free (guid_in_connection);
1477      _DBUS_UNLOCK (shared_connections);
1478      return FALSE;
1479    }
1480
1481  connection->server_guid = guid_in_connection;
1482  connection->shared = TRUE;
1483
1484  /* get a hard ref on this connection */
1485  dbus_connection_ref (connection);
1486
1487  _dbus_verbose ("stored connection to %s to be shared\n",
1488                 connection->server_guid);
1489
1490  _DBUS_UNLOCK (shared_connections);
1491
1492  _dbus_assert (connection->server_guid != NULL);
1493
1494  return TRUE;
1495}
1496
1497static void
1498connection_forget_shared_unlocked (DBusConnection *connection)
1499{
1500  HAVE_LOCK_CHECK (connection);
1501
1502  if (connection->server_guid == NULL)
1503    return;
1504
1505  _dbus_verbose ("dropping connection to %s out of the shared table\n",
1506                 connection->server_guid);
1507
1508  _DBUS_LOCK (shared_connections);
1509
1510  if (!_dbus_hash_table_remove_string (shared_connections,
1511                                       connection->server_guid))
1512    _dbus_assert_not_reached ("connection was not in the shared table");
1513
1514  dbus_free (connection->server_guid);
1515  connection->server_guid = NULL;
1516
1517  /* remove the hash ref */
1518  _dbus_connection_unref_unlocked (connection);
1519  _DBUS_UNLOCK (shared_connections);
1520}
1521
1522static DBusConnection*
1523connection_try_from_address_entry (DBusAddressEntry *entry,
1524                                   DBusError        *error)
1525{
1526  DBusTransport *transport;
1527  DBusConnection *connection;
1528
1529  transport = _dbus_transport_open (entry, error);
1530
1531  if (transport == NULL)
1532    {
1533      _DBUS_ASSERT_ERROR_IS_SET (error);
1534      return NULL;
1535    }
1536
1537  connection = _dbus_connection_new_for_transport (transport);
1538
1539  _dbus_transport_unref (transport);
1540
1541  if (connection == NULL)
1542    {
1543      _DBUS_SET_OOM (error);
1544      return NULL;
1545    }
1546
1547#ifndef DBUS_DISABLE_CHECKS
1548  _dbus_assert (!connection->have_connection_lock);
1549#endif
1550  return connection;
1551}
1552
1553/*
1554 * If the shared parameter is true, then any existing connection will
1555 * be used (and if a new connection is created, it will be available
1556 * for use by others). If the shared parameter is false, a new
1557 * connection will always be created, and the new connection will
1558 * never be returned to other callers.
1559 *
1560 * @param address the address
1561 * @param shared whether the connection is shared or private
1562 * @param error error return
1563 * @returns the connection or #NULL on error
1564 */
1565static DBusConnection*
1566_dbus_connection_open_internal (const char     *address,
1567                                dbus_bool_t     shared,
1568                                DBusError      *error)
1569{
1570  DBusConnection *connection;
1571  DBusAddressEntry **entries;
1572  DBusError tmp_error;
1573  DBusError first_error;
1574  int len, i;
1575
1576  _DBUS_ASSERT_ERROR_IS_CLEAR (error);
1577
1578  _dbus_verbose ("opening %s connection to: %s\n",
1579                 shared ? "shared" : "private", address);
1580
1581  if (!dbus_parse_address (address, &entries, &len, error))
1582    return NULL;
1583
1584  _DBUS_ASSERT_ERROR_IS_CLEAR (error);
1585
1586  connection = NULL;
1587
1588  dbus_error_init (&tmp_error);
1589  dbus_error_init (&first_error);
1590  for (i = 0; i < len; i++)
1591    {
1592      if (shared)
1593        {
1594          if (!connection_lookup_shared (entries[i], &connection))
1595            _DBUS_SET_OOM (&tmp_error);
1596        }
1597
1598      if (connection == NULL)
1599        {
1600          connection = connection_try_from_address_entry (entries[i],
1601                                                          &tmp_error);
1602
1603          if (connection != NULL && shared)
1604            {
1605              const char *guid;
1606
1607              connection->shareable = TRUE;
1608
1609              guid = dbus_address_entry_get_value (entries[i], "guid");
1610
1611              /* we don't have a connection lock but we know nobody
1612               * else has a handle to the connection
1613               */
1614
1615              if (guid &&
1616                  !connection_record_shared_unlocked (connection, guid))
1617                {
1618                  _DBUS_SET_OOM (&tmp_error);
1619                  _dbus_connection_close_internal (connection);
1620                  dbus_connection_unref (connection);
1621                  connection = NULL;
1622                }
1623
1624              /* but as of now the connection is possibly shared
1625               * since another thread could have pulled it from the table
1626               */
1627            }
1628        }
1629
1630      if (connection)
1631	break;
1632
1633      _DBUS_ASSERT_ERROR_IS_SET (&tmp_error);
1634
1635      if (i == 0)
1636        dbus_move_error (&tmp_error, &first_error);
1637      else
1638        dbus_error_free (&tmp_error);
1639    }
1640
1641  /* NOTE we don't have a lock on a possibly-shared connection object */
1642
1643  _DBUS_ASSERT_ERROR_IS_CLEAR (error);
1644  _DBUS_ASSERT_ERROR_IS_CLEAR (&tmp_error);
1645
1646  if (connection == NULL)
1647    {
1648      _DBUS_ASSERT_ERROR_IS_SET (&first_error);
1649      dbus_move_error (&first_error, error);
1650    }
1651  else
1652    {
1653      dbus_error_free (&first_error);
1654    }
1655
1656  dbus_address_entries_free (entries);
1657  return connection;
1658}
1659
1660/** @} */
1661
1662/**
1663 * @addtogroup DBusConnection
1664 *
1665 * @{
1666 */
1667
1668/**
1669 * Gets a connection to a remote address. If a connection to the given
1670 * address already exists, returns the existing connection with its
1671 * reference count incremented.  Otherwise, returns a new connection
1672 * and saves the new connection for possible re-use if a future call
1673 * to dbus_connection_open() asks to connect to the same server.
1674 *
1675 * Use dbus_connection_open_private() to get a dedicated connection
1676 * not shared with other callers of dbus_connection_open().
1677 *
1678 * If the open fails, the function returns #NULL, and provides a
1679 * reason for the failure in the error parameter. Pass #NULL for the
1680 * error parameter if you aren't interested in the reason for
1681 * failure.
1682 *
1683 * @param address the address.
1684 * @param error address where an error can be returned.
1685 * @returns new connection, or #NULL on failure.
1686 */
1687DBusConnection*
1688dbus_connection_open (const char     *address,
1689                      DBusError      *error)
1690{
1691  DBusConnection *connection;
1692
1693  _dbus_return_val_if_fail (address != NULL, NULL);
1694  _dbus_return_val_if_error_is_set (error, NULL);
1695
1696  connection = _dbus_connection_open_internal (address,
1697                                               TRUE,
1698                                               error);
1699
1700  return connection;
1701}
1702
1703/**
1704 * Opens a new, dedicated connection to a remote address. Unlike
1705 * dbus_connection_open(), always creates a new connection.
1706 * This connection will not be saved or recycled by libdbus.
1707 *
1708 * If the open fails, the function returns #NULL, and provides a
1709 * reason for the failure in the error parameter. Pass #NULL for the
1710 * error parameter if you aren't interested in the reason for
1711 * failure.
1712 *
1713 * @param address the address.
1714 * @param error address where an error can be returned.
1715 * @returns new connection, or #NULL on failure.
1716 */
1717DBusConnection*
1718dbus_connection_open_private (const char     *address,
1719                              DBusError      *error)
1720{
1721  DBusConnection *connection;
1722
1723  _dbus_return_val_if_fail (address != NULL, NULL);
1724  _dbus_return_val_if_error_is_set (error, NULL);
1725
1726  connection = _dbus_connection_open_internal (address,
1727                                               FALSE,
1728                                               error);
1729
1730  return connection;
1731}
1732
1733/**
1734 * Increments the reference count of a DBusConnection.
1735 *
1736 * @param connection the connection.
1737 * @returns the connection.
1738 */
1739DBusConnection *
1740dbus_connection_ref (DBusConnection *connection)
1741{
1742  _dbus_return_val_if_fail (connection != NULL, NULL);
1743  _dbus_return_val_if_fail (connection->generation == _dbus_current_generation, NULL);
1744
1745  /* The connection lock is better than the global
1746   * lock in the atomic increment fallback
1747   */
1748
1749#ifdef DBUS_HAVE_ATOMIC_INT
1750  _dbus_atomic_inc (&connection->refcount);
1751#else
1752  CONNECTION_LOCK (connection);
1753  _dbus_assert (connection->refcount.value > 0);
1754
1755  connection->refcount.value += 1;
1756  CONNECTION_UNLOCK (connection);
1757#endif
1758
1759  return connection;
1760}
1761
1762static void
1763free_outgoing_message (void *element,
1764                       void *data)
1765{
1766  DBusMessage *message = element;
1767  DBusConnection *connection = data;
1768
1769  _dbus_message_remove_size_counter (message,
1770                                     connection->outgoing_counter,
1771                                     NULL);
1772  dbus_message_unref (message);
1773}
1774
1775/* This is run without the mutex held, but after the last reference
1776 * to the connection has been dropped we should have no thread-related
1777 * problems
1778 */
1779static void
1780_dbus_connection_last_unref (DBusConnection *connection)
1781{
1782  DBusList *link;
1783
1784  _dbus_verbose ("Finalizing connection %p\n", connection);
1785
1786  _dbus_assert (connection->refcount.value == 0);
1787
1788  /* You have to disconnect the connection before unref:ing it. Otherwise
1789   * you won't get the disconnected message.
1790   */
1791  _dbus_assert (!_dbus_transport_get_is_connected (connection->transport));
1792  _dbus_assert (connection->server_guid == NULL);
1793
1794  /* ---- We're going to call various application callbacks here, hope it doesn't break anything... */
1795  _dbus_object_tree_free_all_unlocked (connection->objects);
1796
1797  dbus_connection_set_dispatch_status_function (connection, NULL, NULL, NULL);
1798  dbus_connection_set_wakeup_main_function (connection, NULL, NULL, NULL);
1799  dbus_connection_set_unix_user_function (connection, NULL, NULL, NULL);
1800
1801  _dbus_watch_list_free (connection->watches);
1802  connection->watches = NULL;
1803
1804  _dbus_timeout_list_free (connection->timeouts);
1805  connection->timeouts = NULL;
1806
1807  _dbus_data_slot_list_free (&connection->slot_list);
1808
1809  link = _dbus_list_get_first_link (&connection->filter_list);
1810  while (link != NULL)
1811    {
1812      DBusMessageFilter *filter = link->data;
1813      DBusList *next = _dbus_list_get_next_link (&connection->filter_list, link);
1814
1815      filter->function = NULL;
1816      _dbus_message_filter_unref (filter); /* calls app callback */
1817      link->data = NULL;
1818
1819      link = next;
1820    }
1821  _dbus_list_clear (&connection->filter_list);
1822
1823  /* ---- Done with stuff that invokes application callbacks */
1824
1825  _dbus_object_tree_unref (connection->objects);
1826
1827  _dbus_hash_table_unref (connection->pending_replies);
1828  connection->pending_replies = NULL;
1829
1830  _dbus_list_clear (&connection->filter_list);
1831
1832  _dbus_list_foreach (&connection->outgoing_messages,
1833                      free_outgoing_message,
1834		      connection);
1835  _dbus_list_clear (&connection->outgoing_messages);
1836
1837  _dbus_list_foreach (&connection->incoming_messages,
1838		      (DBusForeachFunction) dbus_message_unref,
1839		      NULL);
1840  _dbus_list_clear (&connection->incoming_messages);
1841
1842  _dbus_counter_unref (connection->outgoing_counter);
1843
1844  _dbus_transport_unref (connection->transport);
1845
1846  if (connection->disconnect_message_link)
1847    {
1848      DBusMessage *message = connection->disconnect_message_link->data;
1849      dbus_message_unref (message);
1850      _dbus_list_free_link (connection->disconnect_message_link);
1851    }
1852
1853  _dbus_list_clear (&connection->link_cache);
1854
1855  _dbus_condvar_free_at_location (&connection->dispatch_cond);
1856  _dbus_condvar_free_at_location (&connection->io_path_cond);
1857
1858  _dbus_mutex_free_at_location (&connection->io_path_mutex);
1859  _dbus_mutex_free_at_location (&connection->dispatch_mutex);
1860
1861  _dbus_mutex_free_at_location (&connection->mutex);
1862
1863  dbus_free (connection);
1864}
1865
1866/**
1867 * Decrements the reference count of a DBusConnection, and finalizes
1868 * it if the count reaches zero.  It is a bug to drop the last reference
1869 * to a connection that has not been disconnected.
1870 *
1871 * @todo in practice it can be quite tricky to never unref a connection
1872 * that's still connected; maybe there's some way we could avoid
1873 * the requirement.
1874 *
1875 * @param connection the connection.
1876 */
1877void
1878dbus_connection_unref (DBusConnection *connection)
1879{
1880  dbus_bool_t last_unref;
1881
1882  _dbus_return_if_fail (connection != NULL);
1883  _dbus_return_if_fail (connection->generation == _dbus_current_generation);
1884
1885  /* The connection lock is better than the global
1886   * lock in the atomic increment fallback
1887   */
1888
1889#ifdef DBUS_HAVE_ATOMIC_INT
1890  last_unref = (_dbus_atomic_dec (&connection->refcount) == 1);
1891#else
1892  CONNECTION_LOCK (connection);
1893
1894  _dbus_assert (connection->refcount.value > 0);
1895
1896  connection->refcount.value -= 1;
1897  last_unref = (connection->refcount.value == 0);
1898
1899#if 0
1900  printf ("unref() connection %p count = %d\n", connection, connection->refcount.value);
1901#endif
1902
1903  CONNECTION_UNLOCK (connection);
1904#endif
1905
1906  if (last_unref)
1907    _dbus_connection_last_unref (connection);
1908}
1909
1910static void
1911_dbus_connection_close_internal_and_unlock (DBusConnection *connection)
1912{
1913  DBusDispatchStatus status;
1914
1915  _dbus_verbose ("Disconnecting %p\n", connection);
1916
1917  _dbus_transport_disconnect (connection->transport);
1918
1919  _dbus_verbose ("%s middle\n", _DBUS_FUNCTION_NAME);
1920  status = _dbus_connection_get_dispatch_status_unlocked (connection);
1921
1922  /* this calls out to user code */
1923  _dbus_connection_update_dispatch_status_and_unlock (connection, status);
1924}
1925
1926void
1927_dbus_connection_close_internal (DBusConnection *connection)
1928{
1929  _dbus_assert (connection != NULL);
1930  _dbus_assert (connection->generation == _dbus_current_generation);
1931
1932  CONNECTION_LOCK (connection);
1933  _dbus_connection_close_internal_and_unlock (connection);
1934}
1935
1936/**
1937 * Closes the connection, so no further data can be sent or received.
1938 * Any further attempts to send data will result in errors.  This
1939 * function does not affect the connection's reference count.  It's
1940 * safe to disconnect a connection more than once; all calls after the
1941 * first do nothing. It's impossible to "reopen" a connection, a
1942 * new connection must be created. This function may result in a call
1943 * to the DBusDispatchStatusFunction set with
1944 * dbus_connection_set_dispatch_status_function(), as the disconnect
1945 * message it generates needs to be dispatched.
1946 *
1947 * If the connection is a shared connection we print out a warning that
1948 * you can not close shared connection and we return.  Internal calls
1949 * should use _dbus_connection_close_internal() to close shared connections.
1950 *
1951 * @param connection the connection.
1952 */
1953void
1954dbus_connection_close (DBusConnection *connection)
1955{
1956  _dbus_return_if_fail (connection != NULL);
1957  _dbus_return_if_fail (connection->generation == _dbus_current_generation);
1958
1959  CONNECTION_LOCK (connection);
1960
1961  if (connection->shared)
1962    {
1963      CONNECTION_UNLOCK (connection);
1964
1965      _dbus_warn ("Applications can not close shared connections.  Please fix this in your app.  Ignoring close request and continuing.");
1966      return;
1967    }
1968
1969  _dbus_connection_close_internal_and_unlock (connection);
1970}
1971
1972static dbus_bool_t
1973_dbus_connection_get_is_connected_unlocked (DBusConnection *connection)
1974{
1975  HAVE_LOCK_CHECK (connection);
1976  return _dbus_transport_get_is_connected (connection->transport);
1977}
1978
1979/**
1980 * Gets whether the connection is currently connected.  All
1981 * connections are connected when they are opened.  A connection may
1982 * become disconnected when the remote application closes its end, or
1983 * exits; a connection may also be disconnected with
1984 * dbus_connection_close().
1985 *
1986 * @param connection the connection.
1987 * @returns #TRUE if the connection is still alive.
1988 */
1989dbus_bool_t
1990dbus_connection_get_is_connected (DBusConnection *connection)
1991{
1992  dbus_bool_t res;
1993
1994  _dbus_return_val_if_fail (connection != NULL, FALSE);
1995
1996  CONNECTION_LOCK (connection);
1997  res = _dbus_connection_get_is_connected_unlocked (connection);
1998  CONNECTION_UNLOCK (connection);
1999
2000  return res;
2001}
2002
2003/**
2004 * Gets whether the connection was authenticated. (Note that
2005 * if the connection was authenticated then disconnected,
2006 * this function still returns #TRUE)
2007 *
2008 * @param connection the connection
2009 * @returns #TRUE if the connection was ever authenticated
2010 */
2011dbus_bool_t
2012dbus_connection_get_is_authenticated (DBusConnection *connection)
2013{
2014  dbus_bool_t res;
2015
2016  _dbus_return_val_if_fail (connection != NULL, FALSE);
2017
2018  CONNECTION_LOCK (connection);
2019  res = _dbus_transport_get_is_authenticated (connection->transport);
2020  CONNECTION_UNLOCK (connection);
2021
2022  return res;
2023}
2024
2025/**
2026 * Set whether _exit() should be called when the connection receives a
2027 * disconnect signal. The call to _exit() comes after any handlers for
2028 * the disconnect signal run; handlers can cancel the exit by calling
2029 * this function.
2030 *
2031 * By default, exit_on_disconnect is #FALSE; but for message bus
2032 * connections returned from dbus_bus_get() it will be toggled on
2033 * by default.
2034 *
2035 * @param connection the connection
2036 * @param exit_on_disconnect #TRUE if _exit() should be called after a disconnect signal
2037 */
2038void
2039dbus_connection_set_exit_on_disconnect (DBusConnection *connection,
2040                                        dbus_bool_t     exit_on_disconnect)
2041{
2042  _dbus_return_if_fail (connection != NULL);
2043
2044  CONNECTION_LOCK (connection);
2045  connection->exit_on_disconnect = exit_on_disconnect != FALSE;
2046  CONNECTION_UNLOCK (connection);
2047}
2048
2049static DBusPreallocatedSend*
2050_dbus_connection_preallocate_send_unlocked (DBusConnection *connection)
2051{
2052  DBusPreallocatedSend *preallocated;
2053
2054  HAVE_LOCK_CHECK (connection);
2055
2056  _dbus_assert (connection != NULL);
2057
2058  preallocated = dbus_new (DBusPreallocatedSend, 1);
2059  if (preallocated == NULL)
2060    return NULL;
2061
2062  if (connection->link_cache != NULL)
2063    {
2064      preallocated->queue_link =
2065        _dbus_list_pop_first_link (&connection->link_cache);
2066      preallocated->queue_link->data = NULL;
2067    }
2068  else
2069    {
2070      preallocated->queue_link = _dbus_list_alloc_link (NULL);
2071      if (preallocated->queue_link == NULL)
2072        goto failed_0;
2073    }
2074
2075  if (connection->link_cache != NULL)
2076    {
2077      preallocated->counter_link =
2078        _dbus_list_pop_first_link (&connection->link_cache);
2079      preallocated->counter_link->data = connection->outgoing_counter;
2080    }
2081  else
2082    {
2083      preallocated->counter_link = _dbus_list_alloc_link (connection->outgoing_counter);
2084      if (preallocated->counter_link == NULL)
2085        goto failed_1;
2086    }
2087
2088  _dbus_counter_ref (preallocated->counter_link->data);
2089
2090  preallocated->connection = connection;
2091
2092  return preallocated;
2093
2094 failed_1:
2095  _dbus_list_free_link (preallocated->queue_link);
2096 failed_0:
2097  dbus_free (preallocated);
2098
2099  return NULL;
2100}
2101
2102/**
2103 * Preallocates resources needed to send a message, allowing the message
2104 * to be sent without the possibility of memory allocation failure.
2105 * Allows apps to create a future guarantee that they can send
2106 * a message regardless of memory shortages.
2107 *
2108 * @param connection the connection we're preallocating for.
2109 * @returns the preallocated resources, or #NULL
2110 */
2111DBusPreallocatedSend*
2112dbus_connection_preallocate_send (DBusConnection *connection)
2113{
2114  DBusPreallocatedSend *preallocated;
2115
2116  _dbus_return_val_if_fail (connection != NULL, NULL);
2117
2118  CONNECTION_LOCK (connection);
2119
2120  preallocated =
2121    _dbus_connection_preallocate_send_unlocked (connection);
2122
2123  CONNECTION_UNLOCK (connection);
2124
2125  return preallocated;
2126}
2127
2128/**
2129 * Frees preallocated message-sending resources from
2130 * dbus_connection_preallocate_send(). Should only
2131 * be called if the preallocated resources are not used
2132 * to send a message.
2133 *
2134 * @param connection the connection
2135 * @param preallocated the resources
2136 */
2137void
2138dbus_connection_free_preallocated_send (DBusConnection       *connection,
2139                                        DBusPreallocatedSend *preallocated)
2140{
2141  _dbus_return_if_fail (connection != NULL);
2142  _dbus_return_if_fail (preallocated != NULL);
2143  _dbus_return_if_fail (connection == preallocated->connection);
2144
2145  _dbus_list_free_link (preallocated->queue_link);
2146  _dbus_counter_unref (preallocated->counter_link->data);
2147  _dbus_list_free_link (preallocated->counter_link);
2148  dbus_free (preallocated);
2149}
2150
2151/* Called with lock held, does not update dispatch status */
2152static void
2153_dbus_connection_send_preallocated_unlocked_no_update (DBusConnection       *connection,
2154                                                       DBusPreallocatedSend *preallocated,
2155                                                       DBusMessage          *message,
2156                                                       dbus_uint32_t        *client_serial)
2157{
2158  dbus_uint32_t serial;
2159  const char *sig;
2160
2161  preallocated->queue_link->data = message;
2162  _dbus_list_prepend_link (&connection->outgoing_messages,
2163                           preallocated->queue_link);
2164
2165  _dbus_message_add_size_counter_link (message,
2166                                       preallocated->counter_link);
2167
2168  dbus_free (preallocated);
2169  preallocated = NULL;
2170
2171  dbus_message_ref (message);
2172
2173  connection->n_outgoing += 1;
2174
2175  sig = dbus_message_get_signature (message);
2176
2177  _dbus_verbose ("Message %p (%d %s %s %s '%s') for %s added to outgoing queue %p, %d pending to send\n",
2178                 message,
2179                 dbus_message_get_type (message),
2180                 dbus_message_get_path (message) ?
2181                 dbus_message_get_path (message) :
2182                 "no path",
2183                 dbus_message_get_interface (message) ?
2184                 dbus_message_get_interface (message) :
2185                 "no interface",
2186                 dbus_message_get_member (message) ?
2187                 dbus_message_get_member (message) :
2188                 "no member",
2189                 sig,
2190                 dbus_message_get_destination (message) ?
2191                 dbus_message_get_destination (message) :
2192                 "null",
2193                 connection,
2194                 connection->n_outgoing);
2195
2196  if (dbus_message_get_serial (message) == 0)
2197    {
2198      serial = _dbus_connection_get_next_client_serial (connection);
2199      _dbus_message_set_serial (message, serial);
2200      if (client_serial)
2201        *client_serial = serial;
2202    }
2203  else
2204    {
2205      if (client_serial)
2206        *client_serial = dbus_message_get_serial (message);
2207    }
2208
2209  _dbus_verbose ("Message %p serial is %u\n",
2210                 message, dbus_message_get_serial (message));
2211
2212  _dbus_message_lock (message);
2213
2214  /* Now we need to run an iteration to hopefully just write the messages
2215   * out immediately, and otherwise get them queued up
2216   */
2217  _dbus_connection_do_iteration_unlocked (connection,
2218                                          DBUS_ITERATION_DO_WRITING,
2219                                          -1);
2220
2221  /* If stuff is still queued up, be sure we wake up the main loop */
2222  if (connection->n_outgoing > 0)
2223    _dbus_connection_wakeup_mainloop (connection);
2224}
2225
2226static void
2227_dbus_connection_send_preallocated_and_unlock (DBusConnection       *connection,
2228					       DBusPreallocatedSend *preallocated,
2229					       DBusMessage          *message,
2230					       dbus_uint32_t        *client_serial)
2231{
2232  DBusDispatchStatus status;
2233
2234  HAVE_LOCK_CHECK (connection);
2235
2236  _dbus_connection_send_preallocated_unlocked_no_update (connection,
2237                                                         preallocated,
2238                                                         message, client_serial);
2239
2240  _dbus_verbose ("%s middle\n", _DBUS_FUNCTION_NAME);
2241  status = _dbus_connection_get_dispatch_status_unlocked (connection);
2242
2243  /* this calls out to user code */
2244  _dbus_connection_update_dispatch_status_and_unlock (connection, status);
2245}
2246
2247/**
2248 * Sends a message using preallocated resources. This function cannot fail.
2249 * It works identically to dbus_connection_send() in other respects.
2250 * Preallocated resources comes from dbus_connection_preallocate_send().
2251 * This function "consumes" the preallocated resources, they need not
2252 * be freed separately.
2253 *
2254 * @param connection the connection
2255 * @param preallocated the preallocated resources
2256 * @param message the message to send
2257 * @param client_serial return location for client serial assigned to the message
2258 */
2259void
2260dbus_connection_send_preallocated (DBusConnection       *connection,
2261                                   DBusPreallocatedSend *preallocated,
2262                                   DBusMessage          *message,
2263                                   dbus_uint32_t        *client_serial)
2264{
2265  _dbus_return_if_fail (connection != NULL);
2266  _dbus_return_if_fail (preallocated != NULL);
2267  _dbus_return_if_fail (message != NULL);
2268  _dbus_return_if_fail (preallocated->connection == connection);
2269  _dbus_return_if_fail (dbus_message_get_type (message) != DBUS_MESSAGE_TYPE_METHOD_CALL ||
2270                        dbus_message_get_member (message) != NULL);
2271  _dbus_return_if_fail (dbus_message_get_type (message) != DBUS_MESSAGE_TYPE_SIGNAL ||
2272                        (dbus_message_get_interface (message) != NULL &&
2273                         dbus_message_get_member (message) != NULL));
2274
2275  CONNECTION_LOCK (connection);
2276  _dbus_connection_send_preallocated_and_unlock (connection,
2277						 preallocated,
2278						 message, client_serial);
2279}
2280
2281static dbus_bool_t
2282_dbus_connection_send_unlocked_no_update (DBusConnection *connection,
2283                                          DBusMessage    *message,
2284                                          dbus_uint32_t  *client_serial)
2285{
2286  DBusPreallocatedSend *preallocated;
2287
2288  _dbus_assert (connection != NULL);
2289  _dbus_assert (message != NULL);
2290
2291  preallocated = _dbus_connection_preallocate_send_unlocked (connection);
2292  if (preallocated == NULL)
2293    return FALSE;
2294
2295  _dbus_connection_send_preallocated_unlocked_no_update (connection,
2296                                                         preallocated,
2297                                                         message,
2298                                                         client_serial);
2299  return TRUE;
2300}
2301
2302dbus_bool_t
2303_dbus_connection_send_and_unlock (DBusConnection *connection,
2304				  DBusMessage    *message,
2305				  dbus_uint32_t  *client_serial)
2306{
2307  DBusPreallocatedSend *preallocated;
2308
2309  _dbus_assert (connection != NULL);
2310  _dbus_assert (message != NULL);
2311
2312  preallocated = _dbus_connection_preallocate_send_unlocked (connection);
2313  if (preallocated == NULL)
2314    {
2315      CONNECTION_UNLOCK (connection);
2316      return FALSE;
2317    }
2318
2319  _dbus_connection_send_preallocated_and_unlock (connection,
2320						 preallocated,
2321						 message,
2322						 client_serial);
2323  return TRUE;
2324}
2325
2326/**
2327 * Adds a message to the outgoing message queue. Does not block to
2328 * write the message to the network; that happens asynchronously. To
2329 * force the message to be written, call dbus_connection_flush().
2330 * Because this only queues the message, the only reason it can
2331 * fail is lack of memory. Even if the connection is disconnected,
2332 * no error will be returned.
2333 *
2334 * If the function fails due to lack of memory, it returns #FALSE.
2335 * The function will never fail for other reasons; even if the
2336 * connection is disconnected, you can queue an outgoing message,
2337 * though obviously it won't be sent.
2338 *
2339 * @param connection the connection.
2340 * @param message the message to write.
2341 * @param client_serial return location for client serial.
2342 * @returns #TRUE on success.
2343 */
2344dbus_bool_t
2345dbus_connection_send (DBusConnection *connection,
2346                      DBusMessage    *message,
2347                      dbus_uint32_t  *client_serial)
2348{
2349  _dbus_return_val_if_fail (connection != NULL, FALSE);
2350  _dbus_return_val_if_fail (message != NULL, FALSE);
2351
2352  CONNECTION_LOCK (connection);
2353
2354  return _dbus_connection_send_and_unlock (connection,
2355					   message,
2356					   client_serial);
2357}
2358
2359static dbus_bool_t
2360reply_handler_timeout (void *data)
2361{
2362  DBusConnection *connection;
2363  DBusDispatchStatus status;
2364  DBusPendingCall *pending = data;
2365
2366  connection = _dbus_pending_call_get_connection_and_lock (pending);
2367
2368  _dbus_pending_call_queue_timeout_error_unlocked (pending,
2369                                                   connection);
2370  _dbus_connection_remove_timeout_unlocked (connection,
2371				            _dbus_pending_call_get_timeout_unlocked (pending));
2372  _dbus_pending_call_set_timeout_added_unlocked (pending, FALSE);
2373
2374  _dbus_verbose ("%s middle\n", _DBUS_FUNCTION_NAME);
2375  status = _dbus_connection_get_dispatch_status_unlocked (connection);
2376
2377  /* Unlocks, and calls out to user code */
2378  _dbus_connection_update_dispatch_status_and_unlock (connection, status);
2379
2380  return TRUE;
2381}
2382
2383/**
2384 * Queues a message to send, as with dbus_connection_send_message(),
2385 * but also returns a #DBusPendingCall used to receive a reply to the
2386 * message. If no reply is received in the given timeout_milliseconds,
2387 * this function expires the pending reply and generates a synthetic
2388 * error reply (generated in-process, not by the remote application)
2389 * indicating that a timeout occurred.
2390 *
2391 * A #DBusPendingCall will see a reply message after any filters, but
2392 * before any object instances or other handlers. A #DBusPendingCall
2393 * will always see exactly one reply message, unless it's cancelled
2394 * with dbus_pending_call_cancel().
2395 *
2396 * If a filter filters out the reply before the handler sees it, the
2397 * reply is immediately timed out and a timeout error reply is
2398 * generated. If a filter removes the timeout error reply then the
2399 * #DBusPendingCall will get confused. Filtering the timeout error
2400 * is thus considered a bug and will print a warning.
2401 *
2402 * If #NULL is passed for the pending_return, the #DBusPendingCall
2403 * will still be generated internally, and used to track
2404 * the message reply timeout. This means a timeout error will
2405 * occur if no reply arrives, unlike with dbus_connection_send().
2406 *
2407 * If -1 is passed for the timeout, a sane default timeout is used. -1
2408 * is typically the best value for the timeout for this reason, unless
2409 * you want a very short or very long timeout.  There is no way to
2410 * avoid a timeout entirely, other than passing INT_MAX for the
2411 * timeout to postpone it indefinitely.
2412 *
2413 * @param connection the connection
2414 * @param message the message to send
2415 * @param pending_return return location for a #DBusPendingCall object, or #NULLif connection is disconnected
2416 * @param timeout_milliseconds timeout in milliseconds or -1 for default
2417 * @returns #FALSE if no memory, #TRUE otherwise.
2418 *
2419 */
2420dbus_bool_t
2421dbus_connection_send_with_reply (DBusConnection     *connection,
2422                                 DBusMessage        *message,
2423                                 DBusPendingCall   **pending_return,
2424                                 int                 timeout_milliseconds)
2425{
2426  DBusPendingCall *pending;
2427  dbus_int32_t serial = -1;
2428  DBusDispatchStatus status;
2429
2430  _dbus_return_val_if_fail (connection != NULL, FALSE);
2431  _dbus_return_val_if_fail (message != NULL, FALSE);
2432  _dbus_return_val_if_fail (timeout_milliseconds >= 0 || timeout_milliseconds == -1, FALSE);
2433
2434  if (pending_return)
2435    *pending_return = NULL;
2436
2437  CONNECTION_LOCK (connection);
2438
2439   if (!_dbus_connection_get_is_connected_unlocked (connection))
2440    {
2441      CONNECTION_UNLOCK (connection);
2442
2443      *pending_return = NULL;
2444
2445      return TRUE;
2446    }
2447
2448  pending = _dbus_pending_call_new_unlocked (connection,
2449                                             timeout_milliseconds,
2450                                             reply_handler_timeout);
2451
2452  if (pending == NULL)
2453    {
2454      CONNECTION_UNLOCK (connection);
2455      return FALSE;
2456    }
2457
2458  /* Assign a serial to the message */
2459  serial = dbus_message_get_serial (message);
2460  if (serial == 0)
2461    {
2462      serial = _dbus_connection_get_next_client_serial (connection);
2463      _dbus_message_set_serial (message, serial);
2464    }
2465
2466  if (!_dbus_pending_call_set_timeout_error_unlocked (pending, message, serial))
2467    goto error;
2468
2469  /* Insert the serial in the pending replies hash;
2470   * hash takes a refcount on DBusPendingCall.
2471   * Also, add the timeout.
2472   */
2473  if (!_dbus_connection_attach_pending_call_unlocked (connection,
2474						      pending))
2475    goto error;
2476
2477  if (!_dbus_connection_send_unlocked_no_update (connection, message, NULL))
2478    {
2479      _dbus_connection_detach_pending_call_and_unlock (connection,
2480						       pending);
2481      goto error_unlocked;
2482    }
2483
2484  if (pending_return)
2485    *pending_return = pending; /* hand off refcount */
2486  else
2487    {
2488      _dbus_connection_detach_pending_call_unlocked (connection, pending);
2489      /* we still have a ref to the pending call in this case, we unref
2490       * after unlocking, below
2491       */
2492    }
2493
2494  status = _dbus_connection_get_dispatch_status_unlocked (connection);
2495
2496  /* this calls out to user code */
2497  _dbus_connection_update_dispatch_status_and_unlock (connection, status);
2498
2499  if (pending_return == NULL)
2500    dbus_pending_call_unref (pending);
2501
2502  return TRUE;
2503
2504 error:
2505  CONNECTION_UNLOCK (connection);
2506 error_unlocked:
2507  dbus_pending_call_unref (pending);
2508  return FALSE;
2509}
2510
2511/* This is slightly strange since we can pop a message here without
2512 * the dispatch lock.
2513 */
2514static DBusMessage*
2515check_for_reply_unlocked (DBusConnection *connection,
2516                          dbus_uint32_t   client_serial)
2517{
2518  DBusList *link;
2519
2520  HAVE_LOCK_CHECK (connection);
2521
2522  link = _dbus_list_get_first_link (&connection->incoming_messages);
2523
2524  while (link != NULL)
2525    {
2526      DBusMessage *reply = link->data;
2527
2528      if (dbus_message_get_reply_serial (reply) == client_serial)
2529	{
2530	  _dbus_list_remove_link (&connection->incoming_messages, link);
2531	  connection->n_incoming  -= 1;
2532	  return reply;
2533	}
2534      link = _dbus_list_get_next_link (&connection->incoming_messages, link);
2535    }
2536
2537  return NULL;
2538}
2539
2540static void
2541connection_timeout_and_complete_all_pending_calls_unlocked (DBusConnection *connection)
2542{
2543   /* We can't iterate over the hash in the normal way since we'll be
2544    * dropping the lock for each item. So we restart the
2545    * iter each time as we drain the hash table.
2546    */
2547
2548   while (_dbus_hash_table_get_n_entries (connection->pending_replies) > 0)
2549    {
2550      DBusPendingCall *pending;
2551      DBusHashIter iter;
2552
2553      _dbus_hash_iter_init (connection->pending_replies, &iter);
2554      _dbus_hash_iter_next (&iter);
2555
2556      pending = (DBusPendingCall *) _dbus_hash_iter_get_value (&iter);
2557      _dbus_pending_call_ref_unlocked (pending);
2558
2559      _dbus_pending_call_queue_timeout_error_unlocked (pending,
2560                                                       connection);
2561      _dbus_connection_remove_timeout_unlocked (connection,
2562                                                _dbus_pending_call_get_timeout_unlocked (pending));
2563      _dbus_pending_call_set_timeout_added_unlocked (pending, FALSE);
2564      _dbus_hash_iter_remove_entry (&iter);
2565
2566      _dbus_pending_call_unref_and_unlock (pending);
2567      CONNECTION_LOCK (connection);
2568    }
2569  HAVE_LOCK_CHECK (connection);
2570}
2571
2572static void
2573complete_pending_call_and_unlock (DBusConnection  *connection,
2574                                  DBusPendingCall *pending,
2575                                  DBusMessage     *message)
2576{
2577  _dbus_pending_call_set_reply_unlocked (pending, message);
2578  _dbus_pending_call_ref_unlocked (pending); /* in case there's no app with a ref held */
2579  _dbus_connection_detach_pending_call_and_unlock (connection, pending);
2580
2581  /* Must be called unlocked since it invokes app callback */
2582  _dbus_pending_call_complete (pending);
2583  dbus_pending_call_unref (pending);
2584}
2585
2586static dbus_bool_t
2587check_for_reply_and_update_dispatch_unlocked (DBusConnection  *connection,
2588                                              DBusPendingCall *pending)
2589{
2590  DBusMessage *reply;
2591  DBusDispatchStatus status;
2592
2593  reply = check_for_reply_unlocked (connection,
2594                                    _dbus_pending_call_get_reply_serial_unlocked (pending));
2595  if (reply != NULL)
2596    {
2597      _dbus_verbose ("%s checked for reply\n", _DBUS_FUNCTION_NAME);
2598
2599      _dbus_verbose ("dbus_connection_send_with_reply_and_block(): got reply\n");
2600
2601      complete_pending_call_and_unlock (connection, pending, reply);
2602      dbus_message_unref (reply);
2603
2604      CONNECTION_LOCK (connection);
2605      status = _dbus_connection_get_dispatch_status_unlocked (connection);
2606      _dbus_connection_update_dispatch_status_and_unlock (connection, status);
2607      dbus_pending_call_unref (pending);
2608
2609      return TRUE;
2610    }
2611
2612  return FALSE;
2613}
2614
2615/**
2616 * When a function that blocks has been called with a timeout, and we
2617 * run out of memory, the time to wait for memory is based on the
2618 * timeout. If the caller was willing to block a long time we wait a
2619 * relatively long time for memory, if they were only willing to block
2620 * briefly then we retry for memory at a rapid rate.
2621 *
2622 * @timeout_milliseconds the timeout requested for blocking
2623 */
2624static void
2625_dbus_memory_pause_based_on_timeout (int timeout_milliseconds)
2626{
2627  if (timeout_milliseconds == -1)
2628    _dbus_sleep_milliseconds (1000);
2629  else if (timeout_milliseconds < 100)
2630    ; /* just busy loop */
2631  else if (timeout_milliseconds <= 1000)
2632    _dbus_sleep_milliseconds (timeout_milliseconds / 3);
2633  else
2634    _dbus_sleep_milliseconds (1000);
2635}
2636
2637static DBusMessage *
2638generate_local_error_message (dbus_uint32_t serial,
2639                              char *error_name,
2640                              char *error_msg)
2641{
2642  DBusMessage *message;
2643  message = dbus_message_new (DBUS_MESSAGE_TYPE_ERROR);
2644  if (!message)
2645    goto out;
2646
2647  if (!dbus_message_set_error_name (message, error_name))
2648    {
2649      dbus_message_unref (message);
2650      message = NULL;
2651      goto out;
2652    }
2653
2654  dbus_message_set_no_reply (message, TRUE);
2655
2656  if (!dbus_message_set_reply_serial (message,
2657                                      serial))
2658    {
2659      dbus_message_unref (message);
2660      message = NULL;
2661      goto out;
2662    }
2663
2664  if (error_msg != NULL)
2665    {
2666      DBusMessageIter iter;
2667
2668      dbus_message_iter_init_append (message, &iter);
2669      if (!dbus_message_iter_append_basic (&iter,
2670                                           DBUS_TYPE_STRING,
2671                                           &error_msg))
2672        {
2673          dbus_message_unref (message);
2674          message = NULL;
2675	  goto out;
2676        }
2677    }
2678
2679 out:
2680  return message;
2681}
2682
2683/**
2684 * Blocks until a pending call times out or gets a reply.
2685 *
2686 * Does not re-enter the main loop or run filter/path-registered
2687 * callbacks. The reply to the message will not be seen by
2688 * filter callbacks.
2689 *
2690 * Returns immediately if pending call already got a reply.
2691 *
2692 * @todo could use performance improvements (it keeps scanning
2693 * the whole message queue for example)
2694 *
2695 * @param pending the pending call we block for a reply on
2696 */
2697void
2698_dbus_connection_block_pending_call (DBusPendingCall *pending)
2699{
2700  long start_tv_sec, start_tv_usec;
2701  long end_tv_sec, end_tv_usec;
2702  long tv_sec, tv_usec;
2703  DBusDispatchStatus status;
2704  DBusConnection *connection;
2705  dbus_uint32_t client_serial;
2706  int timeout_milliseconds;
2707
2708  _dbus_assert (pending != NULL);
2709
2710  if (dbus_pending_call_get_completed (pending))
2711    return;
2712
2713  dbus_pending_call_ref (pending); /* necessary because the call could be canceled */
2714
2715  connection = _dbus_pending_call_get_connection_and_lock (pending);
2716
2717  /* Flush message queue - note, can affect dispatch status */
2718  _dbus_connection_flush_unlocked (connection);
2719
2720  client_serial = _dbus_pending_call_get_reply_serial_unlocked (pending);
2721
2722  /* note that timeout_milliseconds is limited to a smallish value
2723   * in _dbus_pending_call_new() so overflows aren't possible
2724   * below
2725   */
2726  timeout_milliseconds = dbus_timeout_get_interval (_dbus_pending_call_get_timeout_unlocked (pending));
2727
2728  _dbus_get_current_time (&start_tv_sec, &start_tv_usec);
2729  end_tv_sec = start_tv_sec + timeout_milliseconds / 1000;
2730  end_tv_usec = start_tv_usec + (timeout_milliseconds % 1000) * 1000;
2731  end_tv_sec += end_tv_usec / _DBUS_USEC_PER_SECOND;
2732  end_tv_usec = end_tv_usec % _DBUS_USEC_PER_SECOND;
2733
2734  _dbus_verbose ("dbus_connection_send_with_reply_and_block(): will block %d milliseconds for reply serial %u from %ld sec %ld usec to %ld sec %ld usec\n",
2735                 timeout_milliseconds,
2736                 client_serial,
2737                 start_tv_sec, start_tv_usec,
2738                 end_tv_sec, end_tv_usec);
2739
2740  /* check to see if we already got the data off the socket */
2741  /* from another blocked pending call */
2742  if (check_for_reply_and_update_dispatch_unlocked (connection, pending))
2743    return;
2744
2745  /* Now we wait... */
2746  /* always block at least once as we know we don't have the reply yet */
2747  _dbus_connection_do_iteration_unlocked (connection,
2748                                          DBUS_ITERATION_DO_READING |
2749                                          DBUS_ITERATION_BLOCK,
2750                                          timeout_milliseconds);
2751
2752 recheck_status:
2753
2754  _dbus_verbose ("%s top of recheck\n", _DBUS_FUNCTION_NAME);
2755
2756  HAVE_LOCK_CHECK (connection);
2757
2758  /* queue messages and get status */
2759
2760  status = _dbus_connection_get_dispatch_status_unlocked (connection);
2761
2762  /* the get_completed() is in case a dispatch() while we were blocking
2763   * got the reply instead of us.
2764   */
2765  if (_dbus_pending_call_get_completed_unlocked (pending))
2766    {
2767      _dbus_verbose ("Pending call completed by dispatch in %s\n", _DBUS_FUNCTION_NAME);
2768      _dbus_connection_update_dispatch_status_and_unlock (connection, status);
2769      dbus_pending_call_unref (pending);
2770      return;
2771    }
2772
2773  if (status == DBUS_DISPATCH_DATA_REMAINS) {
2774    if (check_for_reply_and_update_dispatch_unlocked (connection, pending))
2775      return;
2776  }
2777
2778  _dbus_get_current_time (&tv_sec, &tv_usec);
2779
2780  if (!_dbus_connection_get_is_connected_unlocked (connection))
2781    {
2782      DBusMessage *error_msg;
2783
2784      error_msg = generate_local_error_message (client_serial,
2785                                                DBUS_ERROR_DISCONNECTED,
2786                                                "Connection was dissconnected before a reply was recived");
2787
2788      /* on OOM error_msg is set to NULL */
2789      complete_pending_call_and_unlock (connection, pending, error_msg);
2790      dbus_pending_call_unref (pending);
2791      return;
2792    }
2793  else if (tv_sec < start_tv_sec)
2794    _dbus_verbose ("dbus_connection_send_with_reply_and_block(): clock set backward\n");
2795  else if (connection->disconnect_message_link == NULL)
2796    _dbus_verbose ("dbus_connection_send_with_reply_and_block(): disconnected\n");
2797  else if (tv_sec < end_tv_sec ||
2798           (tv_sec == end_tv_sec && tv_usec < end_tv_usec))
2799    {
2800      timeout_milliseconds = (end_tv_sec - tv_sec) * 1000 +
2801        (end_tv_usec - tv_usec) / 1000;
2802      _dbus_verbose ("dbus_connection_send_with_reply_and_block(): %d milliseconds remain\n", timeout_milliseconds);
2803      _dbus_assert (timeout_milliseconds >= 0);
2804
2805      if (status == DBUS_DISPATCH_NEED_MEMORY)
2806        {
2807          /* Try sleeping a bit, as we aren't sure we need to block for reading,
2808           * we may already have a reply in the buffer and just can't process
2809           * it.
2810           */
2811          _dbus_verbose ("dbus_connection_send_with_reply_and_block() waiting for more memory\n");
2812
2813          _dbus_memory_pause_based_on_timeout (timeout_milliseconds);
2814        }
2815      else
2816        {
2817          /* block again, we don't have the reply buffered yet. */
2818          _dbus_connection_do_iteration_unlocked (connection,
2819                                                  DBUS_ITERATION_DO_READING |
2820                                                  DBUS_ITERATION_BLOCK,
2821                                                  timeout_milliseconds);
2822        }
2823
2824      goto recheck_status;
2825    }
2826
2827  _dbus_verbose ("dbus_connection_send_with_reply_and_block(): Waited %ld milliseconds and got no reply\n",
2828                 (tv_sec - start_tv_sec) * 1000 + (tv_usec - start_tv_usec) / 1000);
2829
2830  _dbus_assert (!_dbus_pending_call_get_completed_unlocked (pending));
2831
2832  /* unlock and call user code */
2833  complete_pending_call_and_unlock (connection, pending, NULL);
2834
2835  /* update user code on dispatch status */
2836  CONNECTION_LOCK (connection);
2837  status = _dbus_connection_get_dispatch_status_unlocked (connection);
2838  _dbus_connection_update_dispatch_status_and_unlock (connection, status);
2839  dbus_pending_call_unref (pending);
2840}
2841
2842/**
2843 * Sends a message and blocks a certain time period while waiting for
2844 * a reply.  This function does not reenter the main loop,
2845 * i.e. messages other than the reply are queued up but not
2846 * processed. This function is used to do non-reentrant "method
2847 * calls."
2848 *
2849 * If a normal reply is received, it is returned, and removed from the
2850 * incoming message queue. If it is not received, #NULL is returned
2851 * and the error is set to #DBUS_ERROR_NO_REPLY.  If an error reply is
2852 * received, it is converted to a #DBusError and returned as an error,
2853 * then the reply message is deleted. If something else goes wrong,
2854 * result is set to whatever is appropriate, such as
2855 * #DBUS_ERROR_NO_MEMORY or #DBUS_ERROR_DISCONNECTED.
2856 *
2857 * @param connection the connection
2858 * @param message the message to send
2859 * @param timeout_milliseconds timeout in milliseconds or -1 for default
2860 * @param error return location for error message
2861 * @returns the message that is the reply or #NULL with an error code if the
2862 * function fails.
2863 */
2864DBusMessage*
2865dbus_connection_send_with_reply_and_block (DBusConnection     *connection,
2866                                           DBusMessage        *message,
2867                                           int                 timeout_milliseconds,
2868                                           DBusError          *error)
2869{
2870  DBusMessage *reply;
2871  DBusPendingCall *pending;
2872
2873  _dbus_return_val_if_fail (connection != NULL, NULL);
2874  _dbus_return_val_if_fail (message != NULL, NULL);
2875  _dbus_return_val_if_fail (timeout_milliseconds >= 0 || timeout_milliseconds == -1, NULL);
2876  _dbus_return_val_if_error_is_set (error, NULL);
2877
2878  if (!dbus_connection_send_with_reply (connection, message,
2879                                        &pending, timeout_milliseconds))
2880    {
2881      _DBUS_SET_OOM (error);
2882      return NULL;
2883    }
2884
2885  _dbus_assert (pending != NULL);
2886
2887  dbus_pending_call_block (pending);
2888
2889  reply = dbus_pending_call_steal_reply (pending);
2890  dbus_pending_call_unref (pending);
2891
2892  /* call_complete_and_unlock() called from pending_call_block() should
2893   * always fill this in.
2894   */
2895  _dbus_assert (reply != NULL);
2896
2897   if (dbus_set_error_from_message (error, reply))
2898    {
2899      dbus_message_unref (reply);
2900      return NULL;
2901    }
2902  else
2903    return reply;
2904}
2905
2906/**
2907 * Blocks until the outgoing message queue is empty.
2908 * Assumes connection lock already held.
2909 *
2910 * If you call this, you MUST call update_dispatch_status afterword...
2911 *
2912 * @param connection the connection.
2913 */
2914DBusDispatchStatus
2915_dbus_connection_flush_unlocked (DBusConnection *connection)
2916{
2917  /* We have to specify DBUS_ITERATION_DO_READING here because
2918   * otherwise we could have two apps deadlock if they are both doing
2919   * a flush(), and the kernel buffers fill up. This could change the
2920   * dispatch status.
2921   */
2922  DBusDispatchStatus status;
2923
2924  HAVE_LOCK_CHECK (connection);
2925
2926  while (connection->n_outgoing > 0 &&
2927         _dbus_connection_get_is_connected_unlocked (connection))
2928    {
2929      _dbus_verbose ("doing iteration in %s\n", _DBUS_FUNCTION_NAME);
2930      HAVE_LOCK_CHECK (connection);
2931      _dbus_connection_do_iteration_unlocked (connection,
2932                                              DBUS_ITERATION_DO_READING |
2933                                              DBUS_ITERATION_DO_WRITING |
2934                                              DBUS_ITERATION_BLOCK,
2935                                              -1);
2936    }
2937
2938  HAVE_LOCK_CHECK (connection);
2939  _dbus_verbose ("%s middle\n", _DBUS_FUNCTION_NAME);
2940  status = _dbus_connection_get_dispatch_status_unlocked (connection);
2941
2942  HAVE_LOCK_CHECK (connection);
2943  return status;
2944}
2945
2946/**
2947 * Blocks until the outgoing message queue is empty.
2948 *
2949 * @param connection the connection.
2950 */
2951void
2952dbus_connection_flush (DBusConnection *connection)
2953{
2954  /* We have to specify DBUS_ITERATION_DO_READING here because
2955   * otherwise we could have two apps deadlock if they are both doing
2956   * a flush(), and the kernel buffers fill up. This could change the
2957   * dispatch status.
2958   */
2959  DBusDispatchStatus status;
2960
2961  _dbus_return_if_fail (connection != NULL);
2962
2963  CONNECTION_LOCK (connection);
2964
2965  status = _dbus_connection_flush_unlocked (connection);
2966
2967  HAVE_LOCK_CHECK (connection);
2968  /* Unlocks and calls out to user code */
2969  _dbus_connection_update_dispatch_status_and_unlock (connection, status);
2970
2971  _dbus_verbose ("%s end\n", _DBUS_FUNCTION_NAME);
2972}
2973
2974/**
2975 * This function is intended for use with applications that don't want
2976 * to write a main loop and deal with #DBusWatch and #DBusTimeout. An
2977 * example usage would be:
2978 *
2979 * @code
2980 *   while (dbus_connection_read_write_dispatch (connection, -1))
2981 *     ; // empty loop body
2982 * @endcode
2983 *
2984 * In this usage you would normally have set up a filter function to look
2985 * at each message as it is dispatched. The loop terminates when the last
2986 * message from the connection (the disconnected signal) is processed.
2987 *
2988 * If there are messages to dispatch and the dispatch flag is set, this
2989 * function will dbus_connection_dispatch() once, and return. If there are no
2990 * messages to dispatch, this function will block until it can read or write,
2991 * then read or write, then return.
2992 *
2993 * The way to think of this function is that it either makes some sort
2994 * of progress, or it blocks.
2995 *
2996 * The return value indicates whether the disconnect message has been
2997 * processed, NOT whether the connection is connected. This is
2998 * important because even after disconnecting, you want to process any
2999 * messages you received prior to the disconnect.
3000 *
3001 * @param connection the connection
3002 * @param timeout_milliseconds max time to block or -1 for infinite
3003 * @param dispatch dispatch new messages or leave them on the incoming queue
3004 * @returns #TRUE if the disconnect message has not been processed
3005 */
3006static dbus_bool_t
3007_dbus_connection_read_write_dispatch (DBusConnection *connection,
3008                                     int             timeout_milliseconds,
3009                                     dbus_bool_t     dispatch)
3010{
3011  DBusDispatchStatus dstatus;
3012  dbus_bool_t dispatched_disconnected;
3013
3014  dstatus = dbus_connection_get_dispatch_status (connection);
3015
3016  if (dispatch && dstatus == DBUS_DISPATCH_DATA_REMAINS)
3017    {
3018      _dbus_verbose ("doing dispatch in %s\n", _DBUS_FUNCTION_NAME);
3019      dbus_connection_dispatch (connection);
3020      CONNECTION_LOCK (connection);
3021    }
3022  else if (dstatus == DBUS_DISPATCH_NEED_MEMORY)
3023    {
3024      _dbus_verbose ("pausing for memory in %s\n", _DBUS_FUNCTION_NAME);
3025      _dbus_memory_pause_based_on_timeout (timeout_milliseconds);
3026      CONNECTION_LOCK (connection);
3027    }
3028  else
3029    {
3030      CONNECTION_LOCK (connection);
3031      if (_dbus_connection_get_is_connected_unlocked (connection))
3032        {
3033          _dbus_verbose ("doing iteration in %s\n", _DBUS_FUNCTION_NAME);
3034          _dbus_connection_do_iteration_unlocked (connection,
3035                                                  DBUS_ITERATION_DO_READING |
3036                                                  DBUS_ITERATION_DO_WRITING |
3037                                                  DBUS_ITERATION_BLOCK,
3038                                                  timeout_milliseconds);
3039        }
3040    }
3041
3042  HAVE_LOCK_CHECK (connection);
3043  dispatched_disconnected = connection->n_incoming == 0 &&
3044    connection->disconnect_message_link == NULL;
3045  CONNECTION_UNLOCK (connection);
3046  return !dispatched_disconnected; /* TRUE if we have not processed disconnected */
3047}
3048
3049
3050/**
3051 * This function is intended for use with applications that don't want
3052 * to write a main loop and deal with #DBusWatch and #DBusTimeout. An
3053 * example usage would be:
3054 *
3055 * @code
3056 *   while (dbus_connection_read_write_dispatch (connection, -1))
3057 *     ; // empty loop body
3058 * @endcode
3059 *
3060 * In this usage you would normally have set up a filter function to look
3061 * at each message as it is dispatched. The loop terminates when the last
3062 * message from the connection (the disconnected signal) is processed.
3063 *
3064 * If there are messages to dispatch, this function will
3065 * dbus_connection_dispatch() once, and return. If there are no
3066 * messages to dispatch, this function will block until it can read or
3067 * write, then read or write, then return.
3068 *
3069 * The way to think of this function is that it either makes some sort
3070 * of progress, or it blocks.
3071 *
3072 * The return value indicates whether the disconnect message has been
3073 * processed, NOT whether the connection is connected. This is
3074 * important because even after disconnecting, you want to process any
3075 * messages you received prior to the disconnect.
3076 *
3077 * @param connection the connection
3078 * @param timeout_milliseconds max time to block or -1 for infinite
3079 * @returns #TRUE if the disconnect message has not been processed
3080 */
3081dbus_bool_t
3082dbus_connection_read_write_dispatch (DBusConnection *connection,
3083                                     int             timeout_milliseconds)
3084{
3085  _dbus_return_val_if_fail (connection != NULL, FALSE);
3086  _dbus_return_val_if_fail (timeout_milliseconds >= 0 || timeout_milliseconds == -1, FALSE);
3087   return _dbus_connection_read_write_dispatch(connection, timeout_milliseconds, TRUE);
3088}
3089
3090/**
3091 * This function is intended for use with applications that don't want to
3092 * write a main loop and deal with #DBusWatch and #DBusTimeout.
3093 *
3094 * If there are no messages to dispatch, this function will block until it can
3095 * read or write, then read or write, then return.
3096 *
3097 * The return value indicates whether the disconnect message has been
3098 * processed, NOT whether the connection is connected. This is important
3099 * because even after disconnecting, you want to process any messages you
3100 * received prior to the disconnect.
3101 *
3102 * @param connection the connection
3103 * @param timeout_milliseconds max time to block or -1 for infinite
3104 * @returns #TRUE if the disconnect message has not been processed
3105 */
3106dbus_bool_t
3107dbus_connection_read_write (DBusConnection *connection,
3108                            int             timeout_milliseconds)
3109{
3110  _dbus_return_val_if_fail (connection != NULL, FALSE);
3111  _dbus_return_val_if_fail (timeout_milliseconds >= 0 || timeout_milliseconds == -1, FALSE);
3112   return _dbus_connection_read_write_dispatch(connection, timeout_milliseconds, FALSE);
3113}
3114
3115/**
3116 * Returns the first-received message from the incoming message queue,
3117 * leaving it in the queue. If the queue is empty, returns #NULL.
3118 *
3119 * The caller does not own a reference to the returned message, and
3120 * must either return it using dbus_connection_return_message() or
3121 * keep it after calling dbus_connection_steal_borrowed_message(). No
3122 * one can get at the message while its borrowed, so return it as
3123 * quickly as possible and don't keep a reference to it after
3124 * returning it. If you need to keep the message, make a copy of it.
3125 *
3126 * dbus_connection_dispatch() will block if called while a borrowed
3127 * message is outstanding; only one piece of code can be playing with
3128 * the incoming queue at a time. This function will block if called
3129 * during a dbus_connection_dispatch().
3130 *
3131 * @param connection the connection.
3132 * @returns next message in the incoming queue.
3133 */
3134DBusMessage*
3135dbus_connection_borrow_message (DBusConnection *connection)
3136{
3137  DBusDispatchStatus status;
3138  DBusMessage *message;
3139
3140  _dbus_return_val_if_fail (connection != NULL, NULL);
3141
3142  _dbus_verbose ("%s start\n", _DBUS_FUNCTION_NAME);
3143
3144  /* this is called for the side effect that it queues
3145   * up any messages from the transport
3146   */
3147  status = dbus_connection_get_dispatch_status (connection);
3148  if (status != DBUS_DISPATCH_DATA_REMAINS)
3149    return NULL;
3150
3151  CONNECTION_LOCK (connection);
3152
3153  _dbus_connection_acquire_dispatch (connection);
3154
3155  /* While a message is outstanding, the dispatch lock is held */
3156  _dbus_assert (connection->message_borrowed == NULL);
3157
3158  connection->message_borrowed = _dbus_list_get_first (&connection->incoming_messages);
3159
3160  message = connection->message_borrowed;
3161
3162  /* Note that we KEEP the dispatch lock until the message is returned */
3163  if (message == NULL)
3164    _dbus_connection_release_dispatch (connection);
3165
3166  CONNECTION_UNLOCK (connection);
3167
3168  return message;
3169}
3170
3171/**
3172 * Used to return a message after peeking at it using
3173 * dbus_connection_borrow_message(). Only called if
3174 * message from dbus_connection_borrow_message() was non-#NULL.
3175 *
3176 * @param connection the connection
3177 * @param message the message from dbus_connection_borrow_message()
3178 */
3179void
3180dbus_connection_return_message (DBusConnection *connection,
3181				DBusMessage    *message)
3182{
3183  _dbus_return_if_fail (connection != NULL);
3184  _dbus_return_if_fail (message != NULL);
3185  _dbus_return_if_fail (message == connection->message_borrowed);
3186  _dbus_return_if_fail (connection->dispatch_acquired);
3187
3188  CONNECTION_LOCK (connection);
3189
3190  _dbus_assert (message == connection->message_borrowed);
3191
3192  connection->message_borrowed = NULL;
3193
3194  _dbus_connection_release_dispatch (connection);
3195
3196  CONNECTION_UNLOCK (connection);
3197}
3198
3199/**
3200 * Used to keep a message after peeking at it using
3201 * dbus_connection_borrow_message(). Before using this function, see
3202 * the caveats/warnings in the documentation for
3203 * dbus_connection_pop_message().
3204 *
3205 * @param connection the connection
3206 * @param message the message from dbus_connection_borrow_message()
3207 */
3208void
3209dbus_connection_steal_borrowed_message (DBusConnection *connection,
3210					DBusMessage    *message)
3211{
3212  DBusMessage *pop_message;
3213
3214  _dbus_return_if_fail (connection != NULL);
3215  _dbus_return_if_fail (message != NULL);
3216  _dbus_return_if_fail (message == connection->message_borrowed);
3217  _dbus_return_if_fail (connection->dispatch_acquired);
3218
3219  CONNECTION_LOCK (connection);
3220
3221  _dbus_assert (message == connection->message_borrowed);
3222
3223  pop_message = _dbus_list_pop_first (&connection->incoming_messages);
3224  _dbus_assert (message == pop_message);
3225
3226  connection->n_incoming -= 1;
3227
3228  _dbus_verbose ("Incoming message %p stolen from queue, %d incoming\n",
3229		 message, connection->n_incoming);
3230
3231  connection->message_borrowed = NULL;
3232
3233  _dbus_connection_release_dispatch (connection);
3234
3235  CONNECTION_UNLOCK (connection);
3236}
3237
3238/* See dbus_connection_pop_message, but requires the caller to own
3239 * the lock before calling. May drop the lock while running.
3240 */
3241static DBusList*
3242_dbus_connection_pop_message_link_unlocked (DBusConnection *connection)
3243{
3244  HAVE_LOCK_CHECK (connection);
3245
3246  _dbus_assert (connection->message_borrowed == NULL);
3247
3248  if (connection->n_incoming > 0)
3249    {
3250      DBusList *link;
3251
3252      link = _dbus_list_pop_first_link (&connection->incoming_messages);
3253      connection->n_incoming -= 1;
3254
3255      _dbus_verbose ("Message %p (%d %s %s %s '%s') removed from incoming queue %p, %d incoming\n",
3256                     link->data,
3257                     dbus_message_get_type (link->data),
3258                     dbus_message_get_path (link->data) ?
3259                     dbus_message_get_path (link->data) :
3260                     "no path",
3261                     dbus_message_get_interface (link->data) ?
3262                     dbus_message_get_interface (link->data) :
3263                     "no interface",
3264                     dbus_message_get_member (link->data) ?
3265                     dbus_message_get_member (link->data) :
3266                     "no member",
3267                     dbus_message_get_signature (link->data),
3268                     connection, connection->n_incoming);
3269
3270      return link;
3271    }
3272  else
3273    return NULL;
3274}
3275
3276/* See dbus_connection_pop_message, but requires the caller to own
3277 * the lock before calling. May drop the lock while running.
3278 */
3279static DBusMessage*
3280_dbus_connection_pop_message_unlocked (DBusConnection *connection)
3281{
3282  DBusList *link;
3283
3284  HAVE_LOCK_CHECK (connection);
3285
3286  link = _dbus_connection_pop_message_link_unlocked (connection);
3287
3288  if (link != NULL)
3289    {
3290      DBusMessage *message;
3291
3292      message = link->data;
3293
3294      _dbus_list_free_link (link);
3295
3296      return message;
3297    }
3298  else
3299    return NULL;
3300}
3301
3302static void
3303_dbus_connection_putback_message_link_unlocked (DBusConnection *connection,
3304                                                DBusList       *message_link)
3305{
3306  HAVE_LOCK_CHECK (connection);
3307
3308  _dbus_assert (message_link != NULL);
3309  /* You can't borrow a message while a link is outstanding */
3310  _dbus_assert (connection->message_borrowed == NULL);
3311  /* We had to have the dispatch lock across the pop/putback */
3312  _dbus_assert (connection->dispatch_acquired);
3313
3314  _dbus_list_prepend_link (&connection->incoming_messages,
3315                           message_link);
3316  connection->n_incoming += 1;
3317
3318  _dbus_verbose ("Message %p (%d %s %s '%s') put back into queue %p, %d incoming\n",
3319                 message_link->data,
3320                 dbus_message_get_type (message_link->data),
3321                 dbus_message_get_interface (message_link->data) ?
3322                 dbus_message_get_interface (message_link->data) :
3323                 "no interface",
3324                 dbus_message_get_member (message_link->data) ?
3325                 dbus_message_get_member (message_link->data) :
3326                 "no member",
3327                 dbus_message_get_signature (message_link->data),
3328                 connection, connection->n_incoming);
3329}
3330
3331/**
3332 * Returns the first-received message from the incoming message queue,
3333 * removing it from the queue. The caller owns a reference to the
3334 * returned message. If the queue is empty, returns #NULL.
3335 *
3336 * This function bypasses any message handlers that are registered,
3337 * and so using it is usually wrong. Instead, let the main loop invoke
3338 * dbus_connection_dispatch(). Popping messages manually is only
3339 * useful in very simple programs that don't share a #DBusConnection
3340 * with any libraries or other modules.
3341 *
3342 * There is a lock that covers all ways of accessing the incoming message
3343 * queue, so dbus_connection_dispatch(), dbus_connection_pop_message(),
3344 * dbus_connection_borrow_message(), etc. will all block while one of the others
3345 * in the group is running.
3346 *
3347 * @param connection the connection.
3348 * @returns next message in the incoming queue.
3349 */
3350DBusMessage*
3351dbus_connection_pop_message (DBusConnection *connection)
3352{
3353  DBusMessage *message;
3354  DBusDispatchStatus status;
3355
3356  _dbus_verbose ("%s start\n", _DBUS_FUNCTION_NAME);
3357
3358  /* this is called for the side effect that it queues
3359   * up any messages from the transport
3360   */
3361  status = dbus_connection_get_dispatch_status (connection);
3362  if (status != DBUS_DISPATCH_DATA_REMAINS)
3363    return NULL;
3364
3365  CONNECTION_LOCK (connection);
3366  _dbus_connection_acquire_dispatch (connection);
3367  HAVE_LOCK_CHECK (connection);
3368
3369  message = _dbus_connection_pop_message_unlocked (connection);
3370
3371  _dbus_verbose ("Returning popped message %p\n", message);
3372
3373  _dbus_connection_release_dispatch (connection);
3374  CONNECTION_UNLOCK (connection);
3375
3376  return message;
3377}
3378
3379/**
3380 * Acquire the dispatcher. This is a separate lock so the main
3381 * connection lock can be dropped to call out to application dispatch
3382 * handlers.
3383 *
3384 * @param connection the connection.
3385 */
3386static void
3387_dbus_connection_acquire_dispatch (DBusConnection *connection)
3388{
3389  HAVE_LOCK_CHECK (connection);
3390
3391  _dbus_connection_ref_unlocked (connection);
3392  CONNECTION_UNLOCK (connection);
3393
3394  _dbus_verbose ("%s locking dispatch_mutex\n", _DBUS_FUNCTION_NAME);
3395  _dbus_mutex_lock (connection->dispatch_mutex);
3396
3397  while (connection->dispatch_acquired)
3398    {
3399      _dbus_verbose ("%s waiting for dispatch to be acquirable\n", _DBUS_FUNCTION_NAME);
3400      _dbus_condvar_wait (connection->dispatch_cond,
3401                          connection->dispatch_mutex);
3402    }
3403
3404  _dbus_assert (!connection->dispatch_acquired);
3405
3406  connection->dispatch_acquired = TRUE;
3407
3408  _dbus_verbose ("%s unlocking dispatch_mutex\n", _DBUS_FUNCTION_NAME);
3409  _dbus_mutex_unlock (connection->dispatch_mutex);
3410
3411  CONNECTION_LOCK (connection);
3412  _dbus_connection_unref_unlocked (connection);
3413}
3414
3415/**
3416 * Release the dispatcher when you're done with it. Only call
3417 * after you've acquired the dispatcher. Wakes up at most one
3418 * thread currently waiting to acquire the dispatcher.
3419 *
3420 * @param connection the connection.
3421 */
3422static void
3423_dbus_connection_release_dispatch (DBusConnection *connection)
3424{
3425  HAVE_LOCK_CHECK (connection);
3426
3427  _dbus_verbose ("%s locking dispatch_mutex\n", _DBUS_FUNCTION_NAME);
3428  _dbus_mutex_lock (connection->dispatch_mutex);
3429
3430  _dbus_assert (connection->dispatch_acquired);
3431
3432  connection->dispatch_acquired = FALSE;
3433  _dbus_condvar_wake_one (connection->dispatch_cond);
3434
3435  _dbus_verbose ("%s unlocking dispatch_mutex\n", _DBUS_FUNCTION_NAME);
3436  _dbus_mutex_unlock (connection->dispatch_mutex);
3437}
3438
3439static void
3440_dbus_connection_failed_pop (DBusConnection *connection,
3441			     DBusList       *message_link)
3442{
3443  _dbus_list_prepend_link (&connection->incoming_messages,
3444			   message_link);
3445  connection->n_incoming += 1;
3446}
3447
3448static DBusDispatchStatus
3449_dbus_connection_get_dispatch_status_unlocked (DBusConnection *connection)
3450{
3451  HAVE_LOCK_CHECK (connection);
3452
3453  if (connection->n_incoming > 0)
3454    return DBUS_DISPATCH_DATA_REMAINS;
3455  else if (!_dbus_transport_queue_messages (connection->transport))
3456    return DBUS_DISPATCH_NEED_MEMORY;
3457  else
3458    {
3459      DBusDispatchStatus status;
3460      dbus_bool_t is_connected;
3461
3462      status = _dbus_transport_get_dispatch_status (connection->transport);
3463      is_connected = _dbus_transport_get_is_connected (connection->transport);
3464
3465      _dbus_verbose ("dispatch status = %s is_connected = %d\n",
3466                     DISPATCH_STATUS_NAME (status), is_connected);
3467
3468      if (!is_connected)
3469        {
3470          if (status == DBUS_DISPATCH_COMPLETE &&
3471              connection->disconnect_message_link)
3472            {
3473              _dbus_verbose ("Sending disconnect message from %s\n",
3474                             _DBUS_FUNCTION_NAME);
3475
3476              connection_forget_shared_unlocked (connection);
3477
3478              /* If we have pending calls queued timeouts on disconnect */
3479              connection_timeout_and_complete_all_pending_calls_unlocked (connection);
3480
3481              /* We haven't sent the disconnect message already,
3482               * and all real messages have been queued up.
3483               */
3484              _dbus_connection_queue_synthesized_message_link (connection,
3485                                                               connection->disconnect_message_link);
3486              connection->disconnect_message_link = NULL;
3487
3488              status = DBUS_DISPATCH_DATA_REMAINS;
3489            }
3490
3491          /* Dump the outgoing queue, we aren't going to be able to
3492           * send it now, and we'd like accessors like
3493           * dbus_connection_get_outgoing_size() to be accurate.
3494           */
3495          if (connection->n_outgoing > 0)
3496            {
3497              DBusList *link;
3498
3499              _dbus_verbose ("Dropping %d outgoing messages since we're disconnected\n",
3500                             connection->n_outgoing);
3501
3502              while ((link = _dbus_list_get_last_link (&connection->outgoing_messages)))
3503                {
3504                  _dbus_connection_message_sent (connection, link->data);
3505                }
3506            }
3507        }
3508
3509      if (status != DBUS_DISPATCH_COMPLETE)
3510        return status;
3511      else if (connection->n_incoming > 0)
3512        return DBUS_DISPATCH_DATA_REMAINS;
3513      else
3514        return DBUS_DISPATCH_COMPLETE;
3515    }
3516}
3517
3518static void
3519_dbus_connection_update_dispatch_status_and_unlock (DBusConnection    *connection,
3520                                                    DBusDispatchStatus new_status)
3521{
3522  dbus_bool_t changed;
3523  DBusDispatchStatusFunction function;
3524  void *data;
3525
3526  HAVE_LOCK_CHECK (connection);
3527
3528  _dbus_connection_ref_unlocked (connection);
3529
3530  changed = new_status != connection->last_dispatch_status;
3531
3532  connection->last_dispatch_status = new_status;
3533
3534  function = connection->dispatch_status_function;
3535  data = connection->dispatch_status_data;
3536
3537  /* We drop the lock */
3538  CONNECTION_UNLOCK (connection);
3539
3540  if (changed && function)
3541    {
3542      _dbus_verbose ("Notifying of change to dispatch status of %p now %d (%s)\n",
3543                     connection, new_status,
3544                     DISPATCH_STATUS_NAME (new_status));
3545      (* function) (connection, new_status, data);
3546    }
3547
3548  dbus_connection_unref (connection);
3549}
3550
3551/**
3552 * Gets the current state (what we would currently return
3553 * from dbus_connection_dispatch()) but doesn't actually
3554 * dispatch any messages.
3555 *
3556 * @param connection the connection.
3557 * @returns current dispatch status
3558 */
3559DBusDispatchStatus
3560dbus_connection_get_dispatch_status (DBusConnection *connection)
3561{
3562  DBusDispatchStatus status;
3563
3564  _dbus_return_val_if_fail (connection != NULL, DBUS_DISPATCH_COMPLETE);
3565
3566  _dbus_verbose ("%s start\n", _DBUS_FUNCTION_NAME);
3567
3568  CONNECTION_LOCK (connection);
3569
3570  status = _dbus_connection_get_dispatch_status_unlocked (connection);
3571
3572  CONNECTION_UNLOCK (connection);
3573
3574  return status;
3575}
3576
3577/**
3578* Filter funtion for handling the Peer standard interface
3579**/
3580static DBusHandlerResult
3581_dbus_connection_peer_filter_unlocked_no_update (DBusConnection *connection,
3582                                                 DBusMessage    *message)
3583{
3584  if (dbus_message_is_method_call (message,
3585                                   DBUS_INTERFACE_PEER,
3586                                   "Ping"))
3587    {
3588      DBusMessage *ret;
3589      dbus_bool_t sent;
3590
3591      ret = dbus_message_new_method_return (message);
3592      if (ret == NULL)
3593        return DBUS_HANDLER_RESULT_NEED_MEMORY;
3594
3595      sent = _dbus_connection_send_unlocked_no_update (connection, ret, NULL);
3596
3597      dbus_message_unref (ret);
3598
3599      if (!sent)
3600        return DBUS_HANDLER_RESULT_NEED_MEMORY;
3601
3602      return DBUS_HANDLER_RESULT_HANDLED;
3603    }
3604
3605
3606  return DBUS_HANDLER_RESULT_NOT_YET_HANDLED;
3607}
3608
3609/**
3610* Processes all builtin filter functions
3611*
3612* If the spec specifies a standard interface
3613* they should be processed from this method
3614**/
3615static DBusHandlerResult
3616_dbus_connection_run_builtin_filters_unlocked_no_update (DBusConnection *connection,
3617                                                           DBusMessage    *message)
3618{
3619  /* We just run one filter for now but have the option to run more
3620     if the spec calls for it in the future */
3621
3622  return _dbus_connection_peer_filter_unlocked_no_update (connection, message);
3623}
3624
3625/**
3626 * Processes data buffered while handling watches, queueing zero or
3627 * more incoming messages. Then pops the first-received message from
3628 * the current incoming message queue, runs any handlers for it, and
3629 * unrefs the message. Returns a status indicating whether messages/data
3630 * remain, more memory is needed, or all data has been processed.
3631 *
3632 * Even if the dispatch status is #DBUS_DISPATCH_DATA_REMAINS,
3633 * does not necessarily dispatch a message, as the data may
3634 * be part of authentication or the like.
3635 *
3636 * @todo some FIXME in here about handling DBUS_HANDLER_RESULT_NEED_MEMORY
3637 *
3638 * @todo FIXME what if we call out to application code to handle a
3639 * message, holding the dispatch lock, and the application code runs
3640 * the main loop and dispatches again? Probably deadlocks at the
3641 * moment. Maybe we want a dispatch status of DBUS_DISPATCH_IN_PROGRESS,
3642 * and then the GSource etc. could handle the situation? Right now
3643 * our GSource is NO_RECURSE
3644 *
3645 * @param connection the connection
3646 * @returns dispatch status
3647 */
3648DBusDispatchStatus
3649dbus_connection_dispatch (DBusConnection *connection)
3650{
3651  DBusMessage *message;
3652  DBusList *link, *filter_list_copy, *message_link;
3653  DBusHandlerResult result;
3654  DBusPendingCall *pending;
3655  dbus_int32_t reply_serial;
3656  DBusDispatchStatus status;
3657
3658  _dbus_return_val_if_fail (connection != NULL, DBUS_DISPATCH_COMPLETE);
3659
3660  _dbus_verbose ("%s\n", _DBUS_FUNCTION_NAME);
3661
3662  CONNECTION_LOCK (connection);
3663  status = _dbus_connection_get_dispatch_status_unlocked (connection);
3664  if (status != DBUS_DISPATCH_DATA_REMAINS)
3665    {
3666      /* unlocks and calls out to user code */
3667      _dbus_connection_update_dispatch_status_and_unlock (connection, status);
3668      return status;
3669    }
3670
3671  /* We need to ref the connection since the callback could potentially
3672   * drop the last ref to it
3673   */
3674  _dbus_connection_ref_unlocked (connection);
3675
3676  _dbus_connection_acquire_dispatch (connection);
3677  HAVE_LOCK_CHECK (connection);
3678
3679  message_link = _dbus_connection_pop_message_link_unlocked (connection);
3680  if (message_link == NULL)
3681    {
3682      /* another thread dispatched our stuff */
3683
3684      _dbus_verbose ("another thread dispatched message (during acquire_dispatch above)\n");
3685
3686      _dbus_connection_release_dispatch (connection);
3687
3688      status = _dbus_connection_get_dispatch_status_unlocked (connection);
3689
3690      _dbus_connection_update_dispatch_status_and_unlock (connection, status);
3691
3692      dbus_connection_unref (connection);
3693
3694      return status;
3695    }
3696
3697  message = message_link->data;
3698
3699  _dbus_verbose (" dispatching message %p (%d %s %s '%s')\n",
3700                 message,
3701                 dbus_message_get_type (message),
3702                 dbus_message_get_interface (message) ?
3703                 dbus_message_get_interface (message) :
3704                 "no interface",
3705                 dbus_message_get_member (message) ?
3706                 dbus_message_get_member (message) :
3707                 "no member",
3708                 dbus_message_get_signature (message));
3709
3710  result = DBUS_HANDLER_RESULT_NOT_YET_HANDLED;
3711
3712  /* Pending call handling must be first, because if you do
3713   * dbus_connection_send_with_reply_and_block() or
3714   * dbus_pending_call_block() then no handlers/filters will be run on
3715   * the reply. We want consistent semantics in the case where we
3716   * dbus_connection_dispatch() the reply.
3717   */
3718
3719  reply_serial = dbus_message_get_reply_serial (message);
3720  pending = _dbus_hash_table_lookup_int (connection->pending_replies,
3721                                         reply_serial);
3722  if (pending)
3723    {
3724      _dbus_verbose ("Dispatching a pending reply\n");
3725      complete_pending_call_and_unlock (connection, pending, message);
3726      pending = NULL; /* it's probably unref'd */
3727
3728      CONNECTION_LOCK (connection);
3729      _dbus_verbose ("pending call completed in dispatch\n");
3730      result = DBUS_HANDLER_RESULT_HANDLED;
3731      goto out;
3732    }
3733
3734  result = _dbus_connection_run_builtin_filters_unlocked_no_update (connection, message);
3735  if (result != DBUS_HANDLER_RESULT_NOT_YET_HANDLED)
3736    goto out;
3737
3738  if (!_dbus_list_copy (&connection->filter_list, &filter_list_copy))
3739    {
3740      _dbus_connection_release_dispatch (connection);
3741      HAVE_LOCK_CHECK (connection);
3742
3743      _dbus_connection_failed_pop (connection, message_link);
3744
3745      /* unlocks and calls user code */
3746      _dbus_connection_update_dispatch_status_and_unlock (connection,
3747                                                          DBUS_DISPATCH_NEED_MEMORY);
3748
3749      if (pending)
3750        dbus_pending_call_unref (pending);
3751      dbus_connection_unref (connection);
3752
3753      return DBUS_DISPATCH_NEED_MEMORY;
3754    }
3755
3756  _dbus_list_foreach (&filter_list_copy,
3757		      (DBusForeachFunction)_dbus_message_filter_ref,
3758		      NULL);
3759
3760  /* We're still protected from dispatch() reentrancy here
3761   * since we acquired the dispatcher
3762   */
3763  CONNECTION_UNLOCK (connection);
3764
3765  link = _dbus_list_get_first_link (&filter_list_copy);
3766  while (link != NULL)
3767    {
3768      DBusMessageFilter *filter = link->data;
3769      DBusList *next = _dbus_list_get_next_link (&filter_list_copy, link);
3770
3771      if (filter->function == NULL)
3772        {
3773          _dbus_verbose ("  filter was removed in a callback function\n");
3774          link = next;
3775          continue;
3776        }
3777
3778      _dbus_verbose ("  running filter on message %p\n", message);
3779      result = (* filter->function) (connection, message, filter->user_data);
3780
3781      if (result != DBUS_HANDLER_RESULT_NOT_YET_HANDLED)
3782	break;
3783
3784      link = next;
3785    }
3786
3787  _dbus_list_foreach (&filter_list_copy,
3788		      (DBusForeachFunction)_dbus_message_filter_unref,
3789		      NULL);
3790  _dbus_list_clear (&filter_list_copy);
3791
3792  CONNECTION_LOCK (connection);
3793
3794  if (result == DBUS_HANDLER_RESULT_NEED_MEMORY)
3795    {
3796      _dbus_verbose ("No memory in %s\n", _DBUS_FUNCTION_NAME);
3797      goto out;
3798    }
3799  else if (result == DBUS_HANDLER_RESULT_HANDLED)
3800    {
3801      _dbus_verbose ("filter handled message in dispatch\n");
3802      goto out;
3803    }
3804
3805  /* We're still protected from dispatch() reentrancy here
3806   * since we acquired the dispatcher
3807   */
3808  _dbus_verbose ("  running object path dispatch on message %p (%d %s %s '%s')\n",
3809                 message,
3810                 dbus_message_get_type (message),
3811                 dbus_message_get_interface (message) ?
3812                 dbus_message_get_interface (message) :
3813                 "no interface",
3814                 dbus_message_get_member (message) ?
3815                 dbus_message_get_member (message) :
3816                 "no member",
3817                 dbus_message_get_signature (message));
3818
3819  HAVE_LOCK_CHECK (connection);
3820  result = _dbus_object_tree_dispatch_and_unlock (connection->objects,
3821                                                  message);
3822
3823  CONNECTION_LOCK (connection);
3824
3825  if (result != DBUS_HANDLER_RESULT_NOT_YET_HANDLED)
3826    {
3827      _dbus_verbose ("object tree handled message in dispatch\n");
3828      goto out;
3829    }
3830
3831  if (dbus_message_get_type (message) == DBUS_MESSAGE_TYPE_METHOD_CALL)
3832    {
3833      DBusMessage *reply;
3834      DBusString str;
3835      DBusPreallocatedSend *preallocated;
3836
3837      _dbus_verbose ("  sending error %s\n",
3838                     DBUS_ERROR_UNKNOWN_METHOD);
3839
3840      if (!_dbus_string_init (&str))
3841        {
3842          result = DBUS_HANDLER_RESULT_NEED_MEMORY;
3843          _dbus_verbose ("no memory for error string in dispatch\n");
3844          goto out;
3845        }
3846
3847      if (!_dbus_string_append_printf (&str,
3848                                       "Method \"%s\" with signature \"%s\" on interface \"%s\" doesn't exist\n",
3849                                       dbus_message_get_member (message),
3850                                       dbus_message_get_signature (message),
3851                                       dbus_message_get_interface (message)))
3852        {
3853          _dbus_string_free (&str);
3854          result = DBUS_HANDLER_RESULT_NEED_MEMORY;
3855          _dbus_verbose ("no memory for error string in dispatch\n");
3856          goto out;
3857        }
3858
3859      reply = dbus_message_new_error (message,
3860                                      DBUS_ERROR_UNKNOWN_METHOD,
3861                                      _dbus_string_get_const_data (&str));
3862      _dbus_string_free (&str);
3863
3864      if (reply == NULL)
3865        {
3866          result = DBUS_HANDLER_RESULT_NEED_MEMORY;
3867          _dbus_verbose ("no memory for error reply in dispatch\n");
3868          goto out;
3869        }
3870
3871      preallocated = _dbus_connection_preallocate_send_unlocked (connection);
3872
3873      if (preallocated == NULL)
3874        {
3875          dbus_message_unref (reply);
3876          result = DBUS_HANDLER_RESULT_NEED_MEMORY;
3877          _dbus_verbose ("no memory for error send in dispatch\n");
3878          goto out;
3879        }
3880
3881      _dbus_connection_send_preallocated_unlocked_no_update (connection, preallocated,
3882                                                             reply, NULL);
3883
3884      dbus_message_unref (reply);
3885
3886      result = DBUS_HANDLER_RESULT_HANDLED;
3887    }
3888
3889  _dbus_verbose ("  done dispatching %p (%d %s %s '%s') on connection %p\n", message,
3890                 dbus_message_get_type (message),
3891                 dbus_message_get_interface (message) ?
3892                 dbus_message_get_interface (message) :
3893                 "no interface",
3894                 dbus_message_get_member (message) ?
3895                 dbus_message_get_member (message) :
3896                 "no member",
3897                 dbus_message_get_signature (message),
3898                 connection);
3899
3900 out:
3901  if (result == DBUS_HANDLER_RESULT_NEED_MEMORY)
3902    {
3903      _dbus_verbose ("out of memory in %s\n", _DBUS_FUNCTION_NAME);
3904
3905      /* Put message back, and we'll start over.
3906       * Yes this means handlers must be idempotent if they
3907       * don't return HANDLED; c'est la vie.
3908       */
3909      _dbus_connection_putback_message_link_unlocked (connection,
3910                                                      message_link);
3911    }
3912  else
3913    {
3914      _dbus_verbose (" ... done dispatching in %s\n", _DBUS_FUNCTION_NAME);
3915
3916      if (dbus_message_is_signal (message,
3917                                  DBUS_INTERFACE_LOCAL,
3918                                  "Disconnected"))
3919        {
3920          _dbus_bus_check_connection_and_unref_unlocked (connection);
3921
3922          if (connection->exit_on_disconnect)
3923            {
3924              CONNECTION_UNLOCK (connection);
3925
3926              _dbus_verbose ("Exiting on Disconnected signal\n");
3927              _dbus_exit (1);
3928              _dbus_assert_not_reached ("Call to exit() returned");
3929            }
3930        }
3931
3932      _dbus_list_free_link (message_link);
3933      dbus_message_unref (message); /* don't want the message to count in max message limits
3934                                     * in computing dispatch status below
3935                                     */
3936    }
3937
3938  _dbus_connection_release_dispatch (connection);
3939  HAVE_LOCK_CHECK (connection);
3940
3941  _dbus_verbose ("%s before final status update\n", _DBUS_FUNCTION_NAME);
3942  status = _dbus_connection_get_dispatch_status_unlocked (connection);
3943
3944  /* unlocks and calls user code */
3945  _dbus_connection_update_dispatch_status_and_unlock (connection, status);
3946
3947  dbus_connection_unref (connection);
3948
3949  return status;
3950}
3951
3952/**
3953 * Sets the watch functions for the connection. These functions are
3954 * responsible for making the application's main loop aware of file
3955 * descriptors that need to be monitored for events, using select() or
3956 * poll(). When using Qt, typically the DBusAddWatchFunction would
3957 * create a QSocketNotifier. When using GLib, the DBusAddWatchFunction
3958 * could call g_io_add_watch(), or could be used as part of a more
3959 * elaborate GSource. Note that when a watch is added, it may
3960 * not be enabled.
3961 *
3962 * The DBusWatchToggledFunction notifies the application that the
3963 * watch has been enabled or disabled. Call dbus_watch_get_enabled()
3964 * to check this. A disabled watch should have no effect, and enabled
3965 * watch should be added to the main loop. This feature is used
3966 * instead of simply adding/removing the watch because
3967 * enabling/disabling can be done without memory allocation.  The
3968 * toggled function may be NULL if a main loop re-queries
3969 * dbus_watch_get_enabled() every time anyway.
3970 *
3971 * The DBusWatch can be queried for the file descriptor to watch using
3972 * dbus_watch_get_fd(), and for the events to watch for using
3973 * dbus_watch_get_flags(). The flags returned by
3974 * dbus_watch_get_flags() will only contain DBUS_WATCH_READABLE and
3975 * DBUS_WATCH_WRITABLE, never DBUS_WATCH_HANGUP or DBUS_WATCH_ERROR;
3976 * all watches implicitly include a watch for hangups, errors, and
3977 * other exceptional conditions.
3978 *
3979 * Once a file descriptor becomes readable or writable, or an exception
3980 * occurs, dbus_watch_handle() should be called to
3981 * notify the connection of the file descriptor's condition.
3982 *
3983 * dbus_watch_handle() cannot be called during the
3984 * DBusAddWatchFunction, as the connection will not be ready to handle
3985 * that watch yet.
3986 *
3987 * It is not allowed to reference a DBusWatch after it has been passed
3988 * to remove_function.
3989 *
3990 * If #FALSE is returned due to lack of memory, the failure may be due
3991 * to a #FALSE return from the new add_function. If so, the
3992 * add_function may have been called successfully one or more times,
3993 * but the remove_function will also have been called to remove any
3994 * successful adds. i.e. if #FALSE is returned the net result
3995 * should be that dbus_connection_set_watch_functions() has no effect,
3996 * but the add_function and remove_function may have been called.
3997 *
3998 * @todo We need to drop the lock when we call the
3999 * add/remove/toggled functions which can be a side effect
4000 * of setting the watch functions.
4001 *
4002 * @param connection the connection.
4003 * @param add_function function to begin monitoring a new descriptor.
4004 * @param remove_function function to stop monitoring a descriptor.
4005 * @param toggled_function function to notify of enable/disable
4006 * @param data data to pass to add_function and remove_function.
4007 * @param free_data_function function to be called to free the data.
4008 * @returns #FALSE on failure (no memory)
4009 */
4010dbus_bool_t
4011dbus_connection_set_watch_functions (DBusConnection              *connection,
4012                                     DBusAddWatchFunction         add_function,
4013                                     DBusRemoveWatchFunction      remove_function,
4014                                     DBusWatchToggledFunction     toggled_function,
4015                                     void                        *data,
4016                                     DBusFreeFunction             free_data_function)
4017{
4018  dbus_bool_t retval;
4019  DBusWatchList *watches;
4020
4021  _dbus_return_val_if_fail (connection != NULL, FALSE);
4022
4023  CONNECTION_LOCK (connection);
4024
4025#ifndef DBUS_DISABLE_CHECKS
4026  if (connection->watches == NULL)
4027    {
4028      _dbus_warn ("Re-entrant call to %s is not allowed\n",
4029                  _DBUS_FUNCTION_NAME);
4030      return FALSE;
4031    }
4032#endif
4033
4034  /* ref connection for slightly better reentrancy */
4035  _dbus_connection_ref_unlocked (connection);
4036
4037  /* This can call back into user code, and we need to drop the
4038   * connection lock when it does. This is kind of a lame
4039   * way to do it.
4040   */
4041  watches = connection->watches;
4042  connection->watches = NULL;
4043  CONNECTION_UNLOCK (connection);
4044
4045  retval = _dbus_watch_list_set_functions (watches,
4046                                           add_function, remove_function,
4047                                           toggled_function,
4048                                           data, free_data_function);
4049  CONNECTION_LOCK (connection);
4050  connection->watches = watches;
4051
4052  CONNECTION_UNLOCK (connection);
4053  /* drop our paranoid refcount */
4054  dbus_connection_unref (connection);
4055
4056  return retval;
4057}
4058
4059/**
4060 * Sets the timeout functions for the connection. These functions are
4061 * responsible for making the application's main loop aware of timeouts.
4062 * When using Qt, typically the DBusAddTimeoutFunction would create a
4063 * QTimer. When using GLib, the DBusAddTimeoutFunction would call
4064 * g_timeout_add.
4065 *
4066 * The DBusTimeoutToggledFunction notifies the application that the
4067 * timeout has been enabled or disabled. Call
4068 * dbus_timeout_get_enabled() to check this. A disabled timeout should
4069 * have no effect, and enabled timeout should be added to the main
4070 * loop. This feature is used instead of simply adding/removing the
4071 * timeout because enabling/disabling can be done without memory
4072 * allocation. With Qt, QTimer::start() and QTimer::stop() can be used
4073 * to enable and disable. The toggled function may be NULL if a main
4074 * loop re-queries dbus_timeout_get_enabled() every time anyway.
4075 * Whenever a timeout is toggled, its interval may change.
4076 *
4077 * The DBusTimeout can be queried for the timer interval using
4078 * dbus_timeout_get_interval(). dbus_timeout_handle() should be called
4079 * repeatedly, each time the interval elapses, starting after it has
4080 * elapsed once. The timeout stops firing when it is removed with the
4081 * given remove_function.  The timer interval may change whenever the
4082 * timeout is added, removed, or toggled.
4083 *
4084 * @param connection the connection.
4085 * @param add_function function to add a timeout.
4086 * @param remove_function function to remove a timeout.
4087 * @param toggled_function function to notify of enable/disable
4088 * @param data data to pass to add_function and remove_function.
4089 * @param free_data_function function to be called to free the data.
4090 * @returns #FALSE on failure (no memory)
4091 */
4092dbus_bool_t
4093dbus_connection_set_timeout_functions   (DBusConnection            *connection,
4094					 DBusAddTimeoutFunction     add_function,
4095					 DBusRemoveTimeoutFunction  remove_function,
4096                                         DBusTimeoutToggledFunction toggled_function,
4097					 void                      *data,
4098					 DBusFreeFunction           free_data_function)
4099{
4100  dbus_bool_t retval;
4101  DBusTimeoutList *timeouts;
4102
4103  _dbus_return_val_if_fail (connection != NULL, FALSE);
4104
4105  CONNECTION_LOCK (connection);
4106
4107#ifndef DBUS_DISABLE_CHECKS
4108  if (connection->timeouts == NULL)
4109    {
4110      _dbus_warn ("Re-entrant call to %s is not allowed\n",
4111                  _DBUS_FUNCTION_NAME);
4112      return FALSE;
4113    }
4114#endif
4115
4116  /* ref connection for slightly better reentrancy */
4117  _dbus_connection_ref_unlocked (connection);
4118
4119  timeouts = connection->timeouts;
4120  connection->timeouts = NULL;
4121  CONNECTION_UNLOCK (connection);
4122
4123  retval = _dbus_timeout_list_set_functions (timeouts,
4124                                             add_function, remove_function,
4125                                             toggled_function,
4126                                             data, free_data_function);
4127  CONNECTION_LOCK (connection);
4128  connection->timeouts = timeouts;
4129
4130  CONNECTION_UNLOCK (connection);
4131  /* drop our paranoid refcount */
4132  dbus_connection_unref (connection);
4133
4134  return retval;
4135}
4136
4137/**
4138 * Sets the mainloop wakeup function for the connection. This function is
4139 * responsible for waking up the main loop (if its sleeping) when some some
4140 * change has happened to the connection that the mainloop needs to reconsider
4141 * (e.g. a message has been queued for writing).
4142 * When using Qt, this typically results in a call to QEventLoop::wakeUp().
4143 * When using GLib, it would call g_main_context_wakeup().
4144 *
4145 *
4146 * @param connection the connection.
4147 * @param wakeup_main_function function to wake up the mainloop
4148 * @param data data to pass wakeup_main_function
4149 * @param free_data_function function to be called to free the data.
4150 */
4151void
4152dbus_connection_set_wakeup_main_function (DBusConnection            *connection,
4153					  DBusWakeupMainFunction     wakeup_main_function,
4154					  void                      *data,
4155					  DBusFreeFunction           free_data_function)
4156{
4157  void *old_data;
4158  DBusFreeFunction old_free_data;
4159
4160  _dbus_return_if_fail (connection != NULL);
4161
4162  CONNECTION_LOCK (connection);
4163  old_data = connection->wakeup_main_data;
4164  old_free_data = connection->free_wakeup_main_data;
4165
4166  connection->wakeup_main_function = wakeup_main_function;
4167  connection->wakeup_main_data = data;
4168  connection->free_wakeup_main_data = free_data_function;
4169
4170  CONNECTION_UNLOCK (connection);
4171
4172  /* Callback outside the lock */
4173  if (old_free_data)
4174    (*old_free_data) (old_data);
4175}
4176
4177/**
4178 * Set a function to be invoked when the dispatch status changes.
4179 * If the dispatch status is #DBUS_DISPATCH_DATA_REMAINS, then
4180 * dbus_connection_dispatch() needs to be called to process incoming
4181 * messages. However, dbus_connection_dispatch() MUST NOT BE CALLED
4182 * from inside the DBusDispatchStatusFunction. Indeed, almost
4183 * any reentrancy in this function is a bad idea. Instead,
4184 * the DBusDispatchStatusFunction should simply save an indication
4185 * that messages should be dispatched later, when the main loop
4186 * is re-entered.
4187 *
4188 * @param connection the connection
4189 * @param function function to call on dispatch status changes
4190 * @param data data for function
4191 * @param free_data_function free the function data
4192 */
4193void
4194dbus_connection_set_dispatch_status_function (DBusConnection             *connection,
4195                                              DBusDispatchStatusFunction  function,
4196                                              void                       *data,
4197                                              DBusFreeFunction            free_data_function)
4198{
4199  void *old_data;
4200  DBusFreeFunction old_free_data;
4201
4202  _dbus_return_if_fail (connection != NULL);
4203
4204  CONNECTION_LOCK (connection);
4205  old_data = connection->dispatch_status_data;
4206  old_free_data = connection->free_dispatch_status_data;
4207
4208  connection->dispatch_status_function = function;
4209  connection->dispatch_status_data = data;
4210  connection->free_dispatch_status_data = free_data_function;
4211
4212  CONNECTION_UNLOCK (connection);
4213
4214  /* Callback outside the lock */
4215  if (old_free_data)
4216    (*old_free_data) (old_data);
4217}
4218
4219/**
4220 * Get the UNIX file descriptor of the connection, if any.  This can
4221 * be used for SELinux access control checks with getpeercon() for
4222 * example. DO NOT read or write to the file descriptor, or try to
4223 * select() on it; use DBusWatch for main loop integration. Not all
4224 * connections will have a file descriptor. So for adding descriptors
4225 * to the main loop, use dbus_watch_get_fd() and so forth.
4226 *
4227 * @todo this function should be called get_socket_fd or something;
4228 * there's no reason it can't work on Windows sockets also.
4229 *
4230 * @param connection the connection
4231 * @param fd return location for the file descriptor.
4232 * @returns #TRUE if fd is successfully obtained.
4233 */
4234dbus_bool_t
4235dbus_connection_get_unix_fd (DBusConnection *connection,
4236                             int            *fd)
4237{
4238  dbus_bool_t retval;
4239
4240  _dbus_return_val_if_fail (connection != NULL, FALSE);
4241  _dbus_return_val_if_fail (connection->transport != NULL, FALSE);
4242
4243  CONNECTION_LOCK (connection);
4244
4245  retval = _dbus_transport_get_socket_fd (connection->transport,
4246                                          fd);
4247
4248  CONNECTION_UNLOCK (connection);
4249
4250  return retval;
4251}
4252
4253/**
4254 * Gets the UNIX user ID of the connection if any.
4255 * Returns #TRUE if the uid is filled in.
4256 * Always returns #FALSE on non-UNIX platforms.
4257 * Always returns #FALSE prior to authenticating the
4258 * connection.
4259 *
4260 * @param connection the connection
4261 * @param uid return location for the user ID
4262 * @returns #TRUE if uid is filled in with a valid user ID
4263 */
4264dbus_bool_t
4265dbus_connection_get_unix_user (DBusConnection *connection,
4266                               unsigned long  *uid)
4267{
4268  dbus_bool_t result;
4269
4270  _dbus_return_val_if_fail (connection != NULL, FALSE);
4271  _dbus_return_val_if_fail (uid != NULL, FALSE);
4272
4273#ifdef DBUS_WIN
4274  /* FIXME this should be done at a lower level, but it's kind of hard,
4275   * just want to be sure we don't ship with this API returning
4276   * some weird internal fake uid for 1.0
4277   */
4278  return FALSE;
4279#endif
4280
4281  CONNECTION_LOCK (connection);
4282
4283  if (!_dbus_transport_get_is_authenticated (connection->transport))
4284    result = FALSE;
4285  else
4286    result = _dbus_transport_get_unix_user (connection->transport,
4287                                            uid);
4288  CONNECTION_UNLOCK (connection);
4289
4290  return result;
4291}
4292
4293/**
4294 * Gets the process ID of the connection if any.
4295 * Returns #TRUE if the uid is filled in.
4296 * Always returns #FALSE prior to authenticating the
4297 * connection.
4298 *
4299 * @param connection the connection
4300 * @param pid return location for the process ID
4301 * @returns #TRUE if uid is filled in with a valid process ID
4302 */
4303dbus_bool_t
4304dbus_connection_get_unix_process_id (DBusConnection *connection,
4305				     unsigned long  *pid)
4306{
4307  dbus_bool_t result;
4308
4309  _dbus_return_val_if_fail (connection != NULL, FALSE);
4310  _dbus_return_val_if_fail (pid != NULL, FALSE);
4311
4312#ifdef DBUS_WIN
4313  /* FIXME this should be done at a lower level, but it's kind of hard,
4314   * just want to be sure we don't ship with this API returning
4315   * some weird internal fake uid for 1.0
4316   */
4317  return FALSE;
4318#endif
4319
4320  CONNECTION_LOCK (connection);
4321
4322  if (!_dbus_transport_get_is_authenticated (connection->transport))
4323    result = FALSE;
4324  else
4325    result = _dbus_transport_get_unix_process_id (connection->transport,
4326						  pid);
4327  CONNECTION_UNLOCK (connection);
4328
4329  return result;
4330}
4331
4332/**
4333 * Sets a predicate function used to determine whether a given user ID
4334 * is allowed to connect. When an incoming connection has
4335 * authenticated with a particular user ID, this function is called;
4336 * if it returns #TRUE, the connection is allowed to proceed,
4337 * otherwise the connection is disconnected.
4338 *
4339 * If the function is set to #NULL (as it is by default), then
4340 * only the same UID as the server process will be allowed to
4341 * connect.
4342 *
4343 * @param connection the connection
4344 * @param function the predicate
4345 * @param data data to pass to the predicate
4346 * @param free_data_function function to free the data
4347 */
4348void
4349dbus_connection_set_unix_user_function (DBusConnection             *connection,
4350                                        DBusAllowUnixUserFunction   function,
4351                                        void                       *data,
4352                                        DBusFreeFunction            free_data_function)
4353{
4354  void *old_data = NULL;
4355  DBusFreeFunction old_free_function = NULL;
4356
4357  _dbus_return_if_fail (connection != NULL);
4358
4359  CONNECTION_LOCK (connection);
4360  _dbus_transport_set_unix_user_function (connection->transport,
4361                                          function, data, free_data_function,
4362                                          &old_data, &old_free_function);
4363  CONNECTION_UNLOCK (connection);
4364
4365  if (old_free_function != NULL)
4366    (* old_free_function) (old_data);
4367}
4368
4369/**
4370 * Adds a message filter. Filters are handlers that are run on all
4371 * incoming messages, prior to the objects registered with
4372 * dbus_connection_register_object_path().  Filters are run in the
4373 * order that they were added.  The same handler can be added as a
4374 * filter more than once, in which case it will be run more than once.
4375 * Filters added during a filter callback won't be run on the message
4376 * being processed.
4377 *
4378 * @todo we don't run filters on messages while blocking without
4379 * entering the main loop, since filters are run as part of
4380 * dbus_connection_dispatch(). This is probably a feature, as filters
4381 * could create arbitrary reentrancy. But kind of sucks if you're
4382 * trying to filter METHOD_RETURN for some reason.
4383 *
4384 * @param connection the connection
4385 * @param function function to handle messages
4386 * @param user_data user data to pass to the function
4387 * @param free_data_function function to use for freeing user data
4388 * @returns #TRUE on success, #FALSE if not enough memory.
4389 */
4390dbus_bool_t
4391dbus_connection_add_filter (DBusConnection            *connection,
4392                            DBusHandleMessageFunction  function,
4393                            void                      *user_data,
4394                            DBusFreeFunction           free_data_function)
4395{
4396  DBusMessageFilter *filter;
4397
4398  _dbus_return_val_if_fail (connection != NULL, FALSE);
4399  _dbus_return_val_if_fail (function != NULL, FALSE);
4400
4401  filter = dbus_new0 (DBusMessageFilter, 1);
4402  if (filter == NULL)
4403    return FALSE;
4404
4405  filter->refcount.value = 1;
4406
4407  CONNECTION_LOCK (connection);
4408
4409  if (!_dbus_list_append (&connection->filter_list,
4410                          filter))
4411    {
4412      _dbus_message_filter_unref (filter);
4413      CONNECTION_UNLOCK (connection);
4414      return FALSE;
4415    }
4416
4417  /* Fill in filter after all memory allocated,
4418   * so we don't run the free_user_data_function
4419   * if the add_filter() fails
4420   */
4421
4422  filter->function = function;
4423  filter->user_data = user_data;
4424  filter->free_user_data_function = free_data_function;
4425
4426  CONNECTION_UNLOCK (connection);
4427  return TRUE;
4428}
4429
4430/**
4431 * Removes a previously-added message filter. It is a programming
4432 * error to call this function for a handler that has not been added
4433 * as a filter. If the given handler was added more than once, only
4434 * one instance of it will be removed (the most recently-added
4435 * instance).
4436 *
4437 * @param connection the connection
4438 * @param function the handler to remove
4439 * @param user_data user data for the handler to remove
4440 *
4441 */
4442void
4443dbus_connection_remove_filter (DBusConnection            *connection,
4444                               DBusHandleMessageFunction  function,
4445                               void                      *user_data)
4446{
4447  DBusList *link;
4448  DBusMessageFilter *filter;
4449
4450  _dbus_return_if_fail (connection != NULL);
4451  _dbus_return_if_fail (function != NULL);
4452
4453  CONNECTION_LOCK (connection);
4454
4455  filter = NULL;
4456
4457  link = _dbus_list_get_last_link (&connection->filter_list);
4458  while (link != NULL)
4459    {
4460      filter = link->data;
4461
4462      if (filter->function == function &&
4463          filter->user_data == user_data)
4464        {
4465          _dbus_list_remove_link (&connection->filter_list, link);
4466          filter->function = NULL;
4467
4468          break;
4469        }
4470
4471      link = _dbus_list_get_prev_link (&connection->filter_list, link);
4472    }
4473
4474  CONNECTION_UNLOCK (connection);
4475
4476#ifndef DBUS_DISABLE_CHECKS
4477  if (filter == NULL)
4478    {
4479      _dbus_warn ("Attempt to remove filter function %p user data %p, but no such filter has been added\n",
4480                  function, user_data);
4481      return;
4482    }
4483#endif
4484
4485  /* Call application code */
4486  if (filter->free_user_data_function)
4487    (* filter->free_user_data_function) (filter->user_data);
4488
4489  filter->free_user_data_function = NULL;
4490  filter->user_data = NULL;
4491
4492  _dbus_message_filter_unref (filter);
4493}
4494
4495/**
4496 * Registers a handler for a given path in the object hierarchy.
4497 * The given vtable handles messages sent to exactly the given path.
4498 *
4499 *
4500 * @param connection the connection
4501 * @param path a '/' delimited string of path elements
4502 * @param vtable the virtual table
4503 * @param user_data data to pass to functions in the vtable
4504 * @returns #FALSE if not enough memory
4505 */
4506dbus_bool_t
4507dbus_connection_register_object_path (DBusConnection              *connection,
4508                                      const char                  *path,
4509                                      const DBusObjectPathVTable  *vtable,
4510                                      void                        *user_data)
4511{
4512  char **decomposed_path;
4513  dbus_bool_t retval;
4514
4515  _dbus_return_val_if_fail (connection != NULL, FALSE);
4516  _dbus_return_val_if_fail (path != NULL, FALSE);
4517  _dbus_return_val_if_fail (path[0] == '/', FALSE);
4518  _dbus_return_val_if_fail (vtable != NULL, FALSE);
4519
4520  if (!_dbus_decompose_path (path, strlen (path), &decomposed_path, NULL))
4521    return FALSE;
4522
4523  CONNECTION_LOCK (connection);
4524
4525  retval = _dbus_object_tree_register (connection->objects,
4526                                       FALSE,
4527                                       (const char **) decomposed_path, vtable,
4528                                       user_data);
4529
4530  CONNECTION_UNLOCK (connection);
4531
4532  dbus_free_string_array (decomposed_path);
4533
4534  return retval;
4535}
4536
4537/**
4538 * Registers a fallback handler for a given subsection of the object
4539 * hierarchy.  The given vtable handles messages at or below the given
4540 * path. You can use this to establish a default message handling
4541 * policy for a whole "subdirectory."
4542 *
4543 * @param connection the connection
4544 * @param path a '/' delimited string of path elements
4545 * @param vtable the virtual table
4546 * @param user_data data to pass to functions in the vtable
4547 * @returns #FALSE if not enough memory
4548 */
4549dbus_bool_t
4550dbus_connection_register_fallback (DBusConnection              *connection,
4551                                   const char                  *path,
4552                                   const DBusObjectPathVTable  *vtable,
4553                                   void                        *user_data)
4554{
4555  char **decomposed_path;
4556  dbus_bool_t retval;
4557
4558  _dbus_return_val_if_fail (connection != NULL, FALSE);
4559  _dbus_return_val_if_fail (path != NULL, FALSE);
4560  _dbus_return_val_if_fail (path[0] == '/', FALSE);
4561  _dbus_return_val_if_fail (vtable != NULL, FALSE);
4562
4563  if (!_dbus_decompose_path (path, strlen (path), &decomposed_path, NULL))
4564    return FALSE;
4565
4566  CONNECTION_LOCK (connection);
4567
4568  retval = _dbus_object_tree_register (connection->objects,
4569                                       TRUE,
4570				       (const char **) decomposed_path, vtable,
4571                                       user_data);
4572
4573  CONNECTION_UNLOCK (connection);
4574
4575  dbus_free_string_array (decomposed_path);
4576
4577  return retval;
4578}
4579
4580/**
4581 * Unregisters the handler registered with exactly the given path.
4582 * It's a bug to call this function for a path that isn't registered.
4583 * Can unregister both fallback paths and object paths.
4584 *
4585 * @param connection the connection
4586 * @param path a '/' delimited string of path elements
4587 * @returns #FALSE if not enough memory
4588 */
4589dbus_bool_t
4590dbus_connection_unregister_object_path (DBusConnection              *connection,
4591                                        const char                  *path)
4592{
4593  char **decomposed_path;
4594
4595  _dbus_return_val_if_fail (connection != NULL, FALSE);
4596  _dbus_return_val_if_fail (path != NULL, FALSE);
4597  _dbus_return_val_if_fail (path[0] == '/', FALSE);
4598
4599  if (!_dbus_decompose_path (path, strlen (path), &decomposed_path, NULL))
4600      return FALSE;
4601
4602  CONNECTION_LOCK (connection);
4603
4604  _dbus_object_tree_unregister_and_unlock (connection->objects, (const char **) decomposed_path);
4605
4606  dbus_free_string_array (decomposed_path);
4607
4608  return TRUE;
4609}
4610
4611/**
4612 * Gets the user data passed to dbus_connection_register_object_path()
4613 * or dbus_connection_register_fallback(). If nothing was registered
4614 * at this path, the data is filled in with #NULL.
4615 *
4616 * @param connection the connection
4617 * @param path the path you registered with
4618 * @param data_p location to store the user data, or #NULL
4619 * @returns #FALSE if not enough memory
4620 */
4621dbus_bool_t
4622dbus_connection_get_object_path_data (DBusConnection *connection,
4623                                      const char     *path,
4624                                      void          **data_p)
4625{
4626  char **decomposed_path;
4627
4628  _dbus_return_val_if_fail (connection != NULL, FALSE);
4629  _dbus_return_val_if_fail (path != NULL, FALSE);
4630  _dbus_return_val_if_fail (data_p != NULL, FALSE);
4631
4632  *data_p = NULL;
4633
4634  if (!_dbus_decompose_path (path, strlen (path), &decomposed_path, NULL))
4635    return FALSE;
4636
4637  CONNECTION_LOCK (connection);
4638
4639  *data_p = _dbus_object_tree_get_user_data_unlocked (connection->objects, (const char**) decomposed_path);
4640
4641  CONNECTION_UNLOCK (connection);
4642
4643  dbus_free_string_array (decomposed_path);
4644
4645  return TRUE;
4646}
4647
4648/**
4649 * Lists the registered fallback handlers and object path handlers at
4650 * the given parent_path. The returned array should be freed with
4651 * dbus_free_string_array().
4652 *
4653 * @param connection the connection
4654 * @param parent_path the path to list the child handlers of
4655 * @param child_entries returns #NULL-terminated array of children
4656 * @returns #FALSE if no memory to allocate the child entries
4657 */
4658dbus_bool_t
4659dbus_connection_list_registered (DBusConnection              *connection,
4660                                 const char                  *parent_path,
4661                                 char                      ***child_entries)
4662{
4663  char **decomposed_path;
4664  dbus_bool_t retval;
4665  _dbus_return_val_if_fail (connection != NULL, FALSE);
4666  _dbus_return_val_if_fail (parent_path != NULL, FALSE);
4667  _dbus_return_val_if_fail (parent_path[0] == '/', FALSE);
4668  _dbus_return_val_if_fail (child_entries != NULL, FALSE);
4669
4670  if (!_dbus_decompose_path (parent_path, strlen (parent_path), &decomposed_path, NULL))
4671    return FALSE;
4672
4673  CONNECTION_LOCK (connection);
4674
4675  retval = _dbus_object_tree_list_registered_and_unlock (connection->objects,
4676							 (const char **) decomposed_path,
4677							 child_entries);
4678  dbus_free_string_array (decomposed_path);
4679
4680  return retval;
4681}
4682
4683static DBusDataSlotAllocator slot_allocator;
4684_DBUS_DEFINE_GLOBAL_LOCK (connection_slots);
4685
4686/**
4687 * Allocates an integer ID to be used for storing application-specific
4688 * data on any DBusConnection. The allocated ID may then be used
4689 * with dbus_connection_set_data() and dbus_connection_get_data().
4690 * The passed-in slot must be initialized to -1, and is filled in
4691 * with the slot ID. If the passed-in slot is not -1, it's assumed
4692 * to be already allocated, and its refcount is incremented.
4693 *
4694 * The allocated slot is global, i.e. all DBusConnection objects will
4695 * have a slot with the given integer ID reserved.
4696 *
4697 * @param slot_p address of a global variable storing the slot
4698 * @returns #FALSE on failure (no memory)
4699 */
4700dbus_bool_t
4701dbus_connection_allocate_data_slot (dbus_int32_t *slot_p)
4702{
4703  return _dbus_data_slot_allocator_alloc (&slot_allocator,
4704                                          &_DBUS_LOCK_NAME (connection_slots),
4705                                          slot_p);
4706}
4707
4708/**
4709 * Deallocates a global ID for connection data slots.
4710 * dbus_connection_get_data() and dbus_connection_set_data() may no
4711 * longer be used with this slot.  Existing data stored on existing
4712 * DBusConnection objects will be freed when the connection is
4713 * finalized, but may not be retrieved (and may only be replaced if
4714 * someone else reallocates the slot).  When the refcount on the
4715 * passed-in slot reaches 0, it is set to -1.
4716 *
4717 * @param slot_p address storing the slot to deallocate
4718 */
4719void
4720dbus_connection_free_data_slot (dbus_int32_t *slot_p)
4721{
4722  _dbus_return_if_fail (*slot_p >= 0);
4723
4724  _dbus_data_slot_allocator_free (&slot_allocator, slot_p);
4725}
4726
4727/**
4728 * Stores a pointer on a DBusConnection, along
4729 * with an optional function to be used for freeing
4730 * the data when the data is set again, or when
4731 * the connection is finalized. The slot number
4732 * must have been allocated with dbus_connection_allocate_data_slot().
4733 *
4734 * @param connection the connection
4735 * @param slot the slot number
4736 * @param data the data to store
4737 * @param free_data_func finalizer function for the data
4738 * @returns #TRUE if there was enough memory to store the data
4739 */
4740dbus_bool_t
4741dbus_connection_set_data (DBusConnection   *connection,
4742                          dbus_int32_t      slot,
4743                          void             *data,
4744                          DBusFreeFunction  free_data_func)
4745{
4746  DBusFreeFunction old_free_func;
4747  void *old_data;
4748  dbus_bool_t retval;
4749
4750  _dbus_return_val_if_fail (connection != NULL, FALSE);
4751  _dbus_return_val_if_fail (slot >= 0, FALSE);
4752
4753  CONNECTION_LOCK (connection);
4754
4755  retval = _dbus_data_slot_list_set (&slot_allocator,
4756                                     &connection->slot_list,
4757                                     slot, data, free_data_func,
4758                                     &old_free_func, &old_data);
4759
4760  CONNECTION_UNLOCK (connection);
4761
4762  if (retval)
4763    {
4764      /* Do the actual free outside the connection lock */
4765      if (old_free_func)
4766        (* old_free_func) (old_data);
4767    }
4768
4769  return retval;
4770}
4771
4772/**
4773 * Retrieves data previously set with dbus_connection_set_data().
4774 * The slot must still be allocated (must not have been freed).
4775 *
4776 * @param connection the connection
4777 * @param slot the slot to get data from
4778 * @returns the data, or #NULL if not found
4779 */
4780void*
4781dbus_connection_get_data (DBusConnection   *connection,
4782                          dbus_int32_t      slot)
4783{
4784  void *res;
4785
4786  _dbus_return_val_if_fail (connection != NULL, NULL);
4787
4788  CONNECTION_LOCK (connection);
4789
4790  res = _dbus_data_slot_list_get (&slot_allocator,
4791                                  &connection->slot_list,
4792                                  slot);
4793
4794  CONNECTION_UNLOCK (connection);
4795
4796  return res;
4797}
4798
4799/**
4800 * This function sets a global flag for whether dbus_connection_new()
4801 * will set SIGPIPE behavior to SIG_IGN.
4802 *
4803 * @param will_modify_sigpipe #TRUE to allow sigpipe to be set to SIG_IGN
4804 */
4805void
4806dbus_connection_set_change_sigpipe (dbus_bool_t will_modify_sigpipe)
4807{
4808  _dbus_modify_sigpipe = will_modify_sigpipe != FALSE;
4809}
4810
4811/**
4812 * Specifies the maximum size message this connection is allowed to
4813 * receive. Larger messages will result in disconnecting the
4814 * connection.
4815 *
4816 * @param connection a #DBusConnection
4817 * @param size maximum message size the connection can receive, in bytes
4818 */
4819void
4820dbus_connection_set_max_message_size (DBusConnection *connection,
4821                                      long            size)
4822{
4823  _dbus_return_if_fail (connection != NULL);
4824
4825  CONNECTION_LOCK (connection);
4826  _dbus_transport_set_max_message_size (connection->transport,
4827                                        size);
4828  CONNECTION_UNLOCK (connection);
4829}
4830
4831/**
4832 * Gets the value set by dbus_connection_set_max_message_size().
4833 *
4834 * @param connection the connection
4835 * @returns the max size of a single message
4836 */
4837long
4838dbus_connection_get_max_message_size (DBusConnection *connection)
4839{
4840  long res;
4841
4842  _dbus_return_val_if_fail (connection != NULL, 0);
4843
4844  CONNECTION_LOCK (connection);
4845  res = _dbus_transport_get_max_message_size (connection->transport);
4846  CONNECTION_UNLOCK (connection);
4847  return res;
4848}
4849
4850/**
4851 * Sets the maximum total number of bytes that can be used for all messages
4852 * received on this connection. Messages count toward the maximum until
4853 * they are finalized. When the maximum is reached, the connection will
4854 * not read more data until some messages are finalized.
4855 *
4856 * The semantics of the maximum are: if outstanding messages are
4857 * already above the maximum, additional messages will not be read.
4858 * The semantics are not: if the next message would cause us to exceed
4859 * the maximum, we don't read it. The reason is that we don't know the
4860 * size of a message until after we read it.
4861 *
4862 * Thus, the max live messages size can actually be exceeded
4863 * by up to the maximum size of a single message.
4864 *
4865 * Also, if we read say 1024 bytes off the wire in a single read(),
4866 * and that contains a half-dozen small messages, we may exceed the
4867 * size max by that amount. But this should be inconsequential.
4868 *
4869 * This does imply that we can't call read() with a buffer larger
4870 * than we're willing to exceed this limit by.
4871 *
4872 * @param connection the connection
4873 * @param size the maximum size in bytes of all outstanding messages
4874 */
4875void
4876dbus_connection_set_max_received_size (DBusConnection *connection,
4877                                       long            size)
4878{
4879  _dbus_return_if_fail (connection != NULL);
4880
4881  CONNECTION_LOCK (connection);
4882  _dbus_transport_set_max_received_size (connection->transport,
4883                                         size);
4884  CONNECTION_UNLOCK (connection);
4885}
4886
4887/**
4888 * Gets the value set by dbus_connection_set_max_received_size().
4889 *
4890 * @param connection the connection
4891 * @returns the max size of all live messages
4892 */
4893long
4894dbus_connection_get_max_received_size (DBusConnection *connection)
4895{
4896  long res;
4897
4898  _dbus_return_val_if_fail (connection != NULL, 0);
4899
4900  CONNECTION_LOCK (connection);
4901  res = _dbus_transport_get_max_received_size (connection->transport);
4902  CONNECTION_UNLOCK (connection);
4903  return res;
4904}
4905
4906/**
4907 * Gets the approximate size in bytes of all messages in the outgoing
4908 * message queue. The size is approximate in that you shouldn't use
4909 * it to decide how many bytes to read off the network or anything
4910 * of that nature, as optimizations may choose to tell small white lies
4911 * to avoid performance overhead.
4912 *
4913 * @param connection the connection
4914 * @returns the number of bytes that have been queued up but not sent
4915 */
4916long
4917dbus_connection_get_outgoing_size (DBusConnection *connection)
4918{
4919  long res;
4920
4921  _dbus_return_val_if_fail (connection != NULL, 0);
4922
4923  CONNECTION_LOCK (connection);
4924  res = _dbus_counter_get_value (connection->outgoing_counter);
4925  CONNECTION_UNLOCK (connection);
4926  return res;
4927}
4928
4929/** @} */
4930