| OLD | NEW |
| 1 // Copyright (c) 2011 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2011 The Chromium Authors. All rights reserved. |
| 2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
| 3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
| 4 | 4 |
| 5 #ifndef DBUS_BUS_H_ | 5 #ifndef DBUS_BUS_H_ |
| 6 #define DBUS_BUS_H_ | 6 #define DBUS_BUS_H_ |
| 7 #pragma once | 7 #pragma once |
| 8 | 8 |
| 9 #include <map> | 9 #include <map> |
| 10 #include <set> | 10 #include <set> |
| 11 #include <string> | 11 #include <string> |
| 12 #include <dbus/dbus.h> | 12 #include <dbus/dbus.h> |
| 13 | 13 |
| 14 #include "base/callback.h" | 14 #include "base/callback.h" |
| 15 #include "base/memory/ref_counted.h" | 15 #include "base/memory/ref_counted.h" |
| 16 #include "base/memory/scoped_ptr.h" | 16 #include "base/memory/scoped_ptr.h" |
| 17 #include "base/synchronization/waitable_event.h" |
| 17 #include "base/threading/platform_thread.h" | 18 #include "base/threading/platform_thread.h" |
| 18 #include "base/tracked_objects.h" | 19 #include "base/tracked_objects.h" |
| 19 | 20 |
| 20 class MessageLoop; | 21 class MessageLoop; |
| 21 | 22 |
| 22 namespace base { | 23 namespace base { |
| 23 class Thread; | 24 class Thread; |
| 24 } | 25 } |
| 25 | 26 |
| 26 namespace dbus { | 27 namespace dbus { |
| (...skipping 27 matching lines...) Expand all Loading... |
| 54 // supplied). AssertOnDBusThread() is placed in these functions. | 55 // supplied). AssertOnDBusThread() is placed in these functions. |
| 55 // | 56 // |
| 56 // Note that it's hard to tell if a libdbus function is actually blocking | 57 // Note that it's hard to tell if a libdbus function is actually blocking |
| 57 // or not (ex. dbus_bus_request_name() internally calls | 58 // or not (ex. dbus_bus_request_name() internally calls |
| 58 // dbus_connection_send_with_reply_and_block(), which is a blocking | 59 // dbus_connection_send_with_reply_and_block(), which is a blocking |
| 59 // call). To err on the safe side, we consider all libdbus functions that | 60 // call). To err on the safe side, we consider all libdbus functions that |
| 60 // deal with the connection to dbus-daemon to be blocking. | 61 // deal with the connection to dbus-daemon to be blocking. |
| 61 // | 62 // |
| 62 // SHUTDOWN | 63 // SHUTDOWN |
| 63 // | 64 // |
| 64 // The Bus object must be shut down manually by Shutdown() or | 65 // The Bus object must be shut down manually by ShutdownAndBlock() and |
| 65 // ShutdownAndBlock(). We require the manual shutdown as we should not | 66 // friends. We require the manual shutdown to make the operation explicit |
| 66 // issue blocking calls in the destructor. | 67 // rather than doing it silently in the destructor. |
| 67 // | 68 // |
| 68 // EXAMPLE USAGE: | 69 // EXAMPLE USAGE: |
| 69 // | 70 // |
| 70 // Synchronous method call: | 71 // Synchronous method call: |
| 71 // | 72 // |
| 72 // dbus::Bus::Options options; | 73 // dbus::Bus::Options options; |
| 73 // // Set up the bus options here. | 74 // // Set up the bus options here. |
| 74 // ... | 75 // ... |
| 75 // dbus::Bus bus(options); | 76 // dbus::Bus bus(options); |
| 76 // | 77 // |
| (...skipping 35 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 112 // ... | 113 // ... |
| 113 // dbus::ExportedObject* exported_object = | 114 // dbus::ExportedObject* exported_object = |
| 114 // bus.GetExportedObject(service_name, object_path); | 115 // bus.GetExportedObject(service_name, object_path); |
| 115 // exported_object.ExportMethod(interface_name, method_name, | 116 // exported_object.ExportMethod(interface_name, method_name, |
| 116 // base::Bind(&Echo), | 117 // base::Bind(&Echo), |
| 117 // base::Bind(&OnExported)); | 118 // base::Bind(&OnExported)); |
| 118 // | 119 // |
| 119 // WHY IS THIS A REF COUNTED OBJECT? | 120 // WHY IS THIS A REF COUNTED OBJECT? |
| 120 // | 121 // |
| 121 // Bus is a ref counted object, to ensure that |this| of the object is | 122 // Bus is a ref counted object, to ensure that |this| of the object is |
| 122 // alive when callbacks referencing |this| are called. However, after | 123 // alive when callbacks referencing |this| are called. However, after the |
| 123 // Shutdown() is called, |connection_| can be NULL. Hence, callbacks should | 124 // bus is shut down, |connection_| can be NULL. Hence, callbacks should |
| 124 // not rely on that |connection_| is alive. | 125 // not rely on that |connection_| is alive. |
| 125 class Bus : public base::RefCountedThreadSafe<Bus> { | 126 class Bus : public base::RefCountedThreadSafe<Bus> { |
| 126 public: | 127 public: |
| 127 // Specifies the bus type. SESSION is used to communicate with per-user | 128 // Specifies the bus type. SESSION is used to communicate with per-user |
| 128 // services like GNOME applications. SYSTEM is used to communicate with | 129 // services like GNOME applications. SYSTEM is used to communicate with |
| 129 // system-wide services like NetworkManager. | 130 // system-wide services like NetworkManager. |
| 130 enum BusType { | 131 enum BusType { |
| 131 SESSION = DBUS_BUS_SESSION, | 132 SESSION = DBUS_BUS_SESSION, |
| 132 SYSTEM = DBUS_BUS_SYSTEM, | 133 SYSTEM = DBUS_BUS_SYSTEM, |
| 133 }; | 134 }; |
| (...skipping 22 matching lines...) Expand all Loading... |
| 156 // If the thread is set, the bus object will use the message loop | 157 // If the thread is set, the bus object will use the message loop |
| 157 // attached to the thread to process asynchronous operations. | 158 // attached to the thread to process asynchronous operations. |
| 158 // | 159 // |
| 159 // The thread should meet the following requirements: | 160 // The thread should meet the following requirements: |
| 160 // 1) Already running. | 161 // 1) Already running. |
| 161 // 2) Has a MessageLoopForIO. | 162 // 2) Has a MessageLoopForIO. |
| 162 // 3) Outlives the bus. | 163 // 3) Outlives the bus. |
| 163 base::Thread* dbus_thread; // NULL by default. | 164 base::Thread* dbus_thread; // NULL by default. |
| 164 }; | 165 }; |
| 165 | 166 |
| 166 // Called when shutdown is done. Used for Shutdown(). | |
| 167 typedef base::Callback<void ()> OnShutdownCallback; | |
| 168 | |
| 169 // Creates a Bus object. The actual connection will be established when | 167 // Creates a Bus object. The actual connection will be established when |
| 170 // Connect() is called. | 168 // Connect() is called. |
| 171 explicit Bus(const Options& options); | 169 explicit Bus(const Options& options); |
| 172 | 170 |
| 173 // Gets the object proxy for the given service name and the object path. | 171 // Gets the object proxy for the given service name and the object path. |
| 174 // The caller must not delete the returned object. | 172 // The caller must not delete the returned object. |
| 175 // | 173 // |
| 176 // Returns an existing object proxy if the bus object already owns the | 174 // Returns an existing object proxy if the bus object already owns the |
| 177 // object proxy for the given service name and the object path. | 175 // object proxy for the given service name and the object path. |
| 178 // Never returns NULL. | 176 // Never returns NULL. |
| (...skipping 33 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 212 // Shuts down the bus and blocks until it's done. More specifically, this | 210 // Shuts down the bus and blocks until it's done. More specifically, this |
| 213 // function does the following: | 211 // function does the following: |
| 214 // | 212 // |
| 215 // - Unregisters the object paths | 213 // - Unregisters the object paths |
| 216 // - Releases the service names | 214 // - Releases the service names |
| 217 // - Closes the connection to dbus-daemon. | 215 // - Closes the connection to dbus-daemon. |
| 218 // | 216 // |
| 219 // BLOCKING CALL. | 217 // BLOCKING CALL. |
| 220 virtual void ShutdownAndBlock(); | 218 virtual void ShutdownAndBlock(); |
| 221 | 219 |
| 222 // Shuts down the bus in the D-Bus thread. |callback| will be called in | 220 // Similar to ShutdownAndBlock(), but this function is used to |
| 223 // the origin thread. | 221 // synchronously shut down the bus that uses the D-Bus thread. This |
| 222 // function is intended to be used at the very end of the browser |
| 223 // shutdown, where it makes more sense to shut down the bus |
| 224 // synchronously, than trying to make it asynchronous. |
| 224 // | 225 // |
| 225 // Must be called in the origin thread. | 226 // BLOCKING CALL, but must be called in the origin thread. |
| 226 virtual void Shutdown(OnShutdownCallback callback); | 227 virtual void ShutdownOnDBusThreadAndBlock(); |
| 228 |
| 229 // Returns true if the shutdown has been completed. |
| 230 bool shutdown_completed() { return shutdown_completed_; } |
| 227 | 231 |
| 228 // | 232 // |
| 229 // The public functions below are not intended to be used in client | 233 // The public functions below are not intended to be used in client |
| 230 // code. These are used to implement ObjectProxy and ExportedObject. | 234 // code. These are used to implement ObjectProxy and ExportedObject. |
| 231 // | 235 // |
| 232 | 236 |
| 233 // Connects the bus to the dbus-daemon. | 237 // Connects the bus to the dbus-daemon. |
| 234 // Returns true on success, or the bus is already connected. | 238 // Returns true on success, or the bus is already connected. |
| 235 // | 239 // |
| 236 // BLOCKING CALL. | 240 // BLOCKING CALL. |
| (...skipping 137 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 374 // AssertOnOriginThread(). | 378 // AssertOnOriginThread(). |
| 375 virtual void AssertOnDBusThread(); | 379 virtual void AssertOnDBusThread(); |
| 376 | 380 |
| 377 protected: | 381 protected: |
| 378 // This is protected, so we can define sub classes. | 382 // This is protected, so we can define sub classes. |
| 379 virtual ~Bus(); | 383 virtual ~Bus(); |
| 380 | 384 |
| 381 private: | 385 private: |
| 382 friend class base::RefCountedThreadSafe<Bus>; | 386 friend class base::RefCountedThreadSafe<Bus>; |
| 383 | 387 |
| 384 // Helper function used for Shutdown(). | 388 // Helper function used for ShutdownOnDBusThreadAndBlock(). |
| 385 void ShutdownInternal(OnShutdownCallback callback); | 389 void ShutdownOnDBusThreadAndBlockInternal(); |
| 386 | 390 |
| 387 // Processes the all incoming data to the connection, if any. | 391 // Processes the all incoming data to the connection, if any. |
| 388 // | 392 // |
| 389 // BLOCKING CALL. | 393 // BLOCKING CALL. |
| 390 void ProcessAllIncomingDataIfAny(); | 394 void ProcessAllIncomingDataIfAny(); |
| 391 | 395 |
| 392 // Called when a watch object is added. Used to start monitoring the | 396 // Called when a watch object is added. Used to start monitoring the |
| 393 // file descriptor used for D-Bus communication. | 397 // file descriptor used for D-Bus communication. |
| 394 dbus_bool_t OnAddWatch(DBusWatch* raw_watch); | 398 dbus_bool_t OnAddWatch(DBusWatch* raw_watch); |
| 395 | 399 |
| (...skipping 24 matching lines...) Expand all Loading... |
| 420 static void OnToggleWatchThunk(DBusWatch* raw_watch, void* data); | 424 static void OnToggleWatchThunk(DBusWatch* raw_watch, void* data); |
| 421 static dbus_bool_t OnAddTimeoutThunk(DBusTimeout* raw_timeout, void* data); | 425 static dbus_bool_t OnAddTimeoutThunk(DBusTimeout* raw_timeout, void* data); |
| 422 static void OnRemoveTimeoutThunk(DBusTimeout* raw_timeout, void* data); | 426 static void OnRemoveTimeoutThunk(DBusTimeout* raw_timeout, void* data); |
| 423 static void OnToggleTimeoutThunk(DBusTimeout* raw_timeout, void* data); | 427 static void OnToggleTimeoutThunk(DBusTimeout* raw_timeout, void* data); |
| 424 static void OnDispatchStatusChangedThunk(DBusConnection* connection, | 428 static void OnDispatchStatusChangedThunk(DBusConnection* connection, |
| 425 DBusDispatchStatus status, | 429 DBusDispatchStatus status, |
| 426 void* data); | 430 void* data); |
| 427 const BusType bus_type_; | 431 const BusType bus_type_; |
| 428 const ConnectionType connection_type_; | 432 const ConnectionType connection_type_; |
| 429 base::Thread* dbus_thread_; | 433 base::Thread* dbus_thread_; |
| 434 base::WaitableEvent on_shutdown_; |
| 430 DBusConnection* connection_; | 435 DBusConnection* connection_; |
| 431 | 436 |
| 432 MessageLoop* origin_loop_; | 437 MessageLoop* origin_loop_; |
| 433 base::PlatformThreadId origin_thread_id_; | 438 base::PlatformThreadId origin_thread_id_; |
| 434 base::PlatformThreadId dbus_thread_id_; | 439 base::PlatformThreadId dbus_thread_id_; |
| 435 | 440 |
| 436 std::set<std::string> owned_service_names_; | 441 std::set<std::string> owned_service_names_; |
| 437 // The following sets are used to check if rules/object_paths/filters | 442 // The following sets are used to check if rules/object_paths/filters |
| 438 // are properly cleaned up before destruction of the bus object. | 443 // are properly cleaned up before destruction of the bus object. |
| 439 std::set<std::string> match_rules_added_; | 444 std::set<std::string> match_rules_added_; |
| 440 std::set<std::string> registered_object_paths_; | 445 std::set<std::string> registered_object_paths_; |
| 441 std::set<DBusHandleMessageFunction> filter_functions_added_; | 446 std::set<DBusHandleMessageFunction> filter_functions_added_; |
| 442 | 447 |
| 443 // ObjectProxyTable is used to hold the object proxies created by the | 448 // ObjectProxyTable is used to hold the object proxies created by the |
| 444 // bus object. Key is a concatenated string of service name + object path, | 449 // bus object. Key is a concatenated string of service name + object path, |
| 445 // like "org.chromium.TestService/org/chromium/TestObject". | 450 // like "org.chromium.TestService/org/chromium/TestObject". |
| 446 typedef std::map<std::string, | 451 typedef std::map<std::string, |
| 447 scoped_refptr<dbus::ObjectProxy> > ObjectProxyTable; | 452 scoped_refptr<dbus::ObjectProxy> > ObjectProxyTable; |
| 448 ObjectProxyTable object_proxy_table_; | 453 ObjectProxyTable object_proxy_table_; |
| 449 | 454 |
| 450 // ExportedObjectTable is used to hold the exported objects created by | 455 // ExportedObjectTable is used to hold the exported objects created by |
| 451 // the bus object. Key is a concatenated string of service name + | 456 // the bus object. Key is a concatenated string of service name + |
| 452 // object path, like "org.chromium.TestService/org/chromium/TestObject". | 457 // object path, like "org.chromium.TestService/org/chromium/TestObject". |
| 453 typedef std::map<std::string, | 458 typedef std::map<std::string, |
| 454 scoped_refptr<dbus::ExportedObject> > ExportedObjectTable; | 459 scoped_refptr<dbus::ExportedObject> > ExportedObjectTable; |
| 455 ExportedObjectTable exported_object_table_; | 460 ExportedObjectTable exported_object_table_; |
| 456 | 461 |
| 457 bool async_operations_set_up_; | 462 bool async_operations_set_up_; |
| 463 bool shutdown_completed_; |
| 458 | 464 |
| 459 // Counters to make sure that OnAddWatch()/OnRemoveWatch() and | 465 // Counters to make sure that OnAddWatch()/OnRemoveWatch() and |
| 460 // OnAddTimeout()/OnRemoveTimeou() are balanced. | 466 // OnAddTimeout()/OnRemoveTimeou() are balanced. |
| 461 int num_pending_watches_; | 467 int num_pending_watches_; |
| 462 int num_pending_timeouts_; | 468 int num_pending_timeouts_; |
| 463 | 469 |
| 464 DISALLOW_COPY_AND_ASSIGN(Bus); | 470 DISALLOW_COPY_AND_ASSIGN(Bus); |
| 465 }; | 471 }; |
| 466 | 472 |
| 467 } // namespace dbus | 473 } // namespace dbus |
| 468 | 474 |
| 469 #endif // DBUS_BUS_H_ | 475 #endif // DBUS_BUS_H_ |
| OLD | NEW |