| 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 "device/bluetooth/bluetooth_remote_gatt_characteristic_chromeos.h" | 5 #include "device/bluetooth/bluetooth_remote_gatt_characteristic_chromeos.h" |
| 6 | 6 |
| 7 #include "base/logging.h" | 7 #include "base/logging.h" |
| 8 #include "base/strings/stringprintf.h" | 8 #include "base/strings/stringprintf.h" |
| 9 #include "chromeos/dbus/bluetooth_gatt_characteristic_client.h" | |
| 10 #include "chromeos/dbus/dbus_thread_manager.h" | 9 #include "chromeos/dbus/dbus_thread_manager.h" |
| 11 #include "device/bluetooth/bluetooth_remote_gatt_descriptor_chromeos.h" | 10 #include "device/bluetooth/bluetooth_remote_gatt_descriptor_chromeos.h" |
| 12 #include "device/bluetooth/bluetooth_remote_gatt_service_chromeos.h" | 11 #include "device/bluetooth/bluetooth_remote_gatt_service_chromeos.h" |
| 13 #include "third_party/cros_system_api/dbus/service_constants.h" | 12 #include "third_party/cros_system_api/dbus/service_constants.h" |
| 14 | 13 |
| 15 namespace chromeos { | 14 namespace chromeos { |
| 16 | 15 |
| 17 namespace { | 16 namespace { |
| 18 | 17 |
| 19 // Stream operator for logging vector<uint8>. | 18 // Stream operator for logging vector<uint8>. |
| (...skipping 10 matching lines...) Expand all Loading... |
| 30 | 29 |
| 31 BluetoothRemoteGattCharacteristicChromeOS:: | 30 BluetoothRemoteGattCharacteristicChromeOS:: |
| 32 BluetoothRemoteGattCharacteristicChromeOS( | 31 BluetoothRemoteGattCharacteristicChromeOS( |
| 33 BluetoothRemoteGattServiceChromeOS* service, | 32 BluetoothRemoteGattServiceChromeOS* service, |
| 34 const dbus::ObjectPath& object_path) | 33 const dbus::ObjectPath& object_path) |
| 35 : object_path_(object_path), | 34 : object_path_(object_path), |
| 36 service_(service), | 35 service_(service), |
| 37 weak_ptr_factory_(this) { | 36 weak_ptr_factory_(this) { |
| 38 VLOG(1) << "Creating remote GATT characteristic with identifier: " | 37 VLOG(1) << "Creating remote GATT characteristic with identifier: " |
| 39 << GetIdentifier() << ", UUID: " << GetUUID().canonical_value(); | 38 << GetIdentifier() << ", UUID: " << GetUUID().canonical_value(); |
| 39 DBusThreadManager::Get()->GetBluetoothGattCharacteristicClient()-> |
| 40 AddObserver(this); |
| 40 DBusThreadManager::Get()->GetBluetoothGattDescriptorClient()-> | 41 DBusThreadManager::Get()->GetBluetoothGattDescriptorClient()-> |
| 41 AddObserver(this); | 42 AddObserver(this); |
| 42 | 43 |
| 43 // Add all known GATT characteristic descriptors. | 44 // Add all known GATT characteristic descriptors. |
| 44 const std::vector<dbus::ObjectPath>& gatt_descs = | 45 const std::vector<dbus::ObjectPath>& gatt_descs = |
| 45 DBusThreadManager::Get()->GetBluetoothGattDescriptorClient()-> | 46 DBusThreadManager::Get()->GetBluetoothGattDescriptorClient()-> |
| 46 GetDescriptors(); | 47 GetDescriptors(); |
| 47 for (std::vector<dbus::ObjectPath>::const_iterator iter = gatt_descs.begin(); | 48 for (std::vector<dbus::ObjectPath>::const_iterator iter = gatt_descs.begin(); |
| 48 iter != gatt_descs.end(); ++iter) | 49 iter != gatt_descs.end(); ++iter) |
| 49 GattDescriptorAdded(*iter); | 50 GattDescriptorAdded(*iter); |
| 50 } | 51 } |
| 51 | 52 |
| 52 BluetoothRemoteGattCharacteristicChromeOS:: | 53 BluetoothRemoteGattCharacteristicChromeOS:: |
| 53 ~BluetoothRemoteGattCharacteristicChromeOS() { | 54 ~BluetoothRemoteGattCharacteristicChromeOS() { |
| 54 DBusThreadManager::Get()->GetBluetoothGattDescriptorClient()-> | 55 DBusThreadManager::Get()->GetBluetoothGattDescriptorClient()-> |
| 55 RemoveObserver(this); | 56 RemoveObserver(this); |
| 57 DBusThreadManager::Get()->GetBluetoothGattCharacteristicClient()-> |
| 58 RemoveObserver(this); |
| 56 | 59 |
| 57 // Clean up all the descriptors. There isn't much point in notifying service | 60 // Clean up all the descriptors. There isn't much point in notifying service |
| 58 // observers for each descriptor that gets removed, so just delete them. | 61 // observers for each descriptor that gets removed, so just delete them. |
| 59 for (DescriptorMap::iterator iter = descriptors_.begin(); | 62 for (DescriptorMap::iterator iter = descriptors_.begin(); |
| 60 iter != descriptors_.end(); ++iter) | 63 iter != descriptors_.end(); ++iter) |
| 61 delete iter->second; | 64 delete iter->second; |
| 62 } | 65 } |
| 63 | 66 |
| 64 std::string BluetoothRemoteGattCharacteristicChromeOS::GetIdentifier() const { | 67 std::string BluetoothRemoteGattCharacteristicChromeOS::GetIdentifier() const { |
| 65 return object_path_.value(); | 68 return object_path_.value(); |
| 66 } | 69 } |
| 67 | 70 |
| 68 device::BluetoothUUID | 71 device::BluetoothUUID |
| 69 BluetoothRemoteGattCharacteristicChromeOS::GetUUID() const { | 72 BluetoothRemoteGattCharacteristicChromeOS::GetUUID() const { |
| 70 BluetoothGattCharacteristicClient::Properties* properties = | 73 BluetoothGattCharacteristicClient::Properties* properties = |
| 71 DBusThreadManager::Get()->GetBluetoothGattCharacteristicClient()-> | 74 DBusThreadManager::Get()->GetBluetoothGattCharacteristicClient()-> |
| 72 GetProperties(object_path_); | 75 GetProperties(object_path_); |
| 73 DCHECK(properties); | 76 DCHECK(properties); |
| 74 return device::BluetoothUUID(properties->uuid.value()); | 77 return device::BluetoothUUID(properties->uuid.value()); |
| 75 } | 78 } |
| 76 | 79 |
| 77 bool BluetoothRemoteGattCharacteristicChromeOS::IsLocal() const { | 80 bool BluetoothRemoteGattCharacteristicChromeOS::IsLocal() const { |
| 78 return false; | 81 return false; |
| 79 } | 82 } |
| 80 | 83 |
| 81 const std::vector<uint8>& | 84 const std::vector<uint8>& |
| 82 BluetoothRemoteGattCharacteristicChromeOS::GetValue() const { | 85 BluetoothRemoteGattCharacteristicChromeOS::GetValue() const { |
| 83 BluetoothGattCharacteristicClient::Properties* properties = | 86 return cached_value_; |
| 84 DBusThreadManager::Get()->GetBluetoothGattCharacteristicClient()-> | |
| 85 GetProperties(object_path_); | |
| 86 DCHECK(properties); | |
| 87 return properties->value.value(); | |
| 88 } | 87 } |
| 89 | 88 |
| 90 device::BluetoothGattService* | 89 device::BluetoothGattService* |
| 91 BluetoothRemoteGattCharacteristicChromeOS::GetService() const { | 90 BluetoothRemoteGattCharacteristicChromeOS::GetService() const { |
| 92 return service_; | 91 return service_; |
| 93 } | 92 } |
| 94 | 93 |
| 95 device::BluetoothGattCharacteristic::Properties | 94 device::BluetoothGattCharacteristic::Properties |
| 96 BluetoothRemoteGattCharacteristicChromeOS::GetProperties() const { | 95 BluetoothRemoteGattCharacteristicChromeOS::GetProperties() const { |
| 97 BluetoothGattCharacteristicClient::Properties* properties = | 96 BluetoothGattCharacteristicClient::Properties* properties = |
| (...skipping 68 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 166 VLOG(1) << "Cannot update the value of a remote GATT characteristic."; | 165 VLOG(1) << "Cannot update the value of a remote GATT characteristic."; |
| 167 return false; | 166 return false; |
| 168 } | 167 } |
| 169 | 168 |
| 170 void BluetoothRemoteGattCharacteristicChromeOS::ReadRemoteCharacteristic( | 169 void BluetoothRemoteGattCharacteristicChromeOS::ReadRemoteCharacteristic( |
| 171 const ValueCallback& callback, | 170 const ValueCallback& callback, |
| 172 const ErrorCallback& error_callback) { | 171 const ErrorCallback& error_callback) { |
| 173 VLOG(1) << "Sending GATT characteristic read request to characteristic: " | 172 VLOG(1) << "Sending GATT characteristic read request to characteristic: " |
| 174 << GetIdentifier() << ", UUID: " << GetUUID().canonical_value() | 173 << GetIdentifier() << ", UUID: " << GetUUID().canonical_value() |
| 175 << "."; | 174 << "."; |
| 176 BluetoothGattCharacteristicClient::Properties* properties = | 175 |
| 177 DBusThreadManager::Get()->GetBluetoothGattCharacteristicClient()-> | 176 DBusThreadManager::Get()->GetBluetoothGattCharacteristicClient()->ReadValue( |
| 178 GetProperties(object_path_); | 177 object_path_, |
| 179 DCHECK(properties); | 178 base::Bind(&BluetoothRemoteGattCharacteristicChromeOS::OnValueSuccess, |
| 180 properties->value.Get( | |
| 181 base::Bind(&BluetoothRemoteGattCharacteristicChromeOS::OnGetValue, | |
| 182 weak_ptr_factory_.GetWeakPtr(), | 179 weak_ptr_factory_.GetWeakPtr(), |
| 183 callback, error_callback)); | 180 callback), |
| 181 base::Bind(&BluetoothRemoteGattCharacteristicChromeOS::OnError, |
| 182 weak_ptr_factory_.GetWeakPtr(), |
| 183 error_callback)); |
| 184 } | 184 } |
| 185 | 185 |
| 186 void BluetoothRemoteGattCharacteristicChromeOS::WriteRemoteCharacteristic( | 186 void BluetoothRemoteGattCharacteristicChromeOS::WriteRemoteCharacteristic( |
| 187 const std::vector<uint8>& new_value, | 187 const std::vector<uint8>& new_value, |
| 188 const base::Closure& callback, | 188 const base::Closure& callback, |
| 189 const ErrorCallback& error_callback) { | 189 const ErrorCallback& error_callback) { |
| 190 VLOG(1) << "Sending GATT characteristic write request to characteristic: " | 190 VLOG(1) << "Sending GATT characteristic write request to characteristic: " |
| 191 << GetIdentifier() << ", UUID: " << GetUUID().canonical_value() | 191 << GetIdentifier() << ", UUID: " << GetUUID().canonical_value() |
| 192 << ", with value: " << new_value << "."; | 192 << ", with value: " << new_value << "."; |
| 193 | 193 |
| 194 // Permission and bonding are handled by BlueZ so no need check it here. | 194 DBusThreadManager::Get()->GetBluetoothGattCharacteristicClient()->WriteValue( |
| 195 if (new_value.empty()) { | 195 object_path_, |
| 196 VLOG(1) << "Nothing to write."; | 196 new_value, |
| 197 error_callback.Run(); | 197 callback, |
| 198 base::Bind(&BluetoothRemoteGattCharacteristicChromeOS::OnError, |
| 199 weak_ptr_factory_.GetWeakPtr(), |
| 200 error_callback)); |
| 201 } |
| 202 |
| 203 void BluetoothRemoteGattCharacteristicChromeOS::GattCharacteristicValueUpdated( |
| 204 const dbus::ObjectPath& object_path, |
| 205 const std::vector<uint8>& value) { |
| 206 if (object_path != object_path_) |
| 198 return; | 207 return; |
| 199 } | |
| 200 | 208 |
| 201 BluetoothGattCharacteristicClient::Properties* properties = | 209 cached_value_ = value; |
| 202 DBusThreadManager::Get()->GetBluetoothGattCharacteristicClient()-> | 210 |
| 203 GetProperties(object_path_); | 211 VLOG(1) << "GATT characteristic value has changed: " << object_path.value() |
| 204 DCHECK(properties); | 212 << ": " << value; |
| 205 properties->value.Set( | 213 DCHECK(service_); |
| 206 new_value, | 214 service_->NotifyCharacteristicValueChanged(this, value); |
| 207 base::Bind(&BluetoothRemoteGattCharacteristicChromeOS::OnSetValue, | |
| 208 weak_ptr_factory_.GetWeakPtr(), | |
| 209 callback, error_callback)); | |
| 210 } | 215 } |
| 211 | 216 |
| 212 void BluetoothRemoteGattCharacteristicChromeOS::GattDescriptorAdded( | 217 void BluetoothRemoteGattCharacteristicChromeOS::GattDescriptorAdded( |
| 213 const dbus::ObjectPath& object_path) { | 218 const dbus::ObjectPath& object_path) { |
| 214 if (descriptors_.find(object_path) != descriptors_.end()) { | 219 if (descriptors_.find(object_path) != descriptors_.end()) { |
| 215 VLOG(1) << "Remote GATT characteristic descriptor already exists: " | 220 VLOG(1) << "Remote GATT characteristic descriptor already exists: " |
| 216 << object_path.value(); | 221 << object_path.value(); |
| 217 return; | 222 return; |
| 218 } | 223 } |
| 219 | 224 |
| (...skipping 60 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 280 | 285 |
| 281 VLOG(1) << "GATT descriptor property changed: " << object_path.value() | 286 VLOG(1) << "GATT descriptor property changed: " << object_path.value() |
| 282 << ", property: " << property_name; | 287 << ", property: " << property_name; |
| 283 | 288 |
| 284 DCHECK(service_); | 289 DCHECK(service_); |
| 285 | 290 |
| 286 service_->NotifyDescriptorValueChanged( | 291 service_->NotifyDescriptorValueChanged( |
| 287 this, iter->second, properties->value.value()); | 292 this, iter->second, properties->value.value()); |
| 288 } | 293 } |
| 289 | 294 |
| 290 void BluetoothRemoteGattCharacteristicChromeOS::OnGetValue( | 295 void BluetoothRemoteGattCharacteristicChromeOS::OnValueSuccess( |
| 291 const ValueCallback& callback, | 296 const ValueCallback& callback, |
| 292 const ErrorCallback& error_callback, | 297 const std::vector<uint8>& value) { |
| 293 bool success) { | 298 VLOG(1) << "Characteristic value read: " << value; |
| 294 if (!success) { | 299 cached_value_ = value; |
| 295 VLOG(1) << "Failed to read the value from the remote characteristic."; | |
| 296 error_callback.Run(); | |
| 297 return; | |
| 298 } | |
| 299 | 300 |
| 300 VLOG(1) << "Read value of remote characteristic."; | 301 DCHECK(service_); |
| 301 BluetoothGattCharacteristicClient::Properties* properties = | 302 service_->NotifyCharacteristicValueChanged(this, cached_value_); |
| 302 DBusThreadManager::Get()->GetBluetoothGattCharacteristicClient()-> | 303 |
| 303 GetProperties(object_path_); | 304 callback.Run(value); |
| 304 DCHECK(properties); | |
| 305 callback.Run(properties->value.value()); | |
| 306 } | 305 } |
| 307 | 306 |
| 308 void BluetoothRemoteGattCharacteristicChromeOS::OnSetValue( | 307 void BluetoothRemoteGattCharacteristicChromeOS::OnError( |
| 309 const base::Closure& callback, | |
| 310 const ErrorCallback& error_callback, | 308 const ErrorCallback& error_callback, |
| 311 bool success) { | 309 const std::string& error_name, |
| 312 if (!success) { | 310 const std::string& error_message) { |
| 313 VLOG(1) << "Failed to write the value of remote characteristic."; | 311 VLOG(1) << "Operation failed: " << error_name << ", message: " |
| 314 error_callback.Run(); | 312 << error_message; |
| 315 return; | 313 error_callback.Run(); |
| 316 } | |
| 317 | |
| 318 VLOG(1) << "Wrote value of remote characteristic."; | |
| 319 callback.Run(); | |
| 320 } | 314 } |
| 321 | 315 |
| 322 } // namespace chromeos | 316 } // namespace chromeos |
| OLD | NEW |