| OLD | NEW |
| 1 // Copyright 2013 The Chromium Authors. All rights reserved. | 1 // Copyright 2013 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_adapter_mac.h" | 5 #include "device/bluetooth/bluetooth_adapter_mac.h" |
| 6 | 6 |
| 7 #import <IOBluetooth/objc/IOBluetoothDevice.h> | 7 #import <IOBluetooth/objc/IOBluetoothDevice.h> |
| 8 #import <IOBluetooth/objc/IOBluetoothHostController.h> | 8 #import <IOBluetooth/objc/IOBluetoothHostController.h> |
| 9 #include <stddef.h> | 9 #include <stddef.h> |
| 10 | 10 |
| (...skipping 501 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 512 void BluetoothAdapterMac::LowEnergyDeviceUpdated( | 512 void BluetoothAdapterMac::LowEnergyDeviceUpdated( |
| 513 CBPeripheral* peripheral, | 513 CBPeripheral* peripheral, |
| 514 NSDictionary* advertisement_data, | 514 NSDictionary* advertisement_data, |
| 515 int rssi) { | 515 int rssi) { |
| 516 BluetoothLowEnergyDeviceMac* device_mac = | 516 BluetoothLowEnergyDeviceMac* device_mac = |
| 517 GetBluetoothLowEnergyDeviceMac(peripheral); | 517 GetBluetoothLowEnergyDeviceMac(peripheral); |
| 518 // If has no entry in the map, create new device and insert into |devices_|, | 518 // If has no entry in the map, create new device and insert into |devices_|, |
| 519 // otherwise update the existing device. | 519 // otherwise update the existing device. |
| 520 const bool is_new_device = device_mac == nullptr; | 520 const bool is_new_device = device_mac == nullptr; |
| 521 if (is_new_device) { | 521 if (is_new_device) { |
| 522 VLOG(1) << "LowEnergyDeviceUpdated new device"; | |
| 523 // A new device has been found. | 522 // A new device has been found. |
| 524 device_mac = new BluetoothLowEnergyDeviceMac(this, peripheral); | 523 device_mac = new BluetoothLowEnergyDeviceMac(this, peripheral); |
| 524 VLOG(1) << *device_mac << ": New Device."; |
| 525 } else if (DoesCollideWithKnownDevice(peripheral, device_mac)) { | 525 } else if (DoesCollideWithKnownDevice(peripheral, device_mac)) { |
| 526 return; | 526 return; |
| 527 } | 527 } |
| 528 | 528 |
| 529 DCHECK(device_mac); | 529 DCHECK(device_mac); |
| 530 VLOG(3) << *device_mac << ": Device updated with " |
| 531 << base::SysNSStringToUTF8([advertisement_data description]); |
| 530 | 532 |
| 531 // Get Advertised UUIDs | 533 // Get Advertised UUIDs |
| 532 BluetoothDevice::UUIDList advertised_uuids; | 534 BluetoothDevice::UUIDList advertised_uuids; |
| 533 NSArray* service_uuids = | 535 NSArray* service_uuids = |
| 534 [advertisement_data objectForKey:CBAdvertisementDataServiceUUIDsKey]; | 536 [advertisement_data objectForKey:CBAdvertisementDataServiceUUIDsKey]; |
| 535 for (CBUUID* uuid in service_uuids) { | 537 for (CBUUID* uuid in service_uuids) { |
| 536 advertised_uuids.push_back(BluetoothUUID([[uuid UUIDString] UTF8String])); | 538 advertised_uuids.push_back(BluetoothUUID([[uuid UUIDString] UTF8String])); |
| 537 } | 539 } |
| 538 NSArray* overflow_service_uuids = [advertisement_data | 540 NSArray* overflow_service_uuids = [advertisement_data |
| 539 objectForKey:CBAdvertisementDataOverflowServiceUUIDsKey]; | 541 objectForKey:CBAdvertisementDataOverflowServiceUUIDsKey]; |
| (...skipping 29 matching lines...) Expand all Loading... |
| 569 devices_[device_address] = base::WrapUnique(device_mac); | 571 devices_[device_address] = base::WrapUnique(device_mac); |
| 570 for (auto& observer : observers_) | 572 for (auto& observer : observers_) |
| 571 observer.DeviceAdded(this, device_mac); | 573 observer.DeviceAdded(this, device_mac); |
| 572 } else { | 574 } else { |
| 573 for (auto& observer : observers_) | 575 for (auto& observer : observers_) |
| 574 observer.DeviceChanged(this, device_mac); | 576 observer.DeviceChanged(this, device_mac); |
| 575 } | 577 } |
| 576 } | 578 } |
| 577 | 579 |
| 578 // TODO(krstnmnlsn): Implement. crbug.com/511025 | 580 // TODO(krstnmnlsn): Implement. crbug.com/511025 |
| 579 void BluetoothAdapterMac::LowEnergyCentralManagerUpdatedState() {} | 581 void BluetoothAdapterMac::LowEnergyCentralManagerUpdatedState() { |
| 582 VLOG(1) << "Central manager state updated: " |
| 583 << [low_energy_central_manager_ state]; |
| 584 } |
| 580 | 585 |
| 581 void BluetoothAdapterMac::AddPairedDevices() { | 586 void BluetoothAdapterMac::AddPairedDevices() { |
| 582 // Add any new paired devices. | 587 // Add any new paired devices. |
| 583 for (IOBluetoothDevice* device in [IOBluetoothDevice pairedDevices]) { | 588 for (IOBluetoothDevice* device in [IOBluetoothDevice pairedDevices]) { |
| 584 // pairedDevices sometimes includes unknown devices that are not paired. | 589 // pairedDevices sometimes includes unknown devices that are not paired. |
| 585 // Radar issue with id 2282763004 has been filed about it. | 590 // Radar issue with id 2282763004 has been filed about it. |
| 586 if ([device isPaired]) { | 591 if ([device isPaired]) { |
| 587 ClassicDeviceAdded(device); | 592 ClassicDeviceAdded(device); |
| 588 } | 593 } |
| 589 } | 594 } |
| 590 } | 595 } |
| 591 | 596 |
| 592 std::vector<BluetoothDevice*> | 597 std::vector<BluetoothDevice*> |
| 593 BluetoothAdapterMac::RetrieveGattConnectedDevicesWithService( | 598 BluetoothAdapterMac::RetrieveGattConnectedDevicesWithService( |
| 594 const BluetoothUUID* uuid) { | 599 const BluetoothUUID* uuid) { |
| 595 NSArray* cbUUIDs = nil; | 600 NSArray* cbUUIDs = nil; |
| 596 if (!uuid) { | 601 if (!uuid) { |
| 602 VLOG(1) << "Retrieving all connected devices."; |
| 597 // It is not possible to ask for all connected peripherals with | 603 // It is not possible to ask for all connected peripherals with |
| 598 // -[CBCentralManager retrieveConnectedPeripheralsWithServices:] by passing | 604 // -[CBCentralManager retrieveConnectedPeripheralsWithServices:] by passing |
| 599 // nil. To try to get most of the peripherals, the search is done with | 605 // nil. To try to get most of the peripherals, the search is done with |
| 600 // Generic Access service. | 606 // Generic Access service. |
| 601 CBUUID* genericAccessServiceUUID = [CBUUID UUIDWithString:@"1800"]; | 607 CBUUID* genericAccessServiceUUID = [CBUUID UUIDWithString:@"1800"]; |
| 602 cbUUIDs = @[ genericAccessServiceUUID ]; | 608 cbUUIDs = @[ genericAccessServiceUUID ]; |
| 603 } else { | 609 } else { |
| 610 VLOG(1) << "Retrieving connected devices with UUID: " |
| 611 << uuid->canonical_value(); |
| 604 NSString* uuidString = | 612 NSString* uuidString = |
| 605 base::SysUTF8ToNSString(uuid->canonical_value().c_str()); | 613 base::SysUTF8ToNSString(uuid->canonical_value().c_str()); |
| 606 cbUUIDs = @[ [CBUUID UUIDWithString:uuidString] ]; | 614 cbUUIDs = @[ [CBUUID UUIDWithString:uuidString] ]; |
| 607 } | 615 } |
| 608 NSArray* peripherals = [low_energy_central_manager_ | 616 NSArray* peripherals = [low_energy_central_manager_ |
| 609 retrieveConnectedPeripheralsWithServices:cbUUIDs]; | 617 retrieveConnectedPeripheralsWithServices:cbUUIDs]; |
| 610 std::vector<BluetoothDevice*> connected_devices; | 618 std::vector<BluetoothDevice*> connected_devices; |
| 611 for (CBPeripheral* peripheral in peripherals) { | 619 for (CBPeripheral* peripheral in peripherals) { |
| 612 BluetoothLowEnergyDeviceMac* device_mac = | 620 BluetoothLowEnergyDeviceMac* device_mac = |
| 613 GetBluetoothLowEnergyDeviceMac(peripheral); | 621 GetBluetoothLowEnergyDeviceMac(peripheral); |
| 614 const bool is_new_device = device_mac == nullptr; | 622 const bool is_new_device = device_mac == nullptr; |
| 615 | 623 |
| 616 if (!is_new_device && DoesCollideWithKnownDevice(peripheral, device_mac)) { | 624 if (!is_new_device && DoesCollideWithKnownDevice(peripheral, device_mac)) { |
| 617 continue; | 625 continue; |
| 618 } | 626 } |
| 619 if (is_new_device) { | 627 if (is_new_device) { |
| 620 device_mac = new BluetoothLowEnergyDeviceMac(this, peripheral); | 628 device_mac = new BluetoothLowEnergyDeviceMac(this, peripheral); |
| 621 std::string device_address = | 629 std::string device_address = |
| 622 BluetoothLowEnergyDeviceMac::GetPeripheralHashAddress(peripheral); | 630 BluetoothLowEnergyDeviceMac::GetPeripheralHashAddress(peripheral); |
| 623 devices_[device_address] = base::WrapUnique(device_mac); | 631 devices_[device_address] = base::WrapUnique(device_mac); |
| 624 for (auto& observer : observers_) { | 632 for (auto& observer : observers_) { |
| 625 observer.DeviceAdded(this, device_mac); | 633 observer.DeviceAdded(this, device_mac); |
| 626 } | 634 } |
| 627 } | 635 } |
| 628 connected_devices.push_back(device_mac); | 636 connected_devices.push_back(device_mac); |
| 637 VLOG(1) << *device_mac << ": New connected device."; |
| 629 } | 638 } |
| 630 return connected_devices; | 639 return connected_devices; |
| 631 } | 640 } |
| 632 | 641 |
| 633 void BluetoothAdapterMac::CreateGattConnection( | 642 void BluetoothAdapterMac::CreateGattConnection( |
| 634 BluetoothLowEnergyDeviceMac* device_mac) { | 643 BluetoothLowEnergyDeviceMac* device_mac) { |
| 635 [low_energy_central_manager_ connectPeripheral:device_mac->peripheral_ | 644 [low_energy_central_manager_ connectPeripheral:device_mac->peripheral_ |
| 636 options:nil]; | 645 options:nil]; |
| 637 } | 646 } |
| 638 | 647 |
| (...skipping 15 matching lines...) Expand all Loading... |
| 654 } | 663 } |
| 655 | 664 |
| 656 void BluetoothAdapterMac::DidFailToConnectPeripheral(CBPeripheral* peripheral, | 665 void BluetoothAdapterMac::DidFailToConnectPeripheral(CBPeripheral* peripheral, |
| 657 NSError* error) { | 666 NSError* error) { |
| 658 BluetoothLowEnergyDeviceMac* device_mac = | 667 BluetoothLowEnergyDeviceMac* device_mac = |
| 659 GetBluetoothLowEnergyDeviceMac(peripheral); | 668 GetBluetoothLowEnergyDeviceMac(peripheral); |
| 660 if (!device_mac) { | 669 if (!device_mac) { |
| 661 [low_energy_central_manager_ cancelPeripheralConnection:peripheral]; | 670 [low_energy_central_manager_ cancelPeripheralConnection:peripheral]; |
| 662 return; | 671 return; |
| 663 } | 672 } |
| 664 VLOG(1) << "Failed to connect to peripheral"; | |
| 665 BluetoothDevice::ConnectErrorCode error_code = | 673 BluetoothDevice::ConnectErrorCode error_code = |
| 666 BluetoothDevice::ConnectErrorCode::ERROR_UNKNOWN; | 674 BluetoothDevice::ConnectErrorCode::ERROR_UNKNOWN; |
| 667 if (error) { | 675 if (error) { |
| 668 error_code = BluetoothDeviceMac::GetConnectErrorCodeFromNSError(error); | 676 error_code = BluetoothDeviceMac::GetConnectErrorCodeFromNSError(error); |
| 669 VLOG(1) << "Bluetooth error, domain: " << error.domain.UTF8String | 677 VLOG(1) << "Converting Bluetooth error, domain: " << error.domain.UTF8String |
| 670 << ", error code: " << error.code | 678 << ", error code: " << error.code << ", to: " << error_code; |
| 671 << ", converted into: " << error_code; | |
| 672 } | 679 } |
| 680 VLOG(1) << *device_mac << ": Failed to connect to peripheral with error " |
| 681 << error; |
| 673 device_mac->DidFailToConnectGatt(error_code); | 682 device_mac->DidFailToConnectGatt(error_code); |
| 674 } | 683 } |
| 675 | 684 |
| 676 void BluetoothAdapterMac::DidDisconnectPeripheral(CBPeripheral* peripheral, | 685 void BluetoothAdapterMac::DidDisconnectPeripheral(CBPeripheral* peripheral, |
| 677 NSError* error) { | 686 NSError* error) { |
| 678 BluetoothLowEnergyDeviceMac* device_mac = | 687 BluetoothLowEnergyDeviceMac* device_mac = |
| 679 GetBluetoothLowEnergyDeviceMac(peripheral); | 688 GetBluetoothLowEnergyDeviceMac(peripheral); |
| 680 if (!device_mac) { | 689 if (!device_mac) { |
| 681 [low_energy_central_manager_ cancelPeripheralConnection:peripheral]; | 690 [low_energy_central_manager_ cancelPeripheralConnection:peripheral]; |
| 682 return; | 691 return; |
| 683 } | 692 } |
| 684 VLOG(1) << "Disconnected from peripheral."; | |
| 685 if (error) { | |
| 686 VLOG(1) << "Bluetooth error, domain: " << error.domain.UTF8String | |
| 687 << ", error code: " << error.code; | |
| 688 } | |
| 689 device_mac->DidDisconnectPeripheral(error); | 693 device_mac->DidDisconnectPeripheral(error); |
| 690 } | 694 } |
| 691 | 695 |
| 692 BluetoothLowEnergyDeviceMac* | 696 BluetoothLowEnergyDeviceMac* |
| 693 BluetoothAdapterMac::GetBluetoothLowEnergyDeviceMac(CBPeripheral* peripheral) { | 697 BluetoothAdapterMac::GetBluetoothLowEnergyDeviceMac(CBPeripheral* peripheral) { |
| 694 std::string device_address = | 698 std::string device_address = |
| 695 BluetoothLowEnergyDeviceMac::GetPeripheralHashAddress(peripheral); | 699 BluetoothLowEnergyDeviceMac::GetPeripheralHashAddress(peripheral); |
| 696 auto iter = devices_.find(device_address); | 700 auto iter = devices_.find(device_address); |
| 697 if (iter == devices_.end()) { | 701 if (iter == devices_.end()) { |
| 698 return nil; | 702 return nil; |
| (...skipping 17 matching lines...) Expand all Loading... |
| 716 // hash the probability of this occuring with 10,000 devices | 720 // hash the probability of this occuring with 10,000 devices |
| 717 // simultaneously present is 1e-6 (see | 721 // simultaneously present is 1e-6 (see |
| 718 // https://en.wikipedia.org/wiki/Birthday_problem#Probability_table). We | 722 // https://en.wikipedia.org/wiki/Birthday_problem#Probability_table). We |
| 719 // ignore the second device by returning. | 723 // ignore the second device by returning. |
| 720 return true; | 724 return true; |
| 721 } | 725 } |
| 722 return false; | 726 return false; |
| 723 } | 727 } |
| 724 | 728 |
| 725 } // namespace device | 729 } // namespace device |
| OLD | NEW |