Commit bfd3bf43 authored by Qiyu Hu's avatar Qiyu Hu Committed by Commit Bot

arc: bluetooth: Add EIR as part of OnLEDeviceFound

On each LE advertisement event, we forward the event along with the EIR
such that it's closer to the behavior in Android.

Please review along with ag/5453291

Bug: chromium:887029,b:118334521
Test: CtsVerifier
Change-Id: I4f56ef5e30087768acb7e897c5345380ffb7a633
Reviewed-on: https://chromium-review.googlesource.com/c/1321581Reviewed-by: default avatarGreg Kerr <kerrnel@chromium.org>
Reviewed-by: default avatarGiovanni Ortuño Urquidi <ortuno@chromium.org>
Reviewed-by: default avatarHidehiko Abe <hidehiko@chromium.org>
Commit-Queue: Qiyu Hu <qiyuh@google.com>
Cr-Commit-Position: refs/heads/master@{#607362}
parent 3bf97c16
...@@ -24,6 +24,7 @@ ...@@ -24,6 +24,7 @@
#include "base/posix/eintr_wrapper.h" #include "base/posix/eintr_wrapper.h"
#include "base/strings/string_number_conversions.h" #include "base/strings/string_number_conversions.h"
#include "base/strings/utf_string_conversions.h" #include "base/strings/utf_string_conversions.h"
#include "base/sys_info.h"
#include "base/threading/thread_task_runner_handle.h" #include "base/threading/thread_task_runner_handle.h"
#include "base/time/time.h" #include "base/time/time.h"
#include "chrome/browser/chromeos/profiles/profile_helper.h" #include "chrome/browser/chromeos/profiles/profile_helper.h"
...@@ -70,6 +71,16 @@ using device::BluetoothUUID; ...@@ -70,6 +71,16 @@ using device::BluetoothUUID;
namespace { namespace {
base::Optional<int> SdkVersion() {
constexpr char kVersionKey[] = "CHROMEOS_ARC_ANDROID_SDK_VERSION";
int sdk_version;
std::string sdk_str;
if (!base::SysInfo::GetLsbReleaseValue(kVersionKey, &sdk_str) ||
!base::StringToInt(sdk_str, &sdk_version))
return base::nullopt;
return sdk_version;
}
// https://android.googlesource.com/platform/system/bt/+/master/stack/include/gatt_api.h // https://android.googlesource.com/platform/system/bt/+/master/stack/include/gatt_api.h
constexpr int32_t GATT_CHAR_PROP_BIT_BROADCAST = (1 << 0); constexpr int32_t GATT_CHAR_PROP_BIT_BROADCAST = (1 << 0);
constexpr int32_t GATT_CHAR_PROP_BIT_READ = (1 << 1); constexpr int32_t GATT_CHAR_PROP_BIT_READ = (1 << 1);
...@@ -496,25 +507,17 @@ void ArcBluetoothBridge::DeviceChanged(BluetoothAdapter* adapter, ...@@ -496,25 +507,17 @@ void ArcBluetoothBridge::DeviceChanged(BluetoothAdapter* adapter,
if (!arc_bridge_service_->bluetooth()->IsConnected()) if (!arc_bridge_service_->bluetooth()->IsConnected())
return; return;
auto* device_found = ARC_GET_INSTANCE_FOR_METHOD( auto* bluetooth_instance = ARC_GET_INSTANCE_FOR_METHOD(
arc_bridge_service_->bluetooth(), OnDeviceFound); arc_bridge_service_->bluetooth(), OnDeviceFound);
if (device_found) { if (bluetooth_instance) {
device_found->OnDeviceFound( bluetooth_instance->OnDeviceFound(
GetDeviceProperties(mojom::BluetoothPropertyType::ALL, device)); GetDeviceProperties(mojom::BluetoothPropertyType::ALL, device));
} }
if (!(device->GetType() & device::BLUETOOTH_TRANSPORT_LE)) if (!(device->GetType() & device::BLUETOOTH_TRANSPORT_LE))
return; return;
base::Optional<int8_t> rssi = device->GetInquiryRSSI();
std::string addr = device->GetAddress(); std::string addr = device->GetAddress();
auto* le_device_found = ARC_GET_INSTANCE_FOR_METHOD(
arc_bridge_service_->bluetooth(), OnLEDeviceFound);
if (le_device_found && rssi.has_value()) {
le_device_found->OnLEDeviceFound(mojom::BluetoothAddress::From(addr),
rssi.value(), GetAdvertisingData(device));
}
auto it = gatt_connections_.find(addr); auto it = gatt_connections_.find(addr);
bool was_connected = bool was_connected =
(it != gatt_connections_.end() && (it != gatt_connections_.end() &&
...@@ -599,6 +602,33 @@ void ArcBluetoothBridge::DeviceMTUChanged(BluetoothAdapter* adapter, ...@@ -599,6 +602,33 @@ void ArcBluetoothBridge::DeviceMTUChanged(BluetoothAdapter* adapter,
mojom::BluetoothAddress::From(device->GetAddress()), mtu); mojom::BluetoothAddress::From(device->GetAddress()), mtu);
} }
void ArcBluetoothBridge::DeviceAdvertisementReceived(
BluetoothAdapter* adapter,
BluetoothDevice* device,
int16_t rssi,
const std::vector<uint8_t>& eir) {
constexpr int kAndroidPSdkVersion = 28;
base::Optional<int> sdk_version = SdkVersion();
mojom::BluetoothAddressPtr addr =
mojom::BluetoothAddress::From(device->GetAddress());
if (!sdk_version)
return;
if (sdk_version.value() >= kAndroidPSdkVersion) {
auto* bluetooth_instance = ARC_GET_INSTANCE_FOR_METHOD(
arc_bridge_service_->bluetooth(), OnLEDeviceFound);
if (bluetooth_instance)
bluetooth_instance->OnLEDeviceFound(std::move(addr), rssi, eir);
return;
}
auto* bluetooth_instance = ARC_GET_INSTANCE_FOR_METHOD(
arc_bridge_service_->bluetooth(), OnLEDeviceFoundForN);
if (bluetooth_instance)
bluetooth_instance->OnLEDeviceFoundForN(std::move(addr), rssi,
GetAdvertisingData(device));
}
void ArcBluetoothBridge::DeviceRemoved(BluetoothAdapter* adapter, void ArcBluetoothBridge::DeviceRemoved(BluetoothAdapter* adapter,
BluetoothDevice* device) { BluetoothDevice* device) {
if (!arc_bridge_service_->bluetooth()->IsConnected()) if (!arc_bridge_service_->bluetooth()->IsConnected())
......
...@@ -94,6 +94,11 @@ class ArcBluetoothBridge ...@@ -94,6 +94,11 @@ class ArcBluetoothBridge
device::BluetoothDevice* device, device::BluetoothDevice* device,
uint16_t mtu) override; uint16_t mtu) override;
void DeviceAdvertisementReceived(device::BluetoothAdapter* adapter,
device::BluetoothDevice* device,
int16_t rssi,
const std::vector<uint8_t>& eir) override;
void DeviceRemoved(device::BluetoothAdapter* adapter, void DeviceRemoved(device::BluetoothAdapter* adapter,
device::BluetoothDevice* device) override; device::BluetoothDevice* device) override;
......
...@@ -12,6 +12,7 @@ ...@@ -12,6 +12,7 @@
#include "base/message_loop/message_loop.h" #include "base/message_loop/message_loop.h"
#include "base/run_loop.h" #include "base/run_loop.h"
#include "base/strings/stringprintf.h" #include "base/strings/stringprintf.h"
#include "base/sys_info.h"
#include "components/arc/arc_bridge_service.h" #include "components/arc/arc_bridge_service.h"
#include "components/arc/bluetooth/bluetooth_type_converters.h" #include "components/arc/bluetooth/bluetooth_type_converters.h"
#include "components/arc/common/bluetooth.mojom.h" #include "components/arc/common/bluetooth.mojom.h"
...@@ -31,6 +32,7 @@ namespace { ...@@ -31,6 +32,7 @@ namespace {
constexpr int16_t kTestRssi = -50; constexpr int16_t kTestRssi = -50;
constexpr int16_t kTestRssi2 = -70; constexpr int16_t kTestRssi2 = -70;
constexpr char kTestServiceUUID[] = "00001357-0000-1000-8000-00805f9b34fb"; constexpr char kTestServiceUUID[] = "00001357-0000-1000-8000-00805f9b34fb";
const std::vector<uint8_t> kEIR = {0x00, 0x01, 0x02};
} // namespace } // namespace
namespace arc { namespace arc {
...@@ -58,6 +60,9 @@ class ArcBluetoothBridgeTest : public testing::Test { ...@@ -58,6 +60,9 @@ class ArcBluetoothBridgeTest : public testing::Test {
dbus::ObjectPath(bluez::FakeBluetoothDeviceClient::kLowEnergyPath), dbus::ObjectPath(bluez::FakeBluetoothDeviceClient::kLowEnergyPath),
{kTestServiceUUID}, /* service_data = */ {}, {kTestServiceUUID}, /* service_data = */ {},
/* manufacture_data = */ {}); /* manufacture_data = */ {});
fake_bluetooth_device_client->UpdateEIR(
dbus::ObjectPath(bluez::FakeBluetoothDeviceClient::kLowEnergyPath),
kEIR);
fake_bluetooth_gatt_service_client->ExposeHeartRateService( fake_bluetooth_gatt_service_client->ExposeHeartRateService(
dbus::ObjectPath(bluez::FakeBluetoothDeviceClient::kLowEnergyPath)); dbus::ObjectPath(bluez::FakeBluetoothDeviceClient::kLowEnergyPath));
fake_bluetooth_gatt_characteristic_client->ExposeHeartRateCharacteristics( fake_bluetooth_gatt_characteristic_client->ExposeHeartRateCharacteristics(
...@@ -102,7 +107,9 @@ class ArcBluetoothBridgeTest : public testing::Test { ...@@ -102,7 +107,9 @@ class ArcBluetoothBridgeTest : public testing::Test {
nullptr, arc_bridge_service_.get()); nullptr, arc_bridge_service_.get());
fake_bluetooth_instance_ = std::make_unique<FakeBluetoothInstance>(); fake_bluetooth_instance_ = std::make_unique<FakeBluetoothInstance>();
arc_bridge_service_->bluetooth()->SetInstance( arc_bridge_service_->bluetooth()->SetInstance(
fake_bluetooth_instance_.get(), 2); fake_bluetooth_instance_.get(), 13);
base::SysInfo::SetChromeOSVersionInfoForTest(
"CHROMEOS_ARC_ANDROID_SDK_VERSION=28", base::Time::Now());
WaitForInstanceReady(arc_bridge_service_->bluetooth()); WaitForInstanceReady(arc_bridge_service_->bluetooth());
device::BluetoothAdapterFactory::GetAdapter(base::Bind( device::BluetoothAdapterFactory::GetAdapter(base::Bind(
...@@ -256,6 +263,29 @@ TEST_F(ArcBluetoothBridgeTest, LEDeviceFound) { ...@@ -256,6 +263,29 @@ TEST_F(ArcBluetoothBridgeTest, LEDeviceFound) {
AddTestDevice(); AddTestDevice();
EXPECT_EQ(1u, fake_bluetooth_instance_->le_device_found_data().size()); EXPECT_EQ(1u, fake_bluetooth_instance_->le_device_found_data().size());
const auto& le_device_found_data =
fake_bluetooth_instance_->le_device_found_data().back();
const mojom::BluetoothAddressPtr& addr = le_device_found_data->addr();
const std::vector<uint8_t>& eir = le_device_found_data->eir();
EXPECT_EQ(std::string(bluez::FakeBluetoothDeviceClient::kLowEnergyAddress),
addr->To<std::string>());
EXPECT_EQ(kEIR, eir);
EXPECT_EQ(kTestRssi, le_device_found_data->rssi());
ChangeTestDeviceRssi(kTestRssi2);
EXPECT_EQ(2u, fake_bluetooth_instance_->le_device_found_data().size());
EXPECT_EQ(kTestRssi2,
fake_bluetooth_instance_->le_device_found_data().back()->rssi());
}
TEST_F(ArcBluetoothBridgeTest, LEDeviceFoundForN) {
base::SysInfo::SetChromeOSVersionInfoForTest(
"CHROMEOS_ARC_ANDROID_SDK_VERSION=27", base::Time::Now());
EXPECT_EQ(0u, fake_bluetooth_instance_->le_device_found_data().size());
AddTestDevice();
EXPECT_EQ(1u, fake_bluetooth_instance_->le_device_found_data().size());
const auto& le_device_found_data = const auto& le_device_found_data =
fake_bluetooth_instance_->le_device_found_data().back(); fake_bluetooth_instance_->le_device_found_data().back();
const mojom::BluetoothAddressPtr& addr = le_device_found_data->addr(); const mojom::BluetoothAddressPtr& addr = le_device_found_data->addr();
......
...@@ -2,7 +2,7 @@ ...@@ -2,7 +2,7 @@
// Use of this source code is governed by a BSD-style license that can be // Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file. // found in the LICENSE file.
// Next MinVersion: 13 // Next MinVersion: 14
module arc.mojom; module arc.mojom;
...@@ -401,7 +401,7 @@ interface BluetoothHost { ...@@ -401,7 +401,7 @@ interface BluetoothHost {
=> (BluetoothGattStatus status); => (BluetoothGattStatus status);
}; };
// Next Method ID: 21 // Next Method ID: 22
// Deprecated Method ID: 2 // Deprecated Method ID: 2
interface BluetoothInstance { interface BluetoothInstance {
// DEPRECATED: Please use Init@18 instead. // DEPRECATED: Please use Init@18 instead.
...@@ -422,9 +422,14 @@ interface BluetoothInstance { ...@@ -422,9 +422,14 @@ interface BluetoothInstance {
BluetoothAclState state); BluetoothAclState state);
// Bluetooth Gatt Client callbacks // Bluetooth Gatt Client callbacks
[MinVersion=1] OnLEDeviceFound@7(BluetoothAddress addr, // TODO(b/111367421): Remove this when no active device running Android N.
int32 rssi, [MinVersion=1] OnLEDeviceFoundForN@7(
array<BluetoothAdvertisingData> adv_data); BluetoothAddress addr,
int32 rssi,
array<BluetoothAdvertisingData> adv_data);
[MinVersion=13] OnLEDeviceFound@21(BluetoothAddress addr,
int32 rssi,
array<uint8> eir);
[MinVersion=1] OnLEConnectionStateChange@8(BluetoothAddress remote_addr, [MinVersion=1] OnLEConnectionStateChange@8(BluetoothAddress remote_addr,
bool connected); bool connected);
[MinVersion=4] OnLEDeviceAddressChange@16(BluetoothAddress old_addr, [MinVersion=4] OnLEDeviceAddressChange@16(BluetoothAddress old_addr,
......
...@@ -21,10 +21,14 @@ FakeBluetoothInstance::GattDBResult::GattDBResult( ...@@ -21,10 +21,14 @@ FakeBluetoothInstance::GattDBResult::GattDBResult(
FakeBluetoothInstance::GattDBResult::~GattDBResult() {} FakeBluetoothInstance::GattDBResult::~GattDBResult() {}
FakeBluetoothInstance::LEDeviceFoundData::LEDeviceFoundData( FakeBluetoothInstance::LEDeviceFoundData::LEDeviceFoundData(
mojom::BluetoothAddressPtr&& addr, mojom::BluetoothAddressPtr addr,
int32_t rssi, int32_t rssi,
std::vector<mojom::BluetoothAdvertisingDataPtr>&& adv_data) std::vector<mojom::BluetoothAdvertisingDataPtr> adv_data,
: addr_(std::move(addr)), rssi_(rssi), adv_data_(std::move(adv_data)) {} const std::vector<uint8_t>& eir)
: addr_(std::move(addr)),
rssi_(rssi),
adv_data_(std::move(adv_data)),
eir_(std::move(eir)) {}
FakeBluetoothInstance::LEDeviceFoundData::~LEDeviceFoundData() {} FakeBluetoothInstance::LEDeviceFoundData::~LEDeviceFoundData() {}
...@@ -60,12 +64,20 @@ void FakeBluetoothInstance::OnAclStateChanged( ...@@ -60,12 +64,20 @@ void FakeBluetoothInstance::OnAclStateChanged(
mojom::BluetoothAddressPtr remote_addr, mojom::BluetoothAddressPtr remote_addr,
mojom::BluetoothAclState state) {} mojom::BluetoothAclState state) {}
void FakeBluetoothInstance::OnLEDeviceFound( void FakeBluetoothInstance::OnLEDeviceFoundForN(
mojom::BluetoothAddressPtr addr, mojom::BluetoothAddressPtr addr,
int32_t rssi, int32_t rssi,
std::vector<mojom::BluetoothAdvertisingDataPtr> adv_data) { std::vector<mojom::BluetoothAdvertisingDataPtr> adv_data) {
le_device_found_data_.push_back(std::make_unique<LEDeviceFoundData>( le_device_found_data_.push_back(std::make_unique<LEDeviceFoundData>(
std::move(addr), rssi, std::move(adv_data))); std::move(addr), rssi, std::move(adv_data), std::vector<uint8_t>()));
}
void FakeBluetoothInstance::OnLEDeviceFound(mojom::BluetoothAddressPtr addr,
int32_t rssi,
const std::vector<uint8_t>& eir) {
le_device_found_data_.push_back(std::make_unique<LEDeviceFoundData>(
std::move(addr), rssi, std::vector<mojom::BluetoothAdvertisingDataPtr>(),
eir));
} }
void FakeBluetoothInstance::OnLEConnectionStateChange( void FakeBluetoothInstance::OnLEConnectionStateChange(
......
...@@ -43,10 +43,10 @@ class FakeBluetoothInstance : public mojom::BluetoothInstance { ...@@ -43,10 +43,10 @@ class FakeBluetoothInstance : public mojom::BluetoothInstance {
class LEDeviceFoundData { class LEDeviceFoundData {
public: public:
LEDeviceFoundData( LEDeviceFoundData(mojom::BluetoothAddressPtr addr,
mojom::BluetoothAddressPtr&& addr, int32_t rssi,
int32_t rssi, std::vector<mojom::BluetoothAdvertisingDataPtr> adv_data,
std::vector<mojom::BluetoothAdvertisingDataPtr>&& adv_data); const std::vector<uint8_t>& eir);
~LEDeviceFoundData(); ~LEDeviceFoundData();
const mojom::BluetoothAddressPtr& addr() const { return addr_; } const mojom::BluetoothAddressPtr& addr() const { return addr_; }
...@@ -57,10 +57,13 @@ class FakeBluetoothInstance : public mojom::BluetoothInstance { ...@@ -57,10 +57,13 @@ class FakeBluetoothInstance : public mojom::BluetoothInstance {
return adv_data_; return adv_data_;
} }
const std::vector<uint8_t>& eir() const { return eir_; }
private: private:
mojom::BluetoothAddressPtr addr_; mojom::BluetoothAddressPtr addr_;
int32_t rssi_; int32_t rssi_;
std::vector<mojom::BluetoothAdvertisingDataPtr> adv_data_; std::vector<mojom::BluetoothAdvertisingDataPtr> adv_data_;
std::vector<uint8_t> eir_;
DISALLOW_COPY_AND_ASSIGN(LEDeviceFoundData); DISALLOW_COPY_AND_ASSIGN(LEDeviceFoundData);
}; };
...@@ -83,10 +86,13 @@ class FakeBluetoothInstance : public mojom::BluetoothInstance { ...@@ -83,10 +86,13 @@ class FakeBluetoothInstance : public mojom::BluetoothInstance {
void OnAclStateChanged(mojom::BluetoothStatus status, void OnAclStateChanged(mojom::BluetoothStatus status,
mojom::BluetoothAddressPtr remote_addr, mojom::BluetoothAddressPtr remote_addr,
mojom::BluetoothAclState state) override; mojom::BluetoothAclState state) override;
void OnLEDeviceFound( void OnLEDeviceFoundForN(
mojom::BluetoothAddressPtr addr, mojom::BluetoothAddressPtr addr,
int32_t rssi, int32_t rssi,
std::vector<mojom::BluetoothAdvertisingDataPtr> adv_data) override; std::vector<mojom::BluetoothAdvertisingDataPtr> adv_data) override;
void OnLEDeviceFound(mojom::BluetoothAddressPtr addr,
int32_t rssi,
const std::vector<uint8_t>& eir) override;
void OnLEConnectionStateChange(mojom::BluetoothAddressPtr remote_addr, void OnLEConnectionStateChange(mojom::BluetoothAddressPtr remote_addr,
bool connected) override; bool connected) override;
void OnLEDeviceAddressChange(mojom::BluetoothAddressPtr old_addr, void OnLEDeviceAddressChange(mojom::BluetoothAddressPtr old_addr,
......
...@@ -1631,6 +1631,19 @@ void FakeBluetoothDeviceClient::UpdateServiceAndManufacturerData( ...@@ -1631,6 +1631,19 @@ void FakeBluetoothDeviceClient::UpdateServiceAndManufacturerData(
properties->manufacturer_data.ReplaceValue(merged_manufacturer_data); properties->manufacturer_data.ReplaceValue(merged_manufacturer_data);
} }
void FakeBluetoothDeviceClient::UpdateEIR(const dbus::ObjectPath& object_path,
const std::vector<uint8_t>& eir) {
PropertiesMap::const_iterator iter = properties_map_.find(object_path);
if (iter == properties_map_.end()) {
VLOG(2) << "Fake device does not exist: " << object_path.value();
return;
}
Properties* properties = iter->second.get();
DCHECK(properties);
properties->eir.set_valid(true);
properties->eir.ReplaceValue(eir);
}
void FakeBluetoothDeviceClient::UpdateConnectionInfo( void FakeBluetoothDeviceClient::UpdateConnectionInfo(
uint16_t connection_rssi, uint16_t connection_rssi,
uint16_t transmit_power, uint16_t transmit_power,
......
...@@ -195,6 +195,11 @@ class DEVICE_BLUETOOTH_EXPORT FakeBluetoothDeviceClient ...@@ -195,6 +195,11 @@ class DEVICE_BLUETOOTH_EXPORT FakeBluetoothDeviceClient
const std::map<std::string, std::vector<uint8_t>>& service_data, const std::map<std::string, std::vector<uint8_t>>& service_data,
const std::map<uint16_t, std::vector<uint8_t>>& manufacturer_data); const std::map<uint16_t, std::vector<uint8_t>>& manufacturer_data);
// Updates the EIR property of fake device with object path |object_path| to
// |eir|, if the fake device exists.
void UpdateEIR(const dbus::ObjectPath& object_path,
const std::vector<uint8_t>& eir);
// Adds a pending prepare write request to |object_path|. // Adds a pending prepare write request to |object_path|.
void AddPrepareWriteRequest(const dbus::ObjectPath& object_path, void AddPrepareWriteRequest(const dbus::ObjectPath& object_path,
const std::vector<uint8_t>& value); const std::vector<uint8_t>& value);
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment