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