Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(628)

Side by Side Diff: components/arc/bluetooth/arc_bluetooth_bridge.cc

Issue 2149713002: arc: bluetooth: Add SDP host side support (Closed) Base URL: https://chromium.googlesource.com/chromium/src.git@master
Patch Set: Remove unused includes Created 4 years, 4 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
OLDNEW
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 "components/arc/bluetooth/arc_bluetooth_bridge.h" 5 #include "components/arc/bluetooth/arc_bluetooth_bridge.h"
6 6
7 #include <bluetooth/bluetooth.h> 7 #include <bluetooth/bluetooth.h>
8 #include <fcntl.h> 8 #include <fcntl.h>
9 #include <stddef.h> 9 #include <stddef.h>
10 #include <sys/socket.h> 10 #include <sys/socket.h>
(...skipping 10 matching lines...) Expand all
21 #include "base/threading/thread_task_runner_handle.h" 21 #include "base/threading/thread_task_runner_handle.h"
22 #include "base/time/time.h" 22 #include "base/time/time.h"
23 #include "components/arc/arc_bridge_service.h" 23 #include "components/arc/arc_bridge_service.h"
24 #include "components/arc/bluetooth/bluetooth_type_converters.h" 24 #include "components/arc/bluetooth/bluetooth_type_converters.h"
25 #include "device/bluetooth/bluetooth_common.h" 25 #include "device/bluetooth/bluetooth_common.h"
26 #include "device/bluetooth/bluetooth_device.h" 26 #include "device/bluetooth/bluetooth_device.h"
27 #include "device/bluetooth/bluetooth_gatt_connection.h" 27 #include "device/bluetooth/bluetooth_gatt_connection.h"
28 #include "device/bluetooth/bluetooth_gatt_notify_session.h" 28 #include "device/bluetooth/bluetooth_gatt_notify_session.h"
29 #include "device/bluetooth/bluetooth_local_gatt_characteristic.h" 29 #include "device/bluetooth/bluetooth_local_gatt_characteristic.h"
30 #include "device/bluetooth/bluetooth_local_gatt_descriptor.h" 30 #include "device/bluetooth/bluetooth_local_gatt_descriptor.h"
31 #include "device/bluetooth/bluez/bluetooth_device_bluez.h"
31 #include "mojo/edk/embedder/embedder.h" 32 #include "mojo/edk/embedder/embedder.h"
32 #include "mojo/edk/embedder/scoped_platform_handle.h" 33 #include "mojo/edk/embedder/scoped_platform_handle.h"
33 34
34 using device::BluetoothAdapter; 35 using device::BluetoothAdapter;
35 using device::BluetoothAdapterFactory; 36 using device::BluetoothAdapterFactory;
36 using device::BluetoothAdvertisement; 37 using device::BluetoothAdvertisement;
37 using device::BluetoothDevice; 38 using device::BluetoothDevice;
38 using device::BluetoothDiscoveryFilter; 39 using device::BluetoothDiscoveryFilter;
39 using device::BluetoothDiscoverySession; 40 using device::BluetoothDiscoverySession;
40 using device::BluetoothGattConnection; 41 using device::BluetoothGattConnection;
(...skipping 29 matching lines...) Expand all
70 // Bluetooth Specification Version 4.2 Vol 3 Part F Section 3.2.2 71 // Bluetooth Specification Version 4.2 Vol 3 Part F Section 3.2.2
71 // An attribute handle of value 0xFFFF is known as the maximum attribute handle. 72 // An attribute handle of value 0xFFFF is known as the maximum attribute handle.
72 constexpr int32_t kMaxGattAttributeHandle = 0xFFFF; 73 constexpr int32_t kMaxGattAttributeHandle = 0xFFFF;
73 // Bluetooth Specification Version 4.2 Vol 3 Part F Section 3.2.9 74 // Bluetooth Specification Version 4.2 Vol 3 Part F Section 3.2.9
74 // The maximum length of an attribute value shall be 512 octets. 75 // The maximum length of an attribute value shall be 512 octets.
75 constexpr int kMaxGattAttributeLength = 512; 76 constexpr int kMaxGattAttributeLength = 512;
76 // Copied from Android at system/bt/stack/btm/btm_ble_int.h 77 // Copied from Android at system/bt/stack/btm/btm_ble_int.h
77 // https://goo.gl/k7PM6u 78 // https://goo.gl/k7PM6u
78 constexpr uint16_t kAndroidMBluetoothVersionNumber = 95; 79 constexpr uint16_t kAndroidMBluetoothVersionNumber = 95;
79 constexpr uint16_t kMaxAdvertisement = 5; 80 constexpr uint16_t kMaxAdvertisement = 5;
81 // Bluetooth SDP Service Class ID List Attribute identifier
82 constexpr uint16_t kServiceClassIDListAttributeID = 0x0001;
80 83
81 using GattStatusCallback = 84 using GattStatusCallback =
82 base::Callback<void(arc::mojom::BluetoothGattStatus)>; 85 base::Callback<void(arc::mojom::BluetoothGattStatus)>;
83 using GattReadCallback = 86 using GattReadCallback =
84 base::Callback<void(arc::mojom::BluetoothGattValuePtr)>; 87 base::Callback<void(arc::mojom::BluetoothGattValuePtr)>;
88 using CreateSdpRecordCallback =
89 base::Callback<void(arc::mojom::BluetoothCreateSdpRecordResultPtr)>;
90 using RemoveSdpRecordCallback =
91 base::Callback<void(arc::mojom::BluetoothStatus)>;
85 92
86 // Example of identifier: /org/bluez/hci0/dev_E0_CF_65_8C_86_1A/service001a 93 // Example of identifier: /org/bluez/hci0/dev_E0_CF_65_8C_86_1A/service001a
87 // Convert the last 4 characters of |identifier| to an 94 // Convert the last 4 characters of |identifier| to an
88 // int, by interpreting them as hexadecimal digits. 95 // int, by interpreting them as hexadecimal digits.
89 int ConvertGattIdentifierToId(const std::string identifier) { 96 int ConvertGattIdentifierToId(const std::string identifier) {
90 return std::stoi(identifier.substr(identifier.size() - 4), nullptr, 16); 97 return std::stoi(identifier.substr(identifier.size() - 4), nullptr, 16);
91 } 98 }
92 99
93 // Create GattDBElement and fill in common data for 100 // Create GattDBElement and fill in common data for
94 // Gatt Service/Characteristic/Descriptor. 101 // Gatt Service/Characteristic/Descriptor.
(...skipping 82 matching lines...) Expand 10 before | Expand all | Expand 10 after
177 bool IsGattOffsetValid(int offset) { 184 bool IsGattOffsetValid(int offset) {
178 return 0 <= offset && offset < kMaxGattAttributeLength; 185 return 0 <= offset && offset < kMaxGattAttributeLength;
179 } 186 }
180 187
181 // This is needed because Android only support UUID 16 bits in advertising data. 188 // This is needed because Android only support UUID 16 bits in advertising data.
182 uint16_t GetUUID16(const BluetoothUUID& uuid) { 189 uint16_t GetUUID16(const BluetoothUUID& uuid) {
183 // Convert xxxxyyyy-xxxx-xxxx-xxxx-xxxxxxxxxxxx to int16 yyyy 190 // Convert xxxxyyyy-xxxx-xxxx-xxxx-xxxxxxxxxxxx to int16 yyyy
184 return std::stoi(uuid.canonical_value().substr(4, 4), nullptr, 16); 191 return std::stoi(uuid.canonical_value().substr(4, 4), nullptr, 16);
185 } 192 }
186 193
194 void OnCreateServiceRecordDone(
195 const CreateSdpRecordCallback& callback,
196 uint32_t service_handle) {
197 arc::mojom::BluetoothCreateSdpRecordResultPtr result =
198 arc::mojom::BluetoothCreateSdpRecordResult::New();
199 result->status = arc::mojom::BluetoothStatus::SUCCESS;
200 result->service_handle = service_handle;
201
202 callback.Run(std::move(result));
203 }
204
205 void OnCreateServiceRecordError(
206 const CreateSdpRecordCallback& callback,
207 bluez::BluetoothServiceRecordBlueZ::ErrorCode error_code) {
208 arc::mojom::BluetoothCreateSdpRecordResultPtr result =
209 arc::mojom::BluetoothCreateSdpRecordResult::New();
210 if (error_code ==
211 bluez::BluetoothServiceRecordBlueZ::ErrorCode::ERROR_ADAPTER_NOT_READY)
212 result->status = arc::mojom::BluetoothStatus::NOT_READY;
213 else
214 result->status = arc::mojom::BluetoothStatus::FAIL;
215
216 callback.Run(std::move(result));
217 }
218
219 void OnRemoveServiceRecordDone(
220 const RemoveSdpRecordCallback& callback) {
221 callback.Run(arc::mojom::BluetoothStatus::SUCCESS);
222 }
223
224 void OnRemoveServiceRecordError(
225 const RemoveSdpRecordCallback& callback,
226 bluez::BluetoothServiceRecordBlueZ::ErrorCode error_code) {
227 arc::mojom::BluetoothStatus status;
228 if (error_code ==
229 bluez::BluetoothServiceRecordBlueZ::ErrorCode::ERROR_ADAPTER_NOT_READY)
230 status = arc::mojom::BluetoothStatus::NOT_READY;
231 else
232 status = arc::mojom::BluetoothStatus::FAIL;
233
234 callback.Run(status);
235 }
236
187 } // namespace 237 } // namespace
188 238
189 namespace arc { 239 namespace arc {
190 240
191 ArcBluetoothBridge::ArcBluetoothBridge(ArcBridgeService* bridge_service) 241 ArcBluetoothBridge::ArcBluetoothBridge(ArcBridgeService* bridge_service)
192 : ArcService(bridge_service), binding_(this), weak_factory_(this) { 242 : ArcService(bridge_service), binding_(this), weak_factory_(this) {
193 if (BluetoothAdapterFactory::IsBluetoothAdapterAvailable()) { 243 if (BluetoothAdapterFactory::IsBluetoothAdapterAvailable()) {
194 VLOG(1) << "Registering bluetooth adapter."; 244 VLOG(1) << "Registering bluetooth adapter.";
195 BluetoothAdapterFactory::GetAdapter(base::Bind( 245 BluetoothAdapterFactory::GetAdapter(base::Bind(
196 &ArcBluetoothBridge::OnAdapterInitialized, weak_factory_.GetWeakPtr())); 246 &ArcBluetoothBridge::OnAdapterInitialized, weak_factory_.GetWeakPtr()));
(...skipping 689 matching lines...) Expand 10 before | Expand all | Expand 10 after
886 BluetoothDevice* device = 936 BluetoothDevice* device =
887 bluetooth_adapter_->GetDevice(remote_addr->To<std::string>()); 937 bluetooth_adapter_->GetDevice(remote_addr->To<std::string>());
888 DCHECK(device); 938 DCHECK(device);
889 939
890 if (device->IsConnected()) { 940 if (device->IsConnected()) {
891 arc_bridge_service()->bluetooth()->instance()->OnLEConnectionStateChange( 941 arc_bridge_service()->bluetooth()->instance()->OnLEConnectionStateChange(
892 std::move(remote_addr), true); 942 std::move(remote_addr), true);
893 return; 943 return;
894 } 944 }
895 945
896 // Also pass disconnect callback in error case 946 // Also pass disconnect callback in error case since it would be disconnected
897 // since it would be disconnected anyway. 947 // anyway.
898 mojom::BluetoothAddressPtr remote_addr_clone = remote_addr.Clone(); 948 mojom::BluetoothAddressPtr remote_addr_clone = remote_addr.Clone();
899 device->CreateGattConnection( 949 device->CreateGattConnection(
900 base::Bind(&ArcBluetoothBridge::OnGattConnected, 950 base::Bind(&ArcBluetoothBridge::OnGattConnected,
901 weak_factory_.GetWeakPtr(), base::Passed(&remote_addr)), 951 weak_factory_.GetWeakPtr(), base::Passed(&remote_addr)),
902 base::Bind(&ArcBluetoothBridge::OnGattConnectError, 952 base::Bind(&ArcBluetoothBridge::OnGattConnectError,
903 weak_factory_.GetWeakPtr(), base::Passed(&remote_addr_clone))); 953 weak_factory_.GetWeakPtr(), base::Passed(&remote_addr_clone)));
904 } 954 }
905 955
906 void ArcBluetoothBridge::DisconnectLEDevice( 956 void ArcBluetoothBridge::DisconnectLEDevice(
907 mojom::BluetoothAddressPtr remote_addr) { 957 mojom::BluetoothAddressPtr remote_addr) {
(...skipping 477 matching lines...) Expand 10 before | Expand all | Expand 10 after
1385 OnGattOperationDone(callback); 1435 OnGattOperationDone(callback);
1386 } 1436 }
1387 1437
1388 void ArcBluetoothBridge::SendIndication( 1438 void ArcBluetoothBridge::SendIndication(
1389 int32_t attribute_handle, 1439 int32_t attribute_handle,
1390 mojom::BluetoothAddressPtr address, 1440 mojom::BluetoothAddressPtr address,
1391 bool confirm, 1441 bool confirm,
1392 mojo::Array<uint8_t> value, 1442 mojo::Array<uint8_t> value,
1393 const SendIndicationCallback& callback) {} 1443 const SendIndicationCallback& callback) {}
1394 1444
1445 void ArcBluetoothBridge::GetSdpRecords(
1446 mojom::BluetoothAddressPtr remote_addr,
1447 mojom::BluetoothUUIDPtr target_uuid) {
1448 BluetoothDevice* device =
1449 bluetooth_adapter_->GetDevice(remote_addr->To<std::string>());
1450
1451 // Do an early return if there is no device with |remote_addr|.
1452 if (!device) {
1453 OnGetServiceRecordsError(std::move(remote_addr), std::move(target_uuid),
1454 bluez::BluetoothServiceRecordBlueZ::ErrorCode::
1455 ERROR_DEVICE_DISCONNECTED);
1456 return;
1457 }
1458
1459 bluez::BluetoothDeviceBlueZ* device_bluez =
1460 static_cast<bluez::BluetoothDeviceBlueZ*>(device);
1461
1462 mojom::BluetoothAddressPtr remote_addr_clone = remote_addr.Clone();
1463 mojom::BluetoothUUIDPtr target_uuid_clone = target_uuid.Clone();
1464
1465 device_bluez->GetServiceRecords(
1466 base::Bind(&ArcBluetoothBridge::OnGetServiceRecordsDone,
1467 weak_factory_.GetWeakPtr(), base::Passed(&remote_addr),
1468 base::Passed(&target_uuid)),
1469 base::Bind(&ArcBluetoothBridge::OnGetServiceRecordsError,
1470 weak_factory_.GetWeakPtr(), base::Passed(&remote_addr_clone),
1471 base::Passed(&target_uuid_clone)));
1472 }
1473
1474 void ArcBluetoothBridge::CreateSdpRecord(
1475 const bluez::BluetoothServiceRecordBlueZ& record,
1476 const CreateSdpRecordCallback& callback) {
1477 std::vector<uint16_t> v = record.GetAttributeIds();
1478
1479 // Check if ServiceClassIDList attribute (attribute ID 0x0001) is included
1480 // after type conversion, since it is mandatory for creating a service record.
1481 if (std::find(v.begin(), v.end(), kServiceClassIDListAttributeID) ==
1482 v.end()) {
1483 mojom::BluetoothCreateSdpRecordResultPtr result =
1484 mojom::BluetoothCreateSdpRecordResult::New();
1485 result->status = mojom::BluetoothStatus::FAIL;
1486 callback.Run(std::move(result));
1487 return;
1488 }
1489
1490 bluetooth_adapter_->CreateServiceRecord(
1491 record, base::Bind(&OnCreateServiceRecordDone, callback),
1492 base::Bind(&OnCreateServiceRecordError, callback));
1493 }
1494
1495 void ArcBluetoothBridge::RemoveSdpRecord(
1496 uint32_t service_handle,
1497 const RemoveSdpRecordCallback& callback) {
1498 bluetooth_adapter_->RemoveServiceRecord(
1499 service_handle, base::Bind(&OnRemoveServiceRecordDone, callback),
1500 base::Bind(&OnRemoveServiceRecordError, callback));
1501 }
1502
1395 void ArcBluetoothBridge::OnDiscoveryError() { 1503 void ArcBluetoothBridge::OnDiscoveryError() {
1396 LOG(WARNING) << "failed to change discovery state"; 1504 LOG(WARNING) << "failed to change discovery state";
1397 } 1505 }
1398 1506
1399 void ArcBluetoothBridge::OnPairing(mojom::BluetoothAddressPtr addr) const { 1507 void ArcBluetoothBridge::OnPairing(mojom::BluetoothAddressPtr addr) const {
1400 if (!HasBluetoothInstance()) 1508 if (!HasBluetoothInstance())
1401 return; 1509 return;
1402 1510
1403 arc_bridge_service()->bluetooth()->instance()->OnBondStateChanged( 1511 arc_bridge_service()->bluetooth()->instance()->OnBondStateChanged(
1404 mojom::BluetoothStatus::SUCCESS, std::move(addr), 1512 mojom::BluetoothStatus::SUCCESS, std::move(addr),
(...skipping 322 matching lines...) Expand 10 before | Expand all | Expand 10 after
1727 if (arc_bridge_service()->bluetooth()->version() >= kMinBtleVersion) { 1835 if (arc_bridge_service()->bluetooth()->version() >= kMinBtleVersion) {
1728 base::Optional<int8_t> rssi = device->GetInquiryRSSI(); 1836 base::Optional<int8_t> rssi = device->GetInquiryRSSI();
1729 mojo::Array<mojom::BluetoothAdvertisingDataPtr> adv_data = 1837 mojo::Array<mojom::BluetoothAdvertisingDataPtr> adv_data =
1730 GetAdvertisingData(device); 1838 GetAdvertisingData(device);
1731 arc_bridge_service()->bluetooth()->instance()->OnLEDeviceFound( 1839 arc_bridge_service()->bluetooth()->instance()->OnLEDeviceFound(
1732 addr->Clone(), rssi.value_or(mojom::kUnknownPower), 1840 addr->Clone(), rssi.value_or(mojom::kUnknownPower),
1733 std::move(adv_data)); 1841 std::move(adv_data));
1734 } 1842 }
1735 1843
1736 // OnBondStateChanged must be called with mojom::BluetoothBondState::BONDING 1844 // OnBondStateChanged must be called with mojom::BluetoothBondState::BONDING
1737 // to 1845 // to make sure the bond state machine on Android is ready to take the
1738 // make sure the bond state machine on Android is ready to take the
1739 // pair-done event. Otherwise the pair-done event will be dropped as an 1846 // pair-done event. Otherwise the pair-done event will be dropped as an
1740 // invalid change of paired status. 1847 // invalid change of paired status.
1741 OnPairing(addr->Clone()); 1848 OnPairing(addr->Clone());
1742 OnPairedDone(std::move(addr)); 1849 OnPairedDone(std::move(addr));
1743 } 1850 }
1744 } 1851 }
1745 1852
1853 void ArcBluetoothBridge::OnGetServiceRecordsDone(
1854 mojom::BluetoothAddressPtr remote_addr,
1855 mojom::BluetoothUUIDPtr target_uuid,
1856 const std::vector<bluez::BluetoothServiceRecordBlueZ>& records_bluez) {
1857 if (!HasBluetoothInstance())
1858 return;
1859
1860 arc_bridge_service()->bluetooth()->instance()->OnGetSdpRecords(
1861 mojom::BluetoothStatus::SUCCESS, std::move(remote_addr),
1862 std::move(target_uuid), records_bluez);
1863 }
1864
1865 void ArcBluetoothBridge::OnGetServiceRecordsError(
1866 mojom::BluetoothAddressPtr remote_addr,
1867 mojom::BluetoothUUIDPtr target_uuid,
1868 bluez::BluetoothServiceRecordBlueZ::ErrorCode error_code) {
1869 mojom::BluetoothStatus status;
1870
1871 switch (error_code) {
1872 case bluez::BluetoothServiceRecordBlueZ::ErrorCode::ERROR_ADAPTER_NOT_READY:
1873 status = mojom::BluetoothStatus::NOT_READY;
1874 break;
1875 case bluez::BluetoothServiceRecordBlueZ::ErrorCode::
1876 ERROR_DEVICE_DISCONNECTED:
1877 status = mojom::BluetoothStatus::RMT_DEV_DOWN;
1878 break;
1879 default:
1880 status = mojom::BluetoothStatus::FAIL;
1881 break;
1882 }
1883
1884 arc_bridge_service()->bluetooth()->instance()->OnGetSdpRecords(
1885 status, std::move(remote_addr), std::move(target_uuid),
1886 std::vector<bluez::BluetoothServiceRecordBlueZ>());
1887 }
1888
1746 bool ArcBluetoothBridge::CheckBluetoothInstanceVersion( 1889 bool ArcBluetoothBridge::CheckBluetoothInstanceVersion(
1747 uint32_t version_need) const { 1890 uint32_t version_need) const {
1748 uint32_t version = arc_bridge_service()->bluetooth()->version(); 1891 uint32_t version = arc_bridge_service()->bluetooth()->version();
1749 if (version >= version_need) 1892 if (version >= version_need)
1750 return true; 1893 return true;
1751 LOG(WARNING) << "Bluetooth instance is too old (version " << version 1894 LOG(WARNING) << "Bluetooth instance is too old (version " << version
1752 << ") need version " << version_need; 1895 << ") need version " << version_need;
1753 return false; 1896 return false;
1754 } 1897 }
1755 1898
1756 bool ArcBluetoothBridge::CalledOnValidThread() { 1899 bool ArcBluetoothBridge::CalledOnValidThread() {
1757 return thread_checker_.CalledOnValidThread(); 1900 return thread_checker_.CalledOnValidThread();
1758 } 1901 }
1759 1902
1760 } // namespace arc 1903 } // namespace arc
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698