OLD | NEW |
1 // Copyright 2016 The Chromium Authors. All rights reserved. | 1 // Copyright 2016 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/bluez/bluetooth_remote_gatt_characteristic_bluez.h" | 5 #include "device/bluetooth/bluez/bluetooth_remote_gatt_characteristic_bluez.h" |
6 | 6 |
7 #include <iterator> | 7 #include <iterator> |
8 #include <limits> | 8 #include <limits> |
9 | 9 |
10 #include "base/bind.h" | 10 #include "base/bind.h" |
11 #include "base/callback.h" | 11 #include "base/callback.h" |
12 #include "base/logging.h" | 12 #include "base/logging.h" |
13 #include "base/strings/stringprintf.h" | 13 #include "base/strings/stringprintf.h" |
14 #include "dbus/property.h" | 14 #include "dbus/property.h" |
15 #include "device/bluetooth/bluetooth_device.h" | 15 #include "device/bluetooth/bluetooth_device.h" |
16 #include "device/bluetooth/bluetooth_gatt_characteristic.h" | 16 #include "device/bluetooth/bluetooth_gatt_characteristic.h" |
17 #include "device/bluetooth/bluetooth_gatt_notify_session.h" | |
18 #include "device/bluetooth/bluetooth_gatt_service.h" | 17 #include "device/bluetooth/bluetooth_gatt_service.h" |
19 #include "device/bluetooth/bluez/bluetooth_adapter_bluez.h" | 18 #include "device/bluetooth/bluez/bluetooth_adapter_bluez.h" |
| 19 #include "device/bluetooth/bluez/bluetooth_gatt_notify_session_bluez.h" |
20 #include "device/bluetooth/bluez/bluetooth_remote_gatt_descriptor_bluez.h" | 20 #include "device/bluetooth/bluez/bluetooth_remote_gatt_descriptor_bluez.h" |
21 #include "device/bluetooth/bluez/bluetooth_remote_gatt_service_bluez.h" | 21 #include "device/bluetooth/bluez/bluetooth_remote_gatt_service_bluez.h" |
22 #include "device/bluetooth/dbus/bluetooth_gatt_characteristic_client.h" | 22 #include "device/bluetooth/dbus/bluetooth_gatt_characteristic_client.h" |
23 #include "device/bluetooth/dbus/bluez_dbus_manager.h" | 23 #include "device/bluetooth/dbus/bluez_dbus_manager.h" |
24 #include "third_party/cros_system_api/dbus/service_constants.h" | 24 #include "third_party/cros_system_api/dbus/service_constants.h" |
25 | 25 |
26 namespace bluez { | 26 namespace bluez { |
27 | 27 |
28 namespace { | 28 namespace { |
29 | 29 |
(...skipping 46 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
76 delete iter->second; | 76 delete iter->second; |
77 | 77 |
78 // Report an error for all pending calls to StartNotifySession. | 78 // Report an error for all pending calls to StartNotifySession. |
79 while (!pending_start_notify_calls_.empty()) { | 79 while (!pending_start_notify_calls_.empty()) { |
80 PendingStartNotifyCall callbacks = pending_start_notify_calls_.front(); | 80 PendingStartNotifyCall callbacks = pending_start_notify_calls_.front(); |
81 pending_start_notify_calls_.pop(); | 81 pending_start_notify_calls_.pop(); |
82 callbacks.second.Run(device::BluetoothRemoteGattService::GATT_ERROR_FAILED); | 82 callbacks.second.Run(device::BluetoothRemoteGattService::GATT_ERROR_FAILED); |
83 } | 83 } |
84 } | 84 } |
85 | 85 |
86 void BluetoothRemoteGattCharacteristicBlueZ::StopNotifySession( | |
87 device::BluetoothGattNotifySession* session, | |
88 const base::Closure& callback) { | |
89 VLOG(1) << __func__; | |
90 | |
91 if (num_notify_sessions_ > 1) { | |
92 DCHECK(!notify_call_pending_); | |
93 --num_notify_sessions_; | |
94 callback.Run(); | |
95 return; | |
96 } | |
97 | |
98 // Notifications may have stopped outside our control. If the characteristic | |
99 // is no longer notifying, return success. | |
100 if (!IsNotifying()) { | |
101 num_notify_sessions_ = 0; | |
102 callback.Run(); | |
103 return; | |
104 } | |
105 | |
106 if (notify_call_pending_ || num_notify_sessions_ == 0) { | |
107 callback.Run(); | |
108 return; | |
109 } | |
110 | |
111 DCHECK(num_notify_sessions_ == 1); | |
112 notify_call_pending_ = true; | |
113 bluez::BluezDBusManager::Get() | |
114 ->GetBluetoothGattCharacteristicClient() | |
115 ->StopNotify( | |
116 object_path(), | |
117 base::Bind( | |
118 &BluetoothRemoteGattCharacteristicBlueZ::OnStopNotifySuccess, | |
119 weak_ptr_factory_.GetWeakPtr(), callback), | |
120 base::Bind(&BluetoothRemoteGattCharacteristicBlueZ::OnStopNotifyError, | |
121 weak_ptr_factory_.GetWeakPtr(), callback)); | |
122 } | |
123 | |
124 device::BluetoothUUID BluetoothRemoteGattCharacteristicBlueZ::GetUUID() const { | 86 device::BluetoothUUID BluetoothRemoteGattCharacteristicBlueZ::GetUUID() const { |
125 bluez::BluetoothGattCharacteristicClient::Properties* properties = | 87 bluez::BluetoothGattCharacteristicClient::Properties* properties = |
126 bluez::BluezDBusManager::Get() | 88 bluez::BluezDBusManager::Get() |
127 ->GetBluetoothGattCharacteristicClient() | 89 ->GetBluetoothGattCharacteristicClient() |
128 ->GetProperties(object_path()); | 90 ->GetProperties(object_path()); |
129 DCHECK(properties); | 91 DCHECK(properties); |
130 return device::BluetoothUUID(properties->uuid.value()); | 92 return device::BluetoothUUID(properties->uuid.value()); |
131 } | 93 } |
132 | 94 |
133 device::BluetoothRemoteGattCharacteristic::Properties | 95 device::BluetoothRemoteGattCharacteristic::Properties |
(...skipping 103 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
237 error_callback.Run( | 199 error_callback.Run( |
238 device::BluetoothRemoteGattService::GATT_ERROR_FAILED); | 200 device::BluetoothRemoteGattService::GATT_ERROR_FAILED); |
239 return; | 201 return; |
240 } | 202 } |
241 | 203 |
242 ++num_notify_sessions_; | 204 ++num_notify_sessions_; |
243 DCHECK(service_); | 205 DCHECK(service_); |
244 DCHECK(service_->GetAdapter()); | 206 DCHECK(service_->GetAdapter()); |
245 DCHECK(service_->GetDevice()); | 207 DCHECK(service_->GetDevice()); |
246 std::unique_ptr<device::BluetoothGattNotifySession> session( | 208 std::unique_ptr<device::BluetoothGattNotifySession> session( |
247 new device::BluetoothGattNotifySession( | 209 new BluetoothGattNotifySessionBlueZ( |
248 weak_ptr_factory_.GetWeakPtr())); | 210 service_->GetAdapter(), service_->GetDevice()->GetAddress(), |
| 211 service_->GetIdentifier(), GetIdentifier(), object_path())); |
249 callback.Run(std::move(session)); | 212 callback.Run(std::move(session)); |
250 return; | 213 return; |
251 } | 214 } |
252 | 215 |
253 num_notify_sessions_ = 0; | 216 num_notify_sessions_ = 0; |
254 } | 217 } |
255 | 218 |
256 // Queue the callbacks if there is a pending call to bluetoothd. | 219 // Queue the callbacks if there is a pending call to bluetoothd. |
257 if (notify_call_pending_) { | 220 if (notify_call_pending_) { |
258 pending_start_notify_calls_.push(std::make_pair(callback, error_callback)); | 221 pending_start_notify_calls_.push(std::make_pair(callback, error_callback)); |
(...skipping 35 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
294 << GetIdentifier() << ", UUID: " << GetUUID().canonical_value() | 257 << GetIdentifier() << ", UUID: " << GetUUID().canonical_value() |
295 << ", with value: " << new_value << "."; | 258 << ", with value: " << new_value << "."; |
296 | 259 |
297 bluez::BluezDBusManager::Get() | 260 bluez::BluezDBusManager::Get() |
298 ->GetBluetoothGattCharacteristicClient() | 261 ->GetBluetoothGattCharacteristicClient() |
299 ->WriteValue(object_path(), new_value, callback, | 262 ->WriteValue(object_path(), new_value, callback, |
300 base::Bind(&BluetoothRemoteGattCharacteristicBlueZ::OnError, | 263 base::Bind(&BluetoothRemoteGattCharacteristicBlueZ::OnError, |
301 weak_ptr_factory_.GetWeakPtr(), error_callback)); | 264 weak_ptr_factory_.GetWeakPtr(), error_callback)); |
302 } | 265 } |
303 | 266 |
304 void BluetoothRemoteGattCharacteristicBlueZ::SubscribeToNotifications( | 267 void BluetoothRemoteGattCharacteristicBlueZ::RemoveNotifySession( |
305 device::BluetoothRemoteGattDescriptor* ccc_descriptor, | 268 const base::Closure& callback) { |
306 const base::Closure& callback, | 269 VLOG(1) << __func__; |
307 const ErrorCallback& error_callback) { | |
308 // TODO(http://crbug.com/636275): Implement this method | |
309 NOTIMPLEMENTED(); | |
310 } | |
311 | 270 |
312 void BluetoothRemoteGattCharacteristicBlueZ::UnsubscribeFromNotifications( | 271 if (num_notify_sessions_ > 1) { |
313 device::BluetoothRemoteGattDescriptor* ccc_descriptor, | 272 DCHECK(!notify_call_pending_); |
314 const base::Closure& callback, | 273 --num_notify_sessions_; |
315 const ErrorCallback& error_callback) { | 274 callback.Run(); |
316 // TODO(http://crbug.com/636275): Implement this method | 275 return; |
317 NOTIMPLEMENTED(); | 276 } |
| 277 |
| 278 // Notifications may have stopped outside our control. If the characteristic |
| 279 // is no longer notifying, return success. |
| 280 if (!IsNotifying()) { |
| 281 num_notify_sessions_ = 0; |
| 282 callback.Run(); |
| 283 return; |
| 284 } |
| 285 |
| 286 if (notify_call_pending_ || num_notify_sessions_ == 0) { |
| 287 callback.Run(); |
| 288 return; |
| 289 } |
| 290 |
| 291 DCHECK(num_notify_sessions_ == 1); |
| 292 notify_call_pending_ = true; |
| 293 bluez::BluezDBusManager::Get() |
| 294 ->GetBluetoothGattCharacteristicClient() |
| 295 ->StopNotify( |
| 296 object_path(), |
| 297 base::Bind( |
| 298 &BluetoothRemoteGattCharacteristicBlueZ::OnStopNotifySuccess, |
| 299 weak_ptr_factory_.GetWeakPtr(), callback), |
| 300 base::Bind(&BluetoothRemoteGattCharacteristicBlueZ::OnStopNotifyError, |
| 301 weak_ptr_factory_.GetWeakPtr(), callback)); |
318 } | 302 } |
319 | 303 |
320 void BluetoothRemoteGattCharacteristicBlueZ::GattDescriptorAdded( | 304 void BluetoothRemoteGattCharacteristicBlueZ::GattDescriptorAdded( |
321 const dbus::ObjectPath& object_path) { | 305 const dbus::ObjectPath& object_path) { |
322 if (descriptors_.find(object_path) != descriptors_.end()) { | 306 if (descriptors_.find(object_path) != descriptors_.end()) { |
323 VLOG(1) << "Remote GATT characteristic descriptor already exists: " | 307 VLOG(1) << "Remote GATT characteristic descriptor already exists: " |
324 << object_path.value(); | 308 << object_path.value(); |
325 return; | 309 return; |
326 } | 310 } |
327 | 311 |
(...skipping 75 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
403 DCHECK(num_notify_sessions_ == 0); | 387 DCHECK(num_notify_sessions_ == 0); |
404 DCHECK(notify_call_pending_); | 388 DCHECK(notify_call_pending_); |
405 | 389 |
406 ++num_notify_sessions_; | 390 ++num_notify_sessions_; |
407 notify_call_pending_ = false; | 391 notify_call_pending_ = false; |
408 | 392 |
409 // Invoke the queued callbacks for this operation. | 393 // Invoke the queued callbacks for this operation. |
410 DCHECK(service_); | 394 DCHECK(service_); |
411 DCHECK(service_->GetDevice()); | 395 DCHECK(service_->GetDevice()); |
412 std::unique_ptr<device::BluetoothGattNotifySession> session( | 396 std::unique_ptr<device::BluetoothGattNotifySession> session( |
413 new device::BluetoothGattNotifySession(weak_ptr_factory_.GetWeakPtr())); | 397 new BluetoothGattNotifySessionBlueZ( |
| 398 service_->GetAdapter(), service_->GetDevice()->GetAddress(), |
| 399 service_->GetIdentifier(), GetIdentifier(), object_path())); |
414 callback.Run(std::move(session)); | 400 callback.Run(std::move(session)); |
415 | 401 |
416 ProcessStartNotifyQueue(); | 402 ProcessStartNotifyQueue(); |
417 } | 403 } |
418 | 404 |
419 void BluetoothRemoteGattCharacteristicBlueZ::OnStartNotifyError( | 405 void BluetoothRemoteGattCharacteristicBlueZ::OnStartNotifyError( |
420 const ErrorCallback& error_callback, | 406 const ErrorCallback& error_callback, |
421 const std::string& error_name, | 407 const std::string& error_name, |
422 const std::string& error_message) { | 408 const std::string& error_message) { |
423 VLOG(1) << "Failed to start notifications from characteristic: " | 409 VLOG(1) << "Failed to start notifications from characteristic: " |
(...skipping 46 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
470 const ErrorCallback& error_callback, | 456 const ErrorCallback& error_callback, |
471 const std::string& error_name, | 457 const std::string& error_name, |
472 const std::string& error_message) { | 458 const std::string& error_message) { |
473 VLOG(1) << "Operation failed: " << error_name | 459 VLOG(1) << "Operation failed: " << error_name |
474 << ", message: " << error_message; | 460 << ", message: " << error_message; |
475 error_callback.Run( | 461 error_callback.Run( |
476 BluetoothGattServiceBlueZ::DBusErrorToServiceError(error_name)); | 462 BluetoothGattServiceBlueZ::DBusErrorToServiceError(error_name)); |
477 } | 463 } |
478 | 464 |
479 } // namespace bluez | 465 } // namespace bluez |
OLD | NEW |