OLD | NEW |
1 // Copyright 2014 The Chromium Authors. All rights reserved. | 1 // Copyright 2014 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 #include "chromeos/dbus/bluetooth_gatt_characteristic_client.h" | 5 #include "chromeos/dbus/bluetooth_gatt_characteristic_client.h" |
6 | 6 |
7 #include "base/bind.h" | 7 #include "base/bind.h" |
8 #include "base/memory/weak_ptr.h" | 8 #include "base/memory/weak_ptr.h" |
9 #include "base/observer_list.h" | 9 #include "base/observer_list.h" |
10 #include "dbus/bus.h" | 10 #include "dbus/bus.h" |
11 #include "dbus/object_manager.h" | 11 #include "dbus/object_manager.h" |
12 #include "third_party/cros_system_api/dbus/service_constants.h" | 12 #include "third_party/cros_system_api/dbus/service_constants.h" |
13 | 13 |
14 namespace chromeos { | 14 namespace chromeos { |
15 | 15 |
| 16 // static |
| 17 const char BluetoothGattCharacteristicClient::kNoResponseError[] = |
| 18 "org.chromium.Error.NoResponse"; |
| 19 // static |
| 20 const char BluetoothGattCharacteristicClient::kUnknownCharacteristicError[] = |
| 21 "org.chromium.Error.UnknownCharacteristic"; |
| 22 |
16 BluetoothGattCharacteristicClient::Properties::Properties( | 23 BluetoothGattCharacteristicClient::Properties::Properties( |
17 dbus::ObjectProxy* object_proxy, | 24 dbus::ObjectProxy* object_proxy, |
18 const std::string& interface_name, | 25 const std::string& interface_name, |
19 const PropertyChangedCallback& callback) | 26 const PropertyChangedCallback& callback) |
20 : dbus::PropertySet(object_proxy, interface_name, callback) { | 27 : dbus::PropertySet(object_proxy, interface_name, callback) { |
21 RegisterProperty(bluetooth_gatt_characteristic::kUUIDProperty, &uuid); | 28 RegisterProperty(bluetooth_gatt_characteristic::kUUIDProperty, &uuid); |
22 RegisterProperty(bluetooth_gatt_characteristic::kServiceProperty, &service); | 29 RegisterProperty(bluetooth_gatt_characteristic::kServiceProperty, &service); |
23 RegisterProperty(bluetooth_gatt_characteristic::kValueProperty, &value); | |
24 RegisterProperty(bluetooth_gatt_characteristic::kFlagsProperty, &flags); | 30 RegisterProperty(bluetooth_gatt_characteristic::kFlagsProperty, &flags); |
25 } | 31 } |
26 | 32 |
27 BluetoothGattCharacteristicClient::Properties::~Properties() { | 33 BluetoothGattCharacteristicClient::Properties::~Properties() { |
28 } | 34 } |
29 | 35 |
30 // The BluetoothGattCharacteristicClient implementation used in production. | 36 // The BluetoothGattCharacteristicClient implementation used in production. |
31 class BluetoothGattCharacteristicClientImpl | 37 class BluetoothGattCharacteristicClientImpl |
32 : public BluetoothGattCharacteristicClient, | 38 : public BluetoothGattCharacteristicClient, |
33 public dbus::ObjectManager::Interface { | 39 public dbus::ObjectManager::Interface { |
(...skipping 33 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
67 virtual Properties* GetProperties( | 73 virtual Properties* GetProperties( |
68 const dbus::ObjectPath& object_path) OVERRIDE { | 74 const dbus::ObjectPath& object_path) OVERRIDE { |
69 DCHECK(object_manager_); | 75 DCHECK(object_manager_); |
70 return static_cast<Properties*>( | 76 return static_cast<Properties*>( |
71 object_manager_->GetProperties( | 77 object_manager_->GetProperties( |
72 object_path, | 78 object_path, |
73 bluetooth_gatt_characteristic:: | 79 bluetooth_gatt_characteristic:: |
74 kBluetoothGattCharacteristicInterface)); | 80 kBluetoothGattCharacteristicInterface)); |
75 } | 81 } |
76 | 82 |
| 83 // BluetoothGattCharacteristicClient override. |
| 84 virtual void ReadValue(const dbus::ObjectPath& object_path, |
| 85 const ValueCallback& callback, |
| 86 const ErrorCallback& error_callback) OVERRIDE { |
| 87 dbus::ObjectProxy* object_proxy = |
| 88 object_manager_->GetObjectProxy(object_path); |
| 89 if (!object_proxy) { |
| 90 error_callback.Run(kUnknownCharacteristicError, ""); |
| 91 return; |
| 92 } |
| 93 |
| 94 dbus::MethodCall method_call( |
| 95 bluetooth_gatt_characteristic::kBluetoothGattCharacteristicInterface, |
| 96 bluetooth_gatt_characteristic::kReadValue); |
| 97 |
| 98 object_proxy->CallMethodWithErrorCallback( |
| 99 &method_call, |
| 100 dbus::ObjectProxy::TIMEOUT_USE_DEFAULT, |
| 101 base::Bind(&BluetoothGattCharacteristicClientImpl::OnValueSuccess, |
| 102 weak_ptr_factory_.GetWeakPtr(), |
| 103 callback), |
| 104 base::Bind(&BluetoothGattCharacteristicClientImpl::OnError, |
| 105 weak_ptr_factory_.GetWeakPtr(), |
| 106 error_callback)); |
| 107 } |
| 108 |
| 109 // BluetoothGattCharacteristicClient override. |
| 110 virtual void WriteValue(const dbus::ObjectPath& object_path, |
| 111 const std::vector<uint8>& value, |
| 112 const base::Closure& callback, |
| 113 const ErrorCallback& error_callback) OVERRIDE { |
| 114 dbus::ObjectProxy* object_proxy = |
| 115 object_manager_->GetObjectProxy(object_path); |
| 116 if (!object_proxy) { |
| 117 error_callback.Run(kUnknownCharacteristicError, ""); |
| 118 return; |
| 119 } |
| 120 |
| 121 dbus::MethodCall method_call( |
| 122 bluetooth_gatt_characteristic::kBluetoothGattCharacteristicInterface, |
| 123 bluetooth_gatt_characteristic::kWriteValue); |
| 124 dbus::MessageWriter writer(&method_call); |
| 125 writer.AppendArrayOfBytes(value.data(), value.size()); |
| 126 |
| 127 object_proxy->CallMethodWithErrorCallback( |
| 128 &method_call, |
| 129 dbus::ObjectProxy::TIMEOUT_USE_DEFAULT, |
| 130 base::Bind(&BluetoothGattCharacteristicClientImpl::OnSuccess, |
| 131 weak_ptr_factory_.GetWeakPtr(), |
| 132 callback), |
| 133 base::Bind(&BluetoothGattCharacteristicClientImpl::OnError, |
| 134 weak_ptr_factory_.GetWeakPtr(), |
| 135 error_callback)); |
| 136 } |
| 137 |
77 // dbus::ObjectManager::Interface override. | 138 // dbus::ObjectManager::Interface override. |
78 virtual dbus::PropertySet* CreateProperties( | 139 virtual dbus::PropertySet* CreateProperties( |
79 dbus::ObjectProxy *object_proxy, | 140 dbus::ObjectProxy *object_proxy, |
80 const dbus::ObjectPath& object_path, | 141 const dbus::ObjectPath& object_path, |
81 const std::string& interface_name) OVERRIDE { | 142 const std::string& interface_name) OVERRIDE { |
82 Properties* properties = new Properties( | 143 Properties* properties = new Properties( |
83 object_proxy, | 144 object_proxy, |
84 interface_name, | 145 interface_name, |
85 base::Bind(&BluetoothGattCharacteristicClientImpl::OnPropertyChanged, | 146 base::Bind(&BluetoothGattCharacteristicClientImpl::OnPropertyChanged, |
86 weak_ptr_factory_.GetWeakPtr(), | 147 weak_ptr_factory_.GetWeakPtr(), |
87 object_path)); | 148 object_path)); |
88 return static_cast<dbus::PropertySet*>(properties); | 149 return static_cast<dbus::PropertySet*>(properties); |
89 } | 150 } |
90 | 151 |
91 // dbus::ObjectManager::Interface override. | 152 // dbus::ObjectManager::Interface override. |
92 virtual void ObjectAdded(const dbus::ObjectPath& object_path, | 153 virtual void ObjectAdded(const dbus::ObjectPath& object_path, |
93 const std::string& interface_name) OVERRIDE { | 154 const std::string& interface_name) OVERRIDE { |
94 VLOG(2) << "Remote GATT characteristic added: " << object_path.value(); | 155 VLOG(2) << "Remote GATT characteristic added: " << object_path.value(); |
95 FOR_EACH_OBSERVER(BluetoothGattCharacteristicClient::Observer, observers_, | 156 FOR_EACH_OBSERVER(BluetoothGattCharacteristicClient::Observer, observers_, |
96 GattCharacteristicAdded(object_path)); | 157 GattCharacteristicAdded(object_path)); |
| 158 |
| 159 // Connect the "ValueUpdated" signal. |
| 160 dbus::ObjectProxy* object_proxy = |
| 161 object_manager_->GetObjectProxy(object_path); |
| 162 DCHECK(object_proxy); |
| 163 |
| 164 object_proxy->ConnectToSignal( |
| 165 bluetooth_gatt_characteristic::kBluetoothGattCharacteristicInterface, |
| 166 bluetooth_gatt_characteristic::kValueUpdatedSignal, |
| 167 base::Bind(&BluetoothGattCharacteristicClientImpl::ValueUpdatedReceived, |
| 168 weak_ptr_factory_.GetWeakPtr(), |
| 169 object_path), |
| 170 base::Bind( |
| 171 &BluetoothGattCharacteristicClientImpl::ValueUpdatedConnected, |
| 172 weak_ptr_factory_.GetWeakPtr())); |
97 } | 173 } |
98 | 174 |
99 // dbus::ObjectManager::Interface override. | 175 // dbus::ObjectManager::Interface override. |
100 virtual void ObjectRemoved(const dbus::ObjectPath& object_path, | 176 virtual void ObjectRemoved(const dbus::ObjectPath& object_path, |
101 const std::string& interface_name) OVERRIDE { | 177 const std::string& interface_name) OVERRIDE { |
102 VLOG(2) << "Remote GATT characteristic removed: " << object_path.value(); | 178 VLOG(2) << "Remote GATT characteristic removed: " << object_path.value(); |
103 FOR_EACH_OBSERVER(BluetoothGattCharacteristicClient::Observer, observers_, | 179 FOR_EACH_OBSERVER(BluetoothGattCharacteristicClient::Observer, observers_, |
104 GattCharacteristicRemoved(object_path)); | 180 GattCharacteristicRemoved(object_path)); |
105 } | 181 } |
106 | 182 |
(...skipping 15 matching lines...) Expand all Loading... |
122 // observers. | 198 // observers. |
123 virtual void OnPropertyChanged(const dbus::ObjectPath& object_path, | 199 virtual void OnPropertyChanged(const dbus::ObjectPath& object_path, |
124 const std::string& property_name) { | 200 const std::string& property_name) { |
125 VLOG(2) << "Remote GATT characteristic property changed: " | 201 VLOG(2) << "Remote GATT characteristic property changed: " |
126 << object_path.value() << ": " << property_name; | 202 << object_path.value() << ": " << property_name; |
127 FOR_EACH_OBSERVER(BluetoothGattCharacteristicClient::Observer, observers_, | 203 FOR_EACH_OBSERVER(BluetoothGattCharacteristicClient::Observer, observers_, |
128 GattCharacteristicPropertyChanged(object_path, | 204 GattCharacteristicPropertyChanged(object_path, |
129 property_name)); | 205 property_name)); |
130 } | 206 } |
131 | 207 |
| 208 // Called by dbus:: when a "ValueUpdated" signal is received. |
| 209 void ValueUpdatedReceived(const dbus::ObjectPath& object_path, |
| 210 dbus::Signal* signal) { |
| 211 DCHECK(signal); |
| 212 const uint8* bytes = NULL; |
| 213 size_t length = 0; |
| 214 dbus::MessageReader reader(signal); |
| 215 if (!reader.PopArrayOfBytes(&bytes, &length)) { |
| 216 LOG(WARNING) << "ValueUpdated signal has incorrect parameters: " |
| 217 << signal->ToString(); |
| 218 return; |
| 219 } |
| 220 |
| 221 std::vector<uint8> value; |
| 222 if (bytes) |
| 223 value.assign(bytes, bytes + length); |
| 224 |
| 225 FOR_EACH_OBSERVER(BluetoothGattCharacteristicClient::Observer, |
| 226 observers_, |
| 227 GattCharacteristicValueUpdated(object_path, value)); |
| 228 } |
| 229 |
| 230 // Called by dbus:: when the "ValueUpdated" signal is initially connected. |
| 231 void ValueUpdatedConnected(const std::string& interface_name, |
| 232 const std::string& signal_name, |
| 233 bool success) { |
| 234 LOG_IF(WARNING, !success) << "Failed to connect to the ValueUpdated signal"; |
| 235 } |
| 236 |
| 237 // Called when a response for successful method call is received. |
| 238 void OnSuccess(const base::Closure& callback, dbus::Response* response) { |
| 239 DCHECK(response); |
| 240 callback.Run(); |
| 241 } |
| 242 |
| 243 // Called when a characteristic value response for a successful method call |
| 244 // is received. |
| 245 void OnValueSuccess(const ValueCallback& callback, dbus::Response* response) { |
| 246 DCHECK(response); |
| 247 dbus::MessageReader reader(response); |
| 248 |
| 249 const uint8* bytes = NULL; |
| 250 size_t length = 0; |
| 251 |
| 252 if (!reader.PopArrayOfBytes(&bytes, &length)) |
| 253 VLOG(2) << "Error reading array of bytes in ValueCallback"; |
| 254 |
| 255 std::vector<uint8> value; |
| 256 |
| 257 if (bytes) |
| 258 value.assign(bytes, bytes + length); |
| 259 |
| 260 callback.Run(value); |
| 261 } |
| 262 |
| 263 // Called when a response for a failed method call is received. |
| 264 void OnError(const ErrorCallback& error_callback, |
| 265 dbus::ErrorResponse* response) { |
| 266 // Error response has optional error message argument. |
| 267 std::string error_name; |
| 268 std::string error_message; |
| 269 if (response) { |
| 270 dbus::MessageReader reader(response); |
| 271 error_name = response->GetErrorName(); |
| 272 reader.PopString(&error_message); |
| 273 } else { |
| 274 error_name = kNoResponseError; |
| 275 error_message = ""; |
| 276 } |
| 277 error_callback.Run(error_name, error_message); |
| 278 } |
| 279 |
132 dbus::ObjectManager* object_manager_; | 280 dbus::ObjectManager* object_manager_; |
133 | 281 |
134 // List of observers interested in event notifications from us. | 282 // List of observers interested in event notifications from us. |
135 ObserverList<BluetoothGattCharacteristicClient::Observer> observers_; | 283 ObserverList<BluetoothGattCharacteristicClient::Observer> observers_; |
136 | 284 |
137 // Weak pointer factory for generating 'this' pointers that might live longer | 285 // Weak pointer factory for generating 'this' pointers that might live longer |
138 // than we do. | 286 // than we do. |
139 // Note: This should remain the last member so it'll be destroyed and | 287 // Note: This should remain the last member so it'll be destroyed and |
140 // invalidate its weak pointers before any other members are destroyed. | 288 // invalidate its weak pointers before any other members are destroyed. |
141 base::WeakPtrFactory<BluetoothGattCharacteristicClientImpl> | 289 base::WeakPtrFactory<BluetoothGattCharacteristicClientImpl> |
142 weak_ptr_factory_; | 290 weak_ptr_factory_; |
143 | 291 |
144 DISALLOW_COPY_AND_ASSIGN(BluetoothGattCharacteristicClientImpl); | 292 DISALLOW_COPY_AND_ASSIGN(BluetoothGattCharacteristicClientImpl); |
145 }; | 293 }; |
146 | 294 |
147 BluetoothGattCharacteristicClient::BluetoothGattCharacteristicClient() { | 295 BluetoothGattCharacteristicClient::BluetoothGattCharacteristicClient() { |
148 } | 296 } |
149 | 297 |
150 BluetoothGattCharacteristicClient::~BluetoothGattCharacteristicClient() { | 298 BluetoothGattCharacteristicClient::~BluetoothGattCharacteristicClient() { |
151 } | 299 } |
152 | 300 |
153 // static | 301 // static |
154 BluetoothGattCharacteristicClient* BluetoothGattCharacteristicClient::Create() { | 302 BluetoothGattCharacteristicClient* BluetoothGattCharacteristicClient::Create() { |
155 return new BluetoothGattCharacteristicClientImpl(); | 303 return new BluetoothGattCharacteristicClientImpl(); |
156 } | 304 } |
157 | 305 |
158 } // namespace chromeos | 306 } // namespace chromeos |
OLD | NEW |