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/test/bluetooth_test_win.h" | 5 #include "device/bluetooth/test/bluetooth_test_win.h" |
6 | 6 |
7 #include "base/bind.h" | 7 #include "base/bind.h" |
8 #include "base/strings/sys_string_conversions.h" | 8 #include "base/strings/sys_string_conversions.h" |
9 #include "device/bluetooth/bluetooth_adapter_win.h" | 9 #include "device/bluetooth/bluetooth_adapter_win.h" |
10 #include "device/bluetooth/bluetooth_low_energy_win.h" | 10 #include "device/bluetooth/bluetooth_low_energy_win.h" |
| 11 #include "device/bluetooth/bluetooth_remote_gatt_characteristic_win.h" |
| 12 #include "device/bluetooth/bluetooth_remote_gatt_service_win.h" |
11 | 13 |
12 namespace { | 14 namespace { |
13 | 15 |
14 BLUETOOTH_ADDRESS CanonicalStringToBLUETOOTH_ADDRESS( | 16 BLUETOOTH_ADDRESS CanonicalStringToBLUETOOTH_ADDRESS( |
15 std::string device_address) { | 17 std::string device_address) { |
16 BLUETOOTH_ADDRESS win_addr; | 18 BLUETOOTH_ADDRESS win_addr; |
17 unsigned int data[6]; | 19 unsigned int data[6]; |
18 int result = | 20 int result = |
19 sscanf_s(device_address.c_str(), "%02X:%02X:%02X:%02X:%02X:%02X", | 21 sscanf_s(device_address.c_str(), "%02X:%02X:%02X:%02X:%02X:%02X", |
20 &data[5], &data[4], &data[3], &data[2], &data[1], &data[0]); | 22 &data[5], &data[4], &data[3], &data[2], &data[1], &data[0]); |
21 CHECK(result == 6); | 23 CHECK(result == 6); |
22 for (int i = 0; i < 6; i++) { | 24 for (int i = 0; i < 6; i++) { |
23 win_addr.rgBytes[i] = data[i]; | 25 win_addr.rgBytes[i] = data[i]; |
24 } | 26 } |
25 return win_addr; | 27 return win_addr; |
26 } | 28 } |
27 | 29 |
| 30 // The canonical UUID string format is device::BluetoothUUID.value(). |
| 31 BTH_LE_UUID CanonicalStringToBTH_LE_UUID(std::string uuid) { |
| 32 BTH_LE_UUID win_uuid = {0}; |
| 33 if (uuid.size() == 4) { |
| 34 win_uuid.IsShortUuid = TRUE; |
| 35 unsigned int data[1]; |
| 36 int result = sscanf_s(uuid.c_str(), "%04x", &data[0]); |
| 37 CHECK(result == 1); |
| 38 win_uuid.Value.ShortUuid = data[0]; |
| 39 } else if (uuid.size() == 36) { |
| 40 win_uuid.IsShortUuid = FALSE; |
| 41 unsigned int data[11]; |
| 42 int result = sscanf_s( |
| 43 uuid.c_str(), "%08x-%04x-%04x-%02x%02x-%02x%02x%02x%02x%02x%02x", |
| 44 &data[0], &data[1], &data[2], &data[3], &data[4], &data[5], &data[6], |
| 45 &data[7], &data[8], &data[9], &data[10]); |
| 46 CHECK(result == 11); |
| 47 win_uuid.Value.LongUuid.Data1 = data[0]; |
| 48 win_uuid.Value.LongUuid.Data2 = data[1]; |
| 49 win_uuid.Value.LongUuid.Data3 = data[2]; |
| 50 win_uuid.Value.LongUuid.Data4[0] = data[3]; |
| 51 win_uuid.Value.LongUuid.Data4[1] = data[4]; |
| 52 win_uuid.Value.LongUuid.Data4[2] = data[5]; |
| 53 win_uuid.Value.LongUuid.Data4[3] = data[6]; |
| 54 win_uuid.Value.LongUuid.Data4[4] = data[7]; |
| 55 win_uuid.Value.LongUuid.Data4[5] = data[8]; |
| 56 win_uuid.Value.LongUuid.Data4[6] = data[9]; |
| 57 win_uuid.Value.LongUuid.Data4[7] = data[10]; |
| 58 } else { |
| 59 CHECK(false); |
| 60 } |
| 61 |
| 62 return win_uuid; |
| 63 } |
| 64 |
28 } // namespace | 65 } // namespace |
29 | 66 |
30 namespace device { | 67 namespace device { |
31 BluetoothTestWin::BluetoothTestWin() | 68 BluetoothTestWin::BluetoothTestWin() |
32 : ui_task_runner_(new base::TestSimpleTaskRunner()), | 69 : ui_task_runner_(new base::TestSimpleTaskRunner()), |
33 bluetooth_task_runner_(new base::TestSimpleTaskRunner()) {} | 70 bluetooth_task_runner_(new base::TestSimpleTaskRunner()), |
| 71 adapter_win_(nullptr), |
| 72 fake_bt_classic_wrapper_(nullptr), |
| 73 fake_bt_le_wrapper_(nullptr) {} |
34 BluetoothTestWin::~BluetoothTestWin() {} | 74 BluetoothTestWin::~BluetoothTestWin() {} |
35 | 75 |
36 bool BluetoothTestWin::PlatformSupportsLowEnergy() { | 76 bool BluetoothTestWin::PlatformSupportsLowEnergy() { |
37 return win::IsBluetoothLowEnergySupported(); | 77 if (fake_bt_le_wrapper_) |
| 78 return fake_bt_le_wrapper_->IsBluetoothLowEnergySupported(); |
| 79 return true; |
38 } | 80 } |
39 | 81 |
40 void BluetoothTestWin::AdapterInitCallback() {} | 82 void BluetoothTestWin::AdapterInitCallback() {} |
41 | 83 |
42 void BluetoothTestWin::InitWithDefaultAdapter() { | 84 void BluetoothTestWin::InitWithDefaultAdapter() { |
43 adapter_ = new BluetoothAdapterWin(base::Bind( | 85 adapter_ = new BluetoothAdapterWin(base::Bind( |
44 &BluetoothTestWin::AdapterInitCallback, base::Unretained(this))); | 86 &BluetoothTestWin::AdapterInitCallback, base::Unretained(this))); |
45 adapter_win_ = static_cast<BluetoothAdapterWin*>(adapter_.get()); | 87 adapter_win_ = static_cast<BluetoothAdapterWin*>(adapter_.get()); |
46 adapter_win_->Init(); | 88 adapter_win_->Init(); |
47 } | 89 } |
(...skipping 55 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
103 } break; | 145 } break; |
104 case 4: { | 146 case 4: { |
105 device_name = kTestDeviceNameEmpty; | 147 device_name = kTestDeviceNameEmpty; |
106 device_address = kTestDeviceAddress2; | 148 device_address = kTestDeviceAddress2; |
107 } break; | 149 } break; |
108 } | 150 } |
109 | 151 |
110 win::BLEDevice* simulated_device = fake_bt_le_wrapper_->SimulateBLEDevice( | 152 win::BLEDevice* simulated_device = fake_bt_le_wrapper_->SimulateBLEDevice( |
111 device_name, CanonicalStringToBLUETOOTH_ADDRESS(device_address)); | 153 device_name, CanonicalStringToBLUETOOTH_ADDRESS(device_address)); |
112 if (simulated_device != nullptr) { | 154 if (simulated_device != nullptr) { |
113 if (!service_uuid_1.empty()) | 155 if (!service_uuid_1.empty()) { |
114 fake_bt_le_wrapper_->SimulateBLEGattService(simulated_device, | 156 fake_bt_le_wrapper_->SimulateBLEGattService( |
115 service_uuid_1); | 157 simulated_device, nullptr, |
116 if (!service_uuid_2.empty()) | 158 CanonicalStringToBTH_LE_UUID(service_uuid_1)); |
117 fake_bt_le_wrapper_->SimulateBLEGattService(simulated_device, | 159 } |
118 service_uuid_2); | 160 if (!service_uuid_2.empty()) { |
| 161 fake_bt_le_wrapper_->SimulateBLEGattService( |
| 162 simulated_device, nullptr, |
| 163 CanonicalStringToBTH_LE_UUID(service_uuid_2)); |
| 164 } |
119 } | 165 } |
120 bluetooth_task_runner_->RunPendingTasks(); | 166 bluetooth_task_runner_->RunPendingTasks(); |
121 ui_task_runner_->RunPendingTasks(); | 167 ui_task_runner_->RunPendingTasks(); |
122 | 168 |
123 std::vector<BluetoothDevice*> devices = adapter_win_->GetDevices(); | 169 std::vector<BluetoothDevice*> devices = adapter_win_->GetDevices(); |
124 for (auto device : devices) { | 170 for (auto device : devices) { |
125 if (device->GetAddress() == device_address) | 171 if (device->GetAddress() == device_address) |
126 return device; | 172 return device; |
127 } | 173 } |
128 | 174 |
(...skipping 12 matching lines...) Expand all Loading... |
141 } | 187 } |
142 | 188 |
143 void BluetoothTestWin::SimulateGattServicesDiscovered( | 189 void BluetoothTestWin::SimulateGattServicesDiscovered( |
144 BluetoothDevice* device, | 190 BluetoothDevice* device, |
145 const std::vector<std::string>& uuids) { | 191 const std::vector<std::string>& uuids) { |
146 win::BLEDevice* simulated_device = | 192 win::BLEDevice* simulated_device = |
147 fake_bt_le_wrapper_->GetSimulatedBLEDevice(device->GetAddress()); | 193 fake_bt_le_wrapper_->GetSimulatedBLEDevice(device->GetAddress()); |
148 CHECK(simulated_device); | 194 CHECK(simulated_device); |
149 | 195 |
150 for (auto uuid : uuids) { | 196 for (auto uuid : uuids) { |
151 fake_bt_le_wrapper_->SimulateBLEGattService(simulated_device, uuid); | 197 fake_bt_le_wrapper_->SimulateBLEGattService( |
| 198 simulated_device, nullptr, CanonicalStringToBTH_LE_UUID(uuid)); |
152 } | 199 } |
153 | 200 |
154 bluetooth_task_runner_->RunPendingTasks(); | 201 bluetooth_task_runner_->RunPendingTasks(); |
155 ui_task_runner_->RunPendingTasks(); | 202 ui_task_runner_->RunPendingTasks(); |
156 } | 203 } |
| 204 |
| 205 void BluetoothTestWin::SimulateGattServiceRemoved( |
| 206 BluetoothGattService* service) { |
| 207 std::string device_address = service->GetDevice()->GetAddress(); |
| 208 win::BLEDevice* target_device = |
| 209 fake_bt_le_wrapper_->GetSimulatedBLEDevice(device_address); |
| 210 CHECK(target_device); |
| 211 |
| 212 BluetoothRemoteGattServiceWin* win_service = |
| 213 static_cast<BluetoothRemoteGattServiceWin*>(service); |
| 214 std::string service_att_handle = |
| 215 std::to_string(win_service->GetAttributeHandle()); |
| 216 if (service->IsPrimary()) { |
| 217 fake_bt_le_wrapper_->SimulateBLEGattServiceRemoved(target_device, nullptr, |
| 218 service_att_handle); |
| 219 } else { |
| 220 win::BLEGattService* target_service = |
| 221 GetSimulatedService(target_device, win_service->GetParentService()); |
| 222 fake_bt_le_wrapper_->SimulateBLEGattServiceRemoved( |
| 223 target_device, target_service, service_att_handle); |
| 224 } |
| 225 |
| 226 ForceRefreshDevice(); |
| 227 } |
| 228 |
| 229 void BluetoothTestWin::SimulateGattCharacteristic(BluetoothGattService* service, |
| 230 const std::string& uuid, |
| 231 int properties) { |
| 232 std::string device_address = service->GetDevice()->GetAddress(); |
| 233 win::BLEDevice* target_device = |
| 234 fake_bt_le_wrapper_->GetSimulatedBLEDevice(device_address); |
| 235 CHECK(target_device); |
| 236 win::BLEGattService* target_service = |
| 237 GetSimulatedService(target_device, service); |
| 238 CHECK(target_service); |
| 239 |
| 240 BTH_LE_GATT_CHARACTERISTIC win_cha_info; |
| 241 win_cha_info.CharacteristicUuid = CanonicalStringToBTH_LE_UUID(uuid); |
| 242 if (properties & BluetoothGattCharacteristic::PROPERTY_BROADCAST) |
| 243 win_cha_info.IsBroadcastable = TRUE; |
| 244 if (properties & BluetoothGattCharacteristic::PROPERTY_READ) |
| 245 win_cha_info.IsReadable = TRUE; |
| 246 if (properties & BluetoothGattCharacteristic::PROPERTY_WRITE_WITHOUT_RESPONSE) |
| 247 win_cha_info.IsWritableWithoutResponse = TRUE; |
| 248 if (properties & BluetoothGattCharacteristic::PROPERTY_WRITE) |
| 249 win_cha_info.IsWritable = TRUE; |
| 250 if (properties & BluetoothGattCharacteristic::PROPERTY_NOTIFY) |
| 251 win_cha_info.IsNotifiable = TRUE; |
| 252 if (properties & BluetoothGattCharacteristic::PROPERTY_INDICATE) |
| 253 win_cha_info.IsIndicatable = TRUE; |
| 254 if (properties & |
| 255 BluetoothGattCharacteristic::PROPERTY_AUTHENTICATED_SIGNED_WRITES) |
| 256 win_cha_info.IsSignedWritable = TRUE; |
| 257 if (properties & BluetoothGattCharacteristic::PROPERTY_EXTENDED_PROPERTIES) |
| 258 win_cha_info.HasExtendedProperties = TRUE; |
| 259 fake_bt_le_wrapper_->SimulateBLEGattCharacterisc( |
| 260 device_address, target_service, win_cha_info); |
| 261 |
| 262 ForceRefreshDevice(); |
| 263 } |
| 264 |
| 265 void BluetoothTestWin::SimulateGattCharacteristicRemoved( |
| 266 BluetoothGattService* service, |
| 267 BluetoothGattCharacteristic* characteristic) { |
| 268 CHECK(service); |
| 269 CHECK(characteristic); |
| 270 |
| 271 std::string device_address = service->GetDevice()->GetAddress(); |
| 272 win::BLEGattService* target_service = GetSimulatedService( |
| 273 fake_bt_le_wrapper_->GetSimulatedBLEDevice(device_address), service); |
| 274 CHECK(target_service); |
| 275 |
| 276 std::string characteristic_att_handle = std::to_string( |
| 277 static_cast<BluetoothRemoteGattCharacteristicWin*>(characteristic) |
| 278 ->GetAttributeHandle()); |
| 279 fake_bt_le_wrapper_->SimulateBLEGattCharacteriscRemove( |
| 280 target_service, characteristic_att_handle); |
| 281 |
| 282 ForceRefreshDevice(); |
| 283 } |
| 284 |
| 285 void BluetoothTestWin::SimulateIncludedGattServicesDiscovered( |
| 286 BluetoothGattService* service, |
| 287 const std::vector<std::string>& uuids) { |
| 288 std::string device_address = service->GetDevice()->GetAddress(); |
| 289 win::BLEDevice* target_device = |
| 290 fake_bt_le_wrapper_->GetSimulatedBLEDevice(device_address); |
| 291 CHECK(target_device); |
| 292 win::BLEGattService* target_service = |
| 293 GetSimulatedService(target_device, service); |
| 294 CHECK(target_service); |
| 295 |
| 296 for (const auto& uuid : uuids) { |
| 297 fake_bt_le_wrapper_->SimulateBLEGattService( |
| 298 target_device, target_service, CanonicalStringToBTH_LE_UUID(uuid)); |
| 299 } |
| 300 |
| 301 ForceRefreshDevice(); |
| 302 } |
| 303 |
| 304 win::BLEGattService* BluetoothTestWin::GetSimulatedService( |
| 305 win::BLEDevice* device, |
| 306 BluetoothGattService* service) { |
| 307 CHECK(device); |
| 308 CHECK(service); |
| 309 |
| 310 std::vector<std::string> chain_of_att_handles; |
| 311 BluetoothRemoteGattServiceWin* win_service = |
| 312 static_cast<BluetoothRemoteGattServiceWin*>(service); |
| 313 while (!win_service->IsPrimary()) { |
| 314 chain_of_att_handles.insert( |
| 315 chain_of_att_handles.begin(), |
| 316 std::to_string(win_service->GetAttributeHandle())); |
| 317 win_service = win_service->GetParentService(); |
| 318 } |
| 319 chain_of_att_handles.insert( |
| 320 chain_of_att_handles.begin(), |
| 321 std::to_string(win_service->GetAttributeHandle())); |
| 322 win::BLEGattService* simulated_service = |
| 323 fake_bt_le_wrapper_->GetSimulatedGattService(device, |
| 324 chain_of_att_handles); |
| 325 CHECK(simulated_service); |
| 326 return simulated_service; |
| 327 } |
| 328 |
| 329 void BluetoothTestWin::ForceRefreshDevice() { |
| 330 adapter_win_->force_update_device_for_test_ = true; |
| 331 bluetooth_task_runner_->RunPendingTasks(); |
| 332 ui_task_runner_->RunPendingTasks(); |
| 333 } |
157 } | 334 } |
OLD | NEW |