OLD | NEW |
| (Empty) |
1 // Copyright 2013 The Chromium Authors. All rights reserved. | |
2 // Use of this source code is governed by a BSD-style license that can be | |
3 // found in the LICENSE file. | |
4 | |
5 #ifndef CHROMEOS_DBUS_NFC_CLIENT_HELPERS_H_ | |
6 #define CHROMEOS_DBUS_NFC_CLIENT_HELPERS_H_ | |
7 | |
8 #include <map> | |
9 #include <string> | |
10 #include <utility> | |
11 | |
12 #include "base/callback.h" | |
13 #include "base/macros.h" | |
14 #include "base/values.h" | |
15 #include "chromeos/chromeos_export.h" | |
16 #include "chromeos/dbus/nfc_property_set.h" | |
17 #include "dbus/bus.h" | |
18 #include "dbus/message.h" | |
19 #include "dbus/object_path.h" | |
20 #include "dbus/object_proxy.h" | |
21 | |
22 namespace chromeos { | |
23 namespace nfc_client_helpers { | |
24 | |
25 // Constants used to indicate exceptional error conditions. | |
26 CHROMEOS_EXPORT extern const char kNoResponseError[]; | |
27 CHROMEOS_EXPORT extern const char kUnknownObjectError[]; | |
28 | |
29 // The ErrorCallback is used by D-Bus methods to indicate failure. | |
30 // It receives two arguments: the name of the error in |error_name| and | |
31 // an optional message in |error_message|. | |
32 typedef base::Callback<void(const std::string& error_name, | |
33 const std::string& error_message)> ErrorCallback; | |
34 | |
35 // A vector of object paths is used frequently among the NFC client classes. | |
36 // This typedef makes the type specifier a little less verbose. | |
37 typedef std::vector<dbus::ObjectPath> ObjectPathVector; | |
38 | |
39 // Called when a response for a successful method call is received. | |
40 CHROMEOS_EXPORT void OnSuccess(const base::Closure& callback, | |
41 dbus::Response* response); | |
42 | |
43 // Extracts the error data from |response| and invokes |error_callback| with | |
44 // the resulting error name and error message. | |
45 CHROMEOS_EXPORT void OnError(const ErrorCallback& error_callback, | |
46 dbus::ErrorResponse* response); | |
47 | |
48 // DBusObjectMap is a simple data structure that facilitates keeping track of | |
49 // D-Bus object proxies and properties. It maintains a mapping from object | |
50 // paths to object proxy - property structure pairs. | |
51 // TODO(armansito): This is only needed until neard implements the D-Bus | |
52 // org.freedesktop.DBus.ObjectManager interface. Remove this once we upgrade | |
53 // to neard-0.14. | |
54 class CHROMEOS_EXPORT DBusObjectMap { | |
55 public: | |
56 // DBusObjectMap::Delegate must be implemented by classes that use an | |
57 // instance of DBusObjectMap to manage object proxies. | |
58 class Delegate { | |
59 public: | |
60 virtual ~Delegate() {} | |
61 | |
62 // Called by DBusObjectMap to create a Properties structure for the remote | |
63 // D-Bus object accessible through |object_proxy|. The implementation class | |
64 // should create and return an instance of its own subclass of | |
65 // ::chromeos::NfcPropertySet. DBusObjectMap will handle connecting the | |
66 // signals and update the properties. | |
67 virtual NfcPropertySet* CreateProperties( | |
68 dbus::ObjectProxy* object_proxy) = 0; | |
69 | |
70 // Notifies the delegate that an object was added with object path | |
71 // |object_path|. | |
72 virtual void ObjectAdded(const dbus::ObjectPath& object_path) {} | |
73 | |
74 // Notifies the delegate that an object was removed with object path | |
75 // |object_path|. The object proxy will still be valid before this method | |
76 // returns, so that delegates can perform any clean up that use the object | |
77 // properties. Note that the remote object will no longer be available, | |
78 // but the delegates can still access the cached properties of the object. | |
79 virtual void ObjectRemoved(const dbus::ObjectPath& object_path) {} | |
80 }; | |
81 | |
82 // Constructor takes in the D-Bus service name the proxies belong to and | |
83 // the delegate which will be used to construct properties structures. | |
84 // |service_name| must be a valid D-Bus service name, and |delegate| cannot | |
85 // be NULL. | |
86 DBusObjectMap(const std::string& service_name, | |
87 Delegate* delegate, | |
88 dbus::Bus* bus); | |
89 | |
90 // Destructor destroys all managed object proxies and notifies the delegate | |
91 // for each removed object. | |
92 virtual ~DBusObjectMap(); | |
93 | |
94 // Returns the object proxy for object path |object_path|. If no object proxy | |
95 // exists for |object_path|, returns NULL. | |
96 dbus::ObjectProxy* GetObjectProxy(const dbus::ObjectPath& object_path); | |
97 | |
98 // Returns the properties structure for remote object with object path | |
99 // |object_path|. If no properties structure exists for |object_path|, | |
100 // returns NULL. | |
101 NfcPropertySet* GetObjectProperties(const dbus::ObjectPath& object_path); | |
102 | |
103 // Updates the object proxies from the given list of object paths | |
104 // |object_paths|. It notifies the delegate of each added and removed object | |
105 // via |Delegate::ObjectAdded| and |Delegate::ObjectRemoved|. | |
106 void UpdateObjects(const ObjectPathVector& object_paths); | |
107 | |
108 // Creates and stores an object proxy and properties structure for a remote | |
109 // object with object path |object_path|. If an object proxy was already | |
110 // created, this operation returns false; returns true otherwise. | |
111 bool AddObject(const dbus::ObjectPath& object_path); | |
112 | |
113 // Removes the D-Bus object proxy and the properties structure for the | |
114 // remote object with object path |object_path|. If no known proxy for | |
115 // |object_path| exists, then this operation is a no-op. | |
116 void RemoveObject(const dbus::ObjectPath& object_path); | |
117 | |
118 // Invokes GetAll on the property structure belonging to object path | |
119 // |object_path|. If |object_path| is unknown, this method is a no-op. | |
120 void RefreshProperties(const dbus::ObjectPath& object_path); | |
121 | |
122 // Invokes GetAll on the property structures belonging to all object paths | |
123 // that are managed by this instance. | |
124 void RefreshAllProperties(); | |
125 | |
126 // Returns a list containing the object paths of all remote objects that are | |
127 // managed by this instance. | |
128 ObjectPathVector GetObjectPaths(); | |
129 | |
130 private: | |
131 typedef std::pair<dbus::ObjectProxy*, NfcPropertySet*> ObjectPropertyPair; | |
132 typedef std::map<dbus::ObjectPath, ObjectPropertyPair> ObjectMap; | |
133 | |
134 // Returns an instance of ObjectPropertyPair by looking up |object_path| in | |
135 // |object_map_|. If no entry is found, returns an instance that contains | |
136 // NULL pointers. | |
137 ObjectPropertyPair GetObjectPropertyPair(const dbus::ObjectPath& object_path); | |
138 | |
139 // Cleans up the object proxy and properties structure in |pair|. This method | |
140 // will remove the object proxy by calling |dbus::Bus::RemoveObjectProxy| and | |
141 // explicitly deallocate the properties structure. Once this method exits, | |
142 // both pointers stored by |pair| will become invalid and should not be used. | |
143 // If |pair| contains invalid pointers at the time when this method is called | |
144 // memory errors are likely to happen, so only valid pointers should be | |
145 // passed. | |
146 void CleanUpObjectPropertyPair(const ObjectPropertyPair& pair); | |
147 | |
148 dbus::Bus* bus_; | |
149 ObjectMap object_map_; | |
150 std::string service_name_; | |
151 Delegate* delegate_; | |
152 | |
153 DISALLOW_COPY_AND_ASSIGN(DBusObjectMap); | |
154 }; | |
155 | |
156 // Most NFC D-Bus client classes need to be able to look up object proxies by | |
157 // the path of the object that owns them. For example, NfcTagClient updates tag | |
158 // proxies based on the adapter that owns them. ObjectProxyTree is a two-level | |
159 // mapping that makes this management easy. | |
160 class ObjectProxyTree { | |
161 public: | |
162 ObjectProxyTree(); | |
163 | |
164 // The destructor destroys all contained DBusObjectMap instances. This will | |
165 // cause the delegate to get notified for each removed object proxy according | |
166 // to the DBusObjectMap destructor. | |
167 virtual ~ObjectProxyTree(); | |
168 | |
169 // Creates a DBusObjectMap instance at object path |object_path|. | |
170 // |service_name|, |delegate|, and |bus| are passed to the constructor of the | |
171 // DBusObjectMap that is created. If a DBusObjectMap for |object_path| was | |
172 // already assigned, returns false and does nothing. Otherwise, if a new | |
173 // DBusObjectMap was created, returns true. | |
174 bool CreateObjectMap(const dbus::ObjectPath& object_path, | |
175 const std::string& service_name, | |
176 DBusObjectMap::Delegate* delegate, | |
177 dbus::Bus* bus); | |
178 | |
179 // Destroys the DBusObjectMap instance at object path |object_path|. | |
180 void RemoveObjectMap(const dbus::ObjectPath& object_path); | |
181 | |
182 // Returns the DBusObjectMap instance at object path |object_path|, or NULL | |
183 // if no such instance exists. | |
184 DBusObjectMap* GetObjectMap(const dbus::ObjectPath& object_path); | |
185 | |
186 // Returns the object proxy by searching all stored DBusObjectMap instances | |
187 // for |object_proxy_path|. Returns NULL, if nothing is found. | |
188 dbus::ObjectProxy* FindObjectProxy( | |
189 const dbus::ObjectPath& object_proxy_path); | |
190 | |
191 // Returns the object property structure by searching all stored DBusObjectMap | |
192 // instances for |object_proxy_path|. Returns NULL, if nothing is found. | |
193 NfcPropertySet* FindObjectProperties( | |
194 const dbus::ObjectPath& object_proxy_path); | |
195 | |
196 private: | |
197 typedef std::map<dbus::ObjectPath, DBusObjectMap*> PathsToObjectMapsType; | |
198 PathsToObjectMapsType paths_to_object_maps_; | |
199 | |
200 DISALLOW_COPY_AND_ASSIGN(ObjectProxyTree); | |
201 }; | |
202 | |
203 } // namespace nfc_client_helpers | |
204 } // namespace chromeos | |
205 | |
206 #endif // CHROMEOS_DBUS_NFC_CLIENT_HELPERS_H_ | |
OLD | NEW |