Chromium Code Reviews| Index: components/arc/bluetooth/arc_bluetooth_bridge.cc |
| diff --git a/components/arc/bluetooth/arc_bluetooth_bridge.cc b/components/arc/bluetooth/arc_bluetooth_bridge.cc |
| index 4c5637a916ed6a6b7ea58c9e586cecffed959aaf..9489db9d4a6136b0be5a0aa3c49e92d581e76f5d 100644 |
| --- a/components/arc/bluetooth/arc_bluetooth_bridge.cc |
| +++ b/components/arc/bluetooth/arc_bluetooth_bridge.cc |
| @@ -9,6 +9,7 @@ |
| #include <iomanip> |
| #include <string> |
| +#include <utility> |
| #include "base/bind.h" |
| #include "base/logging.h" |
| @@ -49,6 +50,7 @@ using device::BluetoothUUID; |
| namespace { |
| constexpr int32_t kMinBtleVersion = 1; |
| constexpr int32_t kMinBtleNotifyVersion = 2; |
| +constexpr int32_t kMinGattServerVersion = 3; |
| constexpr uint32_t kGattReadPermission = |
| BluetoothGattCharacteristic::Permission::PERMISSION_READ | |
| BluetoothGattCharacteristic::Permission::PERMISSION_READ_ENCRYPTED | |
| @@ -59,6 +61,7 @@ constexpr uint32_t kGattWritePermission = |
| BluetoothGattCharacteristic::Permission::PERMISSION_WRITE_ENCRYPTED | |
| BluetoothGattCharacteristic::Permission:: |
| PERMISSION_WRITE_ENCRYPTED_AUTHENTICATED; |
| +constexpr int32_t kInvalidGattAttributeHandle = -1; |
| } // namespace |
| namespace arc { |
| @@ -751,10 +754,10 @@ int ArcBluetoothBridge::ConvertGattIdentifierToId( |
| // Create GattDBElement and fill in common data for |
| // Gatt Service/Characteristic/Descriptor. |
| -template <class T> |
| +template <class RemoteGattObjectT> |
| mojom::BluetoothGattDBElementPtr ArcBluetoothBridge::CreateGattDBElement( |
| const mojom::BluetoothGattDBAttributeType type, |
| - const T* gattObject) const { |
| + const RemoteGattObjectT* gattObject) const { |
| mojom::BluetoothGattDBElementPtr element = |
| mojom::BluetoothGattDBElement::New(); |
| element->type = type; |
| @@ -813,12 +816,13 @@ void ArcBluetoothBridge::GetGattDB(mojom::BluetoothAddressPtr remote_addr) { |
| } |
| // Find Gatt Service/Characteristic/Descriptor from std::vector from UUID. |
| -template <class T> |
| -T* ArcBluetoothBridge::FindGattObjectFromUuid( |
| - const std::vector<T*> gatt_objs, |
| +template <class RemoteGattObjectT> |
| +RemoteGattObjectT* ArcBluetoothBridge::FindGattObjectFromUuid( |
| + const std::vector<RemoteGattObjectT*> gatt_objs, |
| const device::BluetoothUUID uuid) const { |
| - auto it = std::find_if(gatt_objs.begin(), gatt_objs.end(), |
| - [&](T* obj) { return obj->GetUUID() == uuid; }); |
| + auto it = std::find_if( |
| + gatt_objs.begin(), gatt_objs.end(), |
| + [&](RemoteGattObjectT* obj) { return obj->GetUUID() == uuid; }); |
| if (it == gatt_objs.end()) |
| return nullptr; |
| return *it; |
| @@ -861,6 +865,19 @@ BluetoothRemoteGattDescriptor* ArcBluetoothBridge::FindGattDescriptor( |
| characteristic->GetDescriptors(), desc_id->uuid.To<BluetoothUUID>()); |
| } |
| +// Common callback function for Gatt operation that only need to report |
|
palmer
2016/07/16 00:45:13
Comment style:
Common callback for GATT operation
puthik_chromium
2016/07/18 21:30:13
Done.
|
| +// Gatt status back to Android. |
| +void ArcBluetoothBridge::OnGattOperationDone( |
| + const GattStatusCallback& callback) const { |
| + callback.Run(mojom::BluetoothGattStatus::GATT_SUCCESS); |
| +} |
| + |
| +void ArcBluetoothBridge::OnGattOperationError( |
| + const GattStatusCallback& callback, |
| + BluetoothGattService::GattErrorCode error_code) const { |
| + callback.Run(mojo::ConvertTo<mojom::BluetoothGattStatus>(error_code)); |
| +} |
| + |
| // Same callback for both ReadGattCharacteristic and ReadGattDescriptor |
| void ArcBluetoothBridge::OnGattReadDone( |
| const GattReadCallback& callback, |
| @@ -881,18 +898,6 @@ void ArcBluetoothBridge::OnGattReadError( |
| callback.Run(std::move(gattValue)); |
| } |
| -// Same callback for both WriteGattCharacteristic and WriteGattDescriptor |
| -void ArcBluetoothBridge::OnGattWriteDone( |
| - const GattWriteCallback& callback) const { |
| - callback.Run(mojom::BluetoothGattStatus::GATT_SUCCESS); |
| -} |
| - |
| -void ArcBluetoothBridge::OnGattWriteError( |
| - const GattWriteCallback& callback, |
| - BluetoothGattService::GattErrorCode error_code) const { |
| - callback.Run(mojo::ConvertTo<mojom::BluetoothGattStatus>(error_code)); |
| -} |
| - |
| void ArcBluetoothBridge::ReadGattCharacteristic( |
| mojom::BluetoothAddressPtr remote_addr, |
| mojom::BluetoothGattServiceIDPtr service_id, |
| @@ -923,9 +928,9 @@ void ArcBluetoothBridge::WriteGattCharacteristic( |
| characteristic->WriteRemoteCharacteristic( |
| value->value.To<std::vector<uint8_t>>(), |
| - base::Bind(&ArcBluetoothBridge::OnGattWriteDone, |
| + base::Bind(&ArcBluetoothBridge::OnGattOperationDone, |
| weak_factory_.GetWeakPtr(), callback), |
| - base::Bind(&ArcBluetoothBridge::OnGattWriteError, |
| + base::Bind(&ArcBluetoothBridge::OnGattOperationError, |
| weak_factory_.GetWeakPtr(), callback)); |
| } |
| @@ -970,15 +975,15 @@ void ArcBluetoothBridge::WriteGattDescriptor( |
| // TODO(http://crbug.com/622832) |
| if (descriptor->GetUUID() == |
| BluetoothGattDescriptor::ClientCharacteristicConfigurationUuid()) { |
| - OnGattWriteDone(callback); |
| + OnGattOperationDone(callback); |
| return; |
| } |
| descriptor->WriteRemoteDescriptor( |
| value->value.To<std::vector<uint8_t>>(), |
| - base::Bind(&ArcBluetoothBridge::OnGattWriteDone, |
| + base::Bind(&ArcBluetoothBridge::OnGattOperationDone, |
| weak_factory_.GetWeakPtr(), callback), |
| - base::Bind(&ArcBluetoothBridge::OnGattWriteError, |
| + base::Bind(&ArcBluetoothBridge::OnGattOperationError, |
| weak_factory_.GetWeakPtr(), callback)); |
| } |
| @@ -990,17 +995,6 @@ void ArcBluetoothBridge::OnGattNotifyStartDone( |
| callback.Run(mojom::BluetoothGattStatus::GATT_SUCCESS); |
| } |
| -void ArcBluetoothBridge::OnGattNotifyStartError( |
| - const RegisterForGattNotificationCallback& callback, |
| - BluetoothGattService::GattErrorCode error_code) const { |
| - callback.Run(mojo::ConvertTo<mojom::BluetoothGattStatus>(error_code)); |
| -} |
| - |
| -void ArcBluetoothBridge::OnGattNotifyStopDone( |
| - const DeregisterForGattNotificationCallback& callback) const { |
| - callback.Run(mojom::BluetoothGattStatus::GATT_SUCCESS); |
| -} |
| - |
| void ArcBluetoothBridge::RegisterForGattNotification( |
| mojom::BluetoothAddressPtr remote_addr, |
| mojom::BluetoothGattServiceIDPtr service_id, |
| @@ -1023,7 +1017,7 @@ void ArcBluetoothBridge::RegisterForGattNotification( |
| base::Bind(&ArcBluetoothBridge::OnGattNotifyStartDone, |
| weak_factory_.GetWeakPtr(), callback, |
| characteristic->GetIdentifier()), |
| - base::Bind(&ArcBluetoothBridge::OnGattNotifyStartError, |
| + base::Bind(&ArcBluetoothBridge::OnGattOperationError, |
| weak_factory_.GetWeakPtr(), callback)); |
| } |
| @@ -1049,7 +1043,7 @@ void ArcBluetoothBridge::DeregisterForGattNotification( |
| std::unique_ptr<BluetoothGattNotifySession> notify = |
| std::move(notification_session_[char_id_str]); |
| notification_session_.erase(char_id_str); |
| - notify->Stop(base::Bind(&ArcBluetoothBridge::OnGattNotifyStopDone, |
| + notify->Stop(base::Bind(&ArcBluetoothBridge::OnGattOperationDone, |
| weak_factory_.GetWeakPtr(), callback)); |
| } |
| @@ -1062,30 +1056,102 @@ void ArcBluetoothBridge::ReadRemoteRssi( |
| callback.Run(rssi); |
| } |
| +template <class LocalGattObjectT> |
| +int32_t ArcBluetoothBridge::CreateGattAttributeHandle( |
| + LocalGattObjectT* gatt_obj) { |
| + if (!gatt_obj) |
| + return kInvalidGattAttributeHandle; |
| + gatt_server_obj_handle++; |
| + std::string identifier = gatt_obj->GetIdentifier(); |
| + gatt_identifier_[gatt_server_obj_handle] = identifier; |
|
palmer
2016/07/16 00:45:13
Nit: You could save a line and write:
gatt_iden
puthik_chromium
2016/07/18 21:30:13
We will reuse |identifier| in the next patch when
|
| + return gatt_server_obj_handle; |
| +} |
| + |
| void ArcBluetoothBridge::AddService(mojom::BluetoothGattServiceIDPtr service_id, |
| int32_t num_handles, |
| - const AddServiceCallback& callback) {} |
| + const AddServiceCallback& callback) { |
| + base::WeakPtr<BluetoothLocalGattService> service = |
| + BluetoothLocalGattService::Create( |
| + bluetooth_adapter_.get(), service_id->id->uuid.To<BluetoothUUID>(), |
| + service_id->is_primary, nullptr /*included_service */, |
| + this /* delegate*/); |
| + callback.Run( |
| + CreateGattAttributeHandle<BluetoothLocalGattService>(service.get())); |
| +} |
| void ArcBluetoothBridge::AddCharacteristic( |
| int32_t service_handle, |
| mojom::BluetoothUUIDPtr uuid, |
| int32_t properties, |
| int32_t permissions, |
| - const AddCharacteristicCallback& callback) {} |
| + const AddCharacteristicCallback& callback) { |
| + base::WeakPtr<BluetoothLocalGattCharacteristic> characteristic = |
| + BluetoothLocalGattCharacteristic::Create( |
| + uuid.To<BluetoothUUID>(), properties, permissions, |
| + bluetooth_adapter_->GetGattService(gatt_identifier_[service_handle])); |
| + int32_t characteristic_handle = |
| + CreateGattAttributeHandle<BluetoothLocalGattCharacteristic>( |
| + characteristic.get()); |
| + last_characteristic_[service_handle] = characteristic_handle; |
| + callback.Run(characteristic_handle); |
| +} |
| void ArcBluetoothBridge::AddDescriptor(int32_t service_handle, |
| mojom::BluetoothUUIDPtr uuid, |
| int32_t permissions, |
| - const AddDescriptorCallback& callback) {} |
| + const AddDescriptorCallback& callback) { |
| + // Chrome automatically add CCC Descriptor to a characteristic when needed. |
|
palmer
2016/07/16 00:45:13
Nit: Check your grammar and punctuation in comment
puthik_chromium
2016/07/18 21:30:12
Done.
|
| + // So we will just generate bogus handle for android. |
| + if (uuid.To<BluetoothUUID>() == |
| + BluetoothGattDescriptor::ClientCharacteristicConfigurationUuid()) { |
| + gatt_server_obj_handle++; |
| + callback.Run(gatt_server_obj_handle); |
| + return; |
| + } |
| + |
| + BluetoothLocalGattService* service = |
| + bluetooth_adapter_->GetGattService(gatt_identifier_[service_handle]); |
| + // Since Android API does not give information which characteristic is the |
|
palmer
2016/07/16 00:45:13
Comment style:
Since the Android API does not giv
puthik_chromium
2016/07/18 21:30:12
I accidentally deleted the last line of comment.
D
|
| + // parent of the new descriptor. We will just assume that it would be the |
| + // last characteristic that was added to the given service. This matches the |
|
rkc
2016/07/16 00:37:29
Incomplete comment?
Please add the Android source
puthik_chromium
2016/07/18 21:30:12
I accidentally deleted the last line of comment.
D
|
| + BluetoothLocalGattCharacteristic* characteristic = service->GetCharacteristic( |
| + gatt_identifier_[last_characteristic_[service_handle]]); |
| + |
| + base::WeakPtr<BluetoothLocalGattDescriptor> descriptor = |
| + BluetoothLocalGattDescriptor::Create(uuid.To<BluetoothUUID>(), |
| + permissions, characteristic); |
| + callback.Run(CreateGattAttributeHandle<BluetoothLocalGattDescriptor>( |
| + descriptor.get())); |
| +} |
| void ArcBluetoothBridge::StartService(int32_t service_handle, |
| - const StartServiceCallback& callback) {} |
| + const StartServiceCallback& callback) { |
| + BluetoothLocalGattService* service = |
| + bluetooth_adapter_->GetGattService(gatt_identifier_[service_handle]); |
| + service->Register(base::Bind(&ArcBluetoothBridge::OnGattOperationDone, |
| + weak_factory_.GetWeakPtr(), callback), |
| + base::Bind(&ArcBluetoothBridge::OnGattOperationError, |
| + weak_factory_.GetWeakPtr(), callback)); |
| +} |
| void ArcBluetoothBridge::StopService(int32_t service_handle, |
| - const StopServiceCallback& callback) {} |
| + const StopServiceCallback& callback) { |
| + BluetoothLocalGattService* service = |
| + bluetooth_adapter_->GetGattService(gatt_identifier_[service_handle]); |
| + service->Unregister(base::Bind(&ArcBluetoothBridge::OnGattOperationDone, |
| + weak_factory_.GetWeakPtr(), callback), |
| + base::Bind(&ArcBluetoothBridge::OnGattOperationError, |
| + weak_factory_.GetWeakPtr(), callback)); |
| +} |
| void ArcBluetoothBridge::DeleteService(int32_t service_handle, |
| - const DeleteServiceCallback& callback) {} |
| + const DeleteServiceCallback& callback) { |
| + BluetoothLocalGattService* service = |
| + bluetooth_adapter_->GetGattService(gatt_identifier_[service_handle]); |
| + service->Delete(); |
| + gatt_identifier_.erase(service_handle); |
| + OnGattOperationDone(callback); |
| +} |
| void ArcBluetoothBridge::SendIndication( |
| int32_t attribute_handle, |