Loading system/service/hal/bluetooth_gatt_interface.cpp +65 −3 Original line number Original line Diff line number Diff line Loading @@ -37,15 +37,21 @@ BluetoothGattInterface* g_interface = nullptr; // Mutex used by callbacks to access |g_interface|. // Mutex used by callbacks to access |g_interface|. mutex g_instance_lock; mutex g_instance_lock; // Helper for obtaining the client observer list. This is forward declared here // Helper for obtaining the observer lists. This is forward declared here // and defined below since it depends on BluetoothInterfaceImpl. // and defined below since it depends on BluetoothInterfaceImpl. base::ObserverList<BluetoothGattInterface::ClientObserver>* base::ObserverList<BluetoothGattInterface::ClientObserver>* GetClientObservers(); GetClientObservers(); base::ObserverList<BluetoothGattInterface::ServerObserver>* GetServerObservers(); #define FOR_EACH_CLIENT_OBSERVER(func) \ #define FOR_EACH_CLIENT_OBSERVER(func) \ FOR_EACH_OBSERVER(BluetoothGattInterface::ClientObserver, \ FOR_EACH_OBSERVER(BluetoothGattInterface::ClientObserver, \ *GetClientObservers(), func) *GetClientObservers(), func) #define FOR_EACH_SERVER_OBSERVER(func) \ FOR_EACH_OBSERVER(BluetoothGattInterface::ServerObserver, \ *GetServerObservers(), func) #define VERIFY_INTERFACE_OR_RETURN() \ #define VERIFY_INTERFACE_OR_RETURN() \ if (!g_interface) { \ if (!g_interface) { \ LOG(WARNING) << "Callback received after |g_interface| is NULL"; \ LOG(WARNING) << "Callback received after |g_interface| is NULL"; \ Loading Loading @@ -102,6 +108,20 @@ void MultiAdvDisableCallback(int client_if, int status) { MultiAdvDisableCallback(g_interface, client_if, status)); MultiAdvDisableCallback(g_interface, client_if, status)); } } void RegisterServerCallback(int status, int server_if, bt_uuid_t* app_uuid) { lock_guard<mutex> lock(g_instance_lock); VLOG(2) << __func__ << " - status: " << status << " server_if: " << server_if; VERIFY_INTERFACE_OR_RETURN(); if (!app_uuid) { LOG(WARNING) << "|app_uuid| is NULL; ignoring RegisterServerCallback"; return; } FOR_EACH_SERVER_OBSERVER( RegisterServerCallback(g_interface, status, server_if, *app_uuid)); } // The HAL Bluetooth GATT client interface callbacks. These signal a mixture of // The HAL Bluetooth GATT client interface callbacks. These signal a mixture of // GATT client-role and GAP events. // GATT client-role and GAP events. const btgatt_client_callbacks_t gatt_client_callbacks = { const btgatt_client_callbacks_t gatt_client_callbacks = { Loading Loading @@ -141,7 +161,7 @@ const btgatt_client_callbacks_t gatt_client_callbacks = { }; }; const btgatt_server_callbacks_t gatt_server_callbacks = { const btgatt_server_callbacks_t gatt_server_callbacks = { nullptr, // register_server_cb RegisterServerCallback, nullptr, // connection_cb nullptr, // connection_cb nullptr, // service_added_cb, nullptr, // service_added_cb, nullptr, // included_service_added_cb, nullptr, // included_service_added_cb, Loading Loading @@ -197,10 +217,32 @@ class BluetoothGattInterfaceImpl : public BluetoothGattInterface { client_observers_.RemoveObserver(observer); client_observers_.RemoveObserver(observer); } } void AddServerObserver(ServerObserver* observer) override { lock_guard<mutex> lock(g_instance_lock); AddServerObserverUnsafe(observer); } void RemoveServerObserver(ServerObserver* observer) override { lock_guard<mutex> lock(g_instance_lock); RemoveServerObserverUnsafe(observer); } void AddServerObserverUnsafe(ServerObserver* observer) override { server_observers_.AddObserver(observer); } void RemoveServerObserverUnsafe(ServerObserver* observer) override { server_observers_.RemoveObserver(observer); } const btgatt_client_interface_t* GetClientHALInterface() const override { const btgatt_client_interface_t* GetClientHALInterface() const override { return hal_iface_->client; return hal_iface_->client; } } const btgatt_server_interface_t* GetServerHALInterface() const override { return hal_iface_->server; } // Initialize the interface. // Initialize the interface. bool Initialize() { bool Initialize() { const bt_interface_t* bt_iface = const bt_interface_t* bt_iface = Loading Loading @@ -230,12 +272,17 @@ class BluetoothGattInterfaceImpl : public BluetoothGattInterface { return &client_observers_; return &client_observers_; } } base::ObserverList<ServerObserver>* server_observers() { return &server_observers_; } private: private: // List of observers that are interested in client notifications from us. // List of observers that are interested in notifications from us. // We're not using a base::ObserverListThreadSafe, which it posts observer // We're not using a base::ObserverListThreadSafe, which it posts observer // events automatically on the origin threads, as we want to avoid that // events automatically on the origin threads, as we want to avoid that // overhead and simply forward the events to the upper layer. // overhead and simply forward the events to the upper layer. base::ObserverList<ClientObserver> client_observers_; base::ObserverList<ClientObserver> client_observers_; base::ObserverList<ServerObserver> server_observers_; // The HAL handle obtained from the shared library. We hold a weak reference // The HAL handle obtained from the shared library. We hold a weak reference // to this since the actual data resides in the shared Bluetooth library. // to this since the actual data resides in the shared Bluetooth library. Loading @@ -253,6 +300,13 @@ GetClientObservers() { g_interface)->client_observers(); g_interface)->client_observers(); } } base::ObserverList<BluetoothGattInterface::ServerObserver>* GetServerObservers() { CHECK(g_interface); return static_cast<BluetoothGattInterfaceImpl*>( g_interface)->server_observers(); } } // namespace } // namespace // Default observer implementations. These are provided so that the methods // Default observer implementations. These are provided so that the methods Loading Loading @@ -289,6 +343,14 @@ void BluetoothGattInterface::ClientObserver::MultiAdvDisableCallback( // Do nothing. // Do nothing. } } void BluetoothGattInterface::ServerObserver::RegisterServerCallback( BluetoothGattInterface* /* gatt_iface */, int /* status */, int /* server_if */, const bt_uuid_t& /* app_uuid */) { // Do nothing. } // static // static bool BluetoothGattInterface::Initialize() { bool BluetoothGattInterface::Initialize() { lock_guard<mutex> lock(g_instance_lock); lock_guard<mutex> lock(g_instance_lock); Loading system/service/hal/bluetooth_gatt_interface.h +36 −1 Original line number Original line Diff line number Diff line Loading @@ -68,6 +68,19 @@ class BluetoothGattInterface { // TODO(armansito): Complete the list of callbacks. // TODO(armansito): Complete the list of callbacks. }; }; // The standard BT-GATT server callback interface. class ServerObserver { public: virtual ~ServerObserver() = default; virtual void RegisterServerCallback( BluetoothGattInterface* gatt_iface, int status, int server_if, const bt_uuid_t& app_uuid); // TODO(armansito): Complete the list of callbacks. }; // Initialize and clean up the BluetoothInterface singleton. Returns false if // Initialize and clean up the BluetoothInterface singleton. Returns false if // the underlying HAL interface failed to initialize, and true on success. // the underlying HAL interface failed to initialize, and true on success. static bool Initialize(); static bool Initialize(); Loading Loading @@ -106,6 +119,22 @@ class BluetoothGattInterface { virtual void AddClientObserverUnsafe(ClientObserver* observer) = 0; virtual void AddClientObserverUnsafe(ClientObserver* observer) = 0; virtual void RemoveClientObserverUnsafe(ClientObserver* observer) = 0; virtual void RemoveClientObserverUnsafe(ClientObserver* observer) = 0; // Add or remove an observer that is interested in GATT server interface // notifications from us. These methods are thread-safe. This implies that // this cannot be called re-entrantly from a ServerObserver event without // causing a dead-lock. If you must modify the observer list re-entrantly, use // the unsafe variants instead. virtual void AddServerObserver(ServerObserver* observer) = 0; virtual void RemoveServerObserver(ServerObserver* observer) = 0; // Unsafe variants of the Add|RemoveServerObserver methods above. The above // methods acquire an internal lock to prevent concurrent access to the // observer list while the unsafe ones don't, so use them wisely. One // recommended use of these methods is from observer methods where the // internal lock is already being held by the executing thread. virtual void AddServerObserverUnsafe(ServerObserver* observer) = 0; virtual void RemoveServerObserverUnsafe(ServerObserver* observer) = 0; // The HAL module pointer that represents the standard BT-GATT client // The HAL module pointer that represents the standard BT-GATT client // interface. This is implemented in and provided by the shared Bluetooth // interface. This is implemented in and provided by the shared Bluetooth // library, so this isn't owned by us. // library, so this isn't owned by us. Loading @@ -114,7 +143,13 @@ class BluetoothGattInterface { // structure. // structure. virtual const btgatt_client_interface_t* GetClientHALInterface() const = 0; virtual const btgatt_client_interface_t* GetClientHALInterface() const = 0; // TODO(armansito): Add getter for server handle. // The HAL module pointer that represents the standard BT-GATT server // interface. This is implemented in and provided by the shared Bluetooth // library, so this isn't owned by us. // // Upper layers can make btgatt_server_interface_t API calls through this // structure. virtual const btgatt_server_interface_t* GetServerHALInterface() const = 0; protected: protected: BluetoothGattInterface() = default; BluetoothGattInterface() = default; Loading system/service/hal/fake_bluetooth_gatt_interface.cpp +125 −53 Original line number Original line Diff line number Diff line Loading @@ -20,21 +20,22 @@ namespace bluetooth { namespace hal { namespace hal { namespace { namespace { // The global TestHandler instance. We have to use this since the HAL interface // The global test handler instances. We have to have globals since the HAL // methods all have to be global and their signatures don't allow us to pass in // interface methods all have to be global and their signatures don't allow us // user_data. // to pass in user_data. std::shared_ptr<FakeBluetoothGattInterface::TestHandler> g_handler; std::shared_ptr<FakeBluetoothGattInterface::TestClientHandler> g_client_handler; std::shared_ptr<FakeBluetoothGattInterface::TestServerHandler> g_server_handler; bt_status_t FakeRegisterClient(bt_uuid_t* app_uuid) { bt_status_t FakeRegisterClient(bt_uuid_t* app_uuid) { if (g_handler.get()) if (g_client_handler) return g_handler->RegisterClient(app_uuid); return g_client_handler->RegisterClient(app_uuid); return BT_STATUS_FAIL; return BT_STATUS_FAIL; } } bt_status_t FakeUnregisterClient(int client_if) { bt_status_t FakeUnregisterClient(int client_if) { if (g_handler.get()) if (g_client_handler) return g_handler->UnregisterClient(client_if); return g_client_handler->UnregisterClient(client_if); return BT_STATUS_FAIL; return BT_STATUS_FAIL; } } Loading @@ -42,8 +43,8 @@ bt_status_t FakeUnregisterClient(int client_if) { bt_status_t FakeMultiAdvEnable( bt_status_t FakeMultiAdvEnable( int client_if, int min_interval, int max_interval, int adv_type, int client_if, int min_interval, int max_interval, int adv_type, int chnl_map, int tx_power, int timeout_s) { int chnl_map, int tx_power, int timeout_s) { if (g_handler.get()) if (g_client_handler) return g_handler->MultiAdvEnable(client_if, min_interval, max_interval, return g_client_handler->MultiAdvEnable(client_if, min_interval, max_interval, adv_type, chnl_map, tx_power, timeout_s); adv_type, chnl_map, tx_power, timeout_s); return BT_STATUS_FAIL; return BT_STATUS_FAIL; Loading @@ -55,8 +56,8 @@ bt_status_t FakeMultiAdvSetInstData( int manufacturer_len, char* manufacturer_data, int manufacturer_len, char* manufacturer_data, int service_data_len, char* service_data, int service_data_len, char* service_data, int service_uuid_len, char* service_uuid) { int service_uuid_len, char* service_uuid) { if (g_handler.get()) if (g_client_handler) return g_handler->MultiAdvSetInstData( return g_client_handler->MultiAdvSetInstData( client_if, set_scan_rsp, include_name, client_if, set_scan_rsp, include_name, incl_txpower, appearance, incl_txpower, appearance, manufacturer_len, manufacturer_data, manufacturer_len, manufacturer_data, Loading @@ -67,8 +68,22 @@ bt_status_t FakeMultiAdvSetInstData( } } bt_status_t FakeMultiAdvDisable(int client_if) { bt_status_t FakeMultiAdvDisable(int client_if) { if (g_handler.get()) if (g_client_handler) return g_handler->MultiAdvDisable(client_if); return g_client_handler->MultiAdvDisable(client_if); return BT_STATUS_FAIL; } bt_status_t FakeRegisterServer(bt_uuid_t* app_uuid) { if (g_server_handler) return g_server_handler->RegisterServer(app_uuid); return BT_STATUS_FAIL; } bt_status_t FakeUnregisterServer(int server_if) { if (g_server_handler) return g_server_handler->UnregisterServer(server_if); return BT_STATUS_FAIL; return BT_STATUS_FAIL; } } Loading @@ -76,58 +91,82 @@ bt_status_t FakeMultiAdvDisable(int client_if) { btgatt_client_interface_t fake_btgattc_iface = { btgatt_client_interface_t fake_btgattc_iface = { FakeRegisterClient, FakeRegisterClient, FakeUnregisterClient, FakeUnregisterClient, nullptr, /* scan */ nullptr, // scan nullptr, /* connect */ nullptr, // connect nullptr, /* disconnect */ nullptr, // disconnect nullptr, /* listen */ nullptr, // listen nullptr, /* refresh */ nullptr, // refresh nullptr, /* search_service */ nullptr, // search_service nullptr, /* get_included_service */ nullptr, // get_included_service nullptr, /* get_characteristic */ nullptr, // get_characteristic nullptr, /* get_descriptor */ nullptr, // get_descriptor nullptr, /* read_characteristic */ nullptr, // read_characteristic nullptr, /* write_characteristic */ nullptr, // write_characteristic nullptr, /* read_descriptor */ nullptr, // read_descriptor nullptr, /* write_descriptor */ nullptr, // write_descriptor nullptr, /* execute_write */ nullptr, // execute_write nullptr, /* register_for_notification */ nullptr, // register_for_notification nullptr, /* deregister_for_notification */ nullptr, // deregister_for_notification nullptr, /* read_remote_rssi */ nullptr, // read_remote_rssi nullptr, /* scan_filter_param_setup */ nullptr, // scan_filter_param_setup nullptr, /* scan_filter_add_remove */ nullptr, // scan_filter_add_remove nullptr, /* scan_filter_clear */ nullptr, // scan_filter_clear nullptr, /* scan_filter_enable */ nullptr, // scan_filter_enable nullptr, /* get_device_type */ nullptr, // get_device_type nullptr, /* set_adv_data */ nullptr, // set_adv_data nullptr, /* configure_mtu */ nullptr, // configure_mtu nullptr, /* conn_parameter_update */ nullptr, // conn_parameter_update nullptr, /* set_scan_parameters */ nullptr, // set_scan_parameters FakeMultiAdvEnable, FakeMultiAdvEnable, nullptr, /* multi_adv_update */ nullptr, // multi_adv_update FakeMultiAdvSetInstData, FakeMultiAdvSetInstData, FakeMultiAdvDisable, FakeMultiAdvDisable, nullptr, /* batchscan_cfg_storate */ nullptr, // batchscan_cfg_storate nullptr, /* batchscan_enb_batch_scan */ nullptr, // batchscan_enb_batch_scan nullptr, /* batchscan_dis_batch_scan */ nullptr, // batchscan_dis_batch_scan nullptr, /* batchscan_read_reports */ nullptr, // batchscan_read_reports nullptr, /* test_command */ nullptr, // test_command }; btgatt_server_interface_t fake_btgatts_iface = { FakeRegisterServer, FakeUnregisterServer, nullptr, // connect nullptr, // disconnect nullptr, // add_service nullptr, // add_included_service nullptr, // add_characteristic nullptr, // add_descriptor nullptr, // start_service nullptr, // stop_service nullptr, // delete_service nullptr, // send_indication nullptr, // send_response }; }; } // namespace } // namespace FakeBluetoothGattInterface::FakeBluetoothGattInterface( FakeBluetoothGattInterface::FakeBluetoothGattInterface( std::shared_ptr<TestHandler> handler) std::shared_ptr<TestClientHandler> client_handler, : handler_(handler) { std::shared_ptr<TestServerHandler> server_handler) CHECK(!g_handler.get()); : client_handler_(client_handler) { CHECK(!g_client_handler); CHECK(!g_server_handler); // We allow passing NULL. In this case all calls we fail by default. // We allow passing NULL. In this case all calls we fail by default. if (handler.get()) if (client_handler) g_handler = handler; g_client_handler = client_handler; if (server_handler) g_server_handler = server_handler; } } FakeBluetoothGattInterface::~FakeBluetoothGattInterface() { FakeBluetoothGattInterface::~FakeBluetoothGattInterface() { if (g_handler.get()) if (g_client_handler) g_handler = nullptr; g_client_handler = nullptr; if (g_server_handler) g_server_handler = nullptr; } } // The methods below can be used to notify observers with certain events and // The methods below can be used to notify observers with certain events and Loading Loading @@ -157,6 +196,13 @@ void FakeBluetoothGattInterface::NotifyMultiAdvDisableCallback( MultiAdvDisableCallback(this, client_if, status)); MultiAdvDisableCallback(this, client_if, status)); } } void FakeBluetoothGattInterface::NotifyRegisterServerCallback( int status, int server_if, const bt_uuid_t& app_uuid) { FOR_EACH_OBSERVER(ServerObserver, server_observers_, RegisterServerCallback(this, status, server_if, app_uuid)); } void FakeBluetoothGattInterface::AddClientObserver(ClientObserver* observer) { void FakeBluetoothGattInterface::AddClientObserver(ClientObserver* observer) { CHECK(observer); CHECK(observer); client_observers_.AddObserver(observer); client_observers_.AddObserver(observer); Loading @@ -178,10 +224,36 @@ void FakeBluetoothGattInterface::RemoveClientObserverUnsafe( RemoveClientObserver(observer); RemoveClientObserver(observer); } } void FakeBluetoothGattInterface::AddServerObserver(ServerObserver* observer) { CHECK(observer); server_observers_.AddObserver(observer); } void FakeBluetoothGattInterface::RemoveServerObserver( ServerObserver* observer) { CHECK(observer); server_observers_.RemoveObserver(observer); } void FakeBluetoothGattInterface::AddServerObserverUnsafe( ServerObserver* observer) { AddServerObserver(observer); } void FakeBluetoothGattInterface::RemoveServerObserverUnsafe( ServerObserver* observer) { RemoveServerObserver(observer); } const btgatt_client_interface_t* const btgatt_client_interface_t* FakeBluetoothGattInterface::GetClientHALInterface() const { FakeBluetoothGattInterface::GetClientHALInterface() const { return &fake_btgattc_iface; return &fake_btgattc_iface; } } const btgatt_server_interface_t* FakeBluetoothGattInterface::GetServerHALInterface() const { return &fake_btgatts_iface; } } // namespace hal } // namespace hal } // namespace bluetooth } // namespace bluetooth system/service/hal/fake_bluetooth_gatt_interface.h +30 −7 Original line number Original line Diff line number Diff line Loading @@ -26,11 +26,12 @@ namespace hal { class FakeBluetoothGattInterface : public BluetoothGattInterface { class FakeBluetoothGattInterface : public BluetoothGattInterface { public: public: // Handles HAL Bluetooth API calls for testing. Test code can provide a fake // Handles HAL Bluetooth GATT client API calls for testing. Test code can // or mock implementation of this and all calls will be routed to it. // provide a fake or mock implementation of this and all calls will be routed class TestHandler { // to it. class TestClientHandler { public: public: virtual ~TestHandler() = default; virtual ~TestClientHandler() = default; virtual bt_status_t RegisterClient(bt_uuid_t* app_uuid) = 0; virtual bt_status_t RegisterClient(bt_uuid_t* app_uuid) = 0; virtual bt_status_t UnregisterClient(int client_if) = 0; virtual bt_status_t UnregisterClient(int client_if) = 0; Loading @@ -46,10 +47,22 @@ class FakeBluetoothGattInterface : public BluetoothGattInterface { virtual bt_status_t MultiAdvDisable(int client_if) = 0; virtual bt_status_t MultiAdvDisable(int client_if) = 0; }; }; // Constructs the fake with the given handler |handler|. Implementations can // Handles HAL Bluetooth GATT server API calls for testing. Test code can // provide a fake or mock implementation of this and all calls will be routed // to it. class TestServerHandler { public: virtual ~TestServerHandler() = default; virtual bt_status_t RegisterServer(bt_uuid_t* app_uuid) = 0; virtual bt_status_t UnregisterServer(int server_if) = 0; }; // Constructs the fake with the given handlers. Implementations can // provide their own handlers or simply pass "nullptr" for the default // provide their own handlers or simply pass "nullptr" for the default // behavior in which BT_STATUS_FAIL will be returned from all calls. // behavior in which BT_STATUS_FAIL will be returned from all calls. FakeBluetoothGattInterface(std::shared_ptr<TestHandler> handler); FakeBluetoothGattInterface(std::shared_ptr<TestClientHandler> client_handler, std::shared_ptr<TestServerHandler> server_handler); ~FakeBluetoothGattInterface(); ~FakeBluetoothGattInterface(); // The methods below can be used to notify observers with certain events and // The methods below can be used to notify observers with certain events and Loading @@ -60,16 +73,26 @@ class FakeBluetoothGattInterface : public BluetoothGattInterface { void NotifyMultiAdvDataCallback(int client_if, int status); void NotifyMultiAdvDataCallback(int client_if, int status); void NotifyMultiAdvDisableCallback(int client_if, int status); void NotifyMultiAdvDisableCallback(int client_if, int status); void NotifyRegisterServerCallback(int status, int server_if, const bt_uuid_t& app_uuid); // BluetoothGattInterface overrides: // BluetoothGattInterface overrides: void AddClientObserver(ClientObserver* observer) override; void AddClientObserver(ClientObserver* observer) override; void RemoveClientObserver(ClientObserver* observer) override; void RemoveClientObserver(ClientObserver* observer) override; void AddClientObserverUnsafe(ClientObserver* observer) override; void AddClientObserverUnsafe(ClientObserver* observer) override; void RemoveClientObserverUnsafe(ClientObserver* observer) override; void RemoveClientObserverUnsafe(ClientObserver* observer) override; void AddServerObserver(ServerObserver* observer) override; void RemoveServerObserver(ServerObserver* observer) override; void AddServerObserverUnsafe(ServerObserver* observer) override; void RemoveServerObserverUnsafe(ServerObserver* observer) override; const btgatt_client_interface_t* GetClientHALInterface() const override; const btgatt_client_interface_t* GetClientHALInterface() const override; const btgatt_server_interface_t* GetServerHALInterface() const override; private: private: base::ObserverList<ClientObserver> client_observers_; base::ObserverList<ClientObserver> client_observers_; std::shared_ptr<TestHandler> handler_; base::ObserverList<ServerObserver> server_observers_; std::shared_ptr<TestClientHandler> client_handler_; std::shared_ptr<TestServerHandler> server_handler_; DISALLOW_COPY_AND_ASSIGN(FakeBluetoothGattInterface); DISALLOW_COPY_AND_ASSIGN(FakeBluetoothGattInterface); }; }; Loading system/service/test/adapter_unittest.cpp +2 −2 Original line number Original line Diff line number Diff line Loading @@ -34,9 +34,9 @@ class AdapterTest : public ::testing::Test { fake_hal_iface_ = new hal::FakeBluetoothInterface(); fake_hal_iface_ = new hal::FakeBluetoothInterface(); hal::BluetoothInterface::InitializeForTesting(fake_hal_iface_); hal::BluetoothInterface::InitializeForTesting(fake_hal_iface_); // Initialize GATT interface with default handler. // Initialize GATT interface with default handlers. hal::BluetoothGattInterface::InitializeForTesting( hal::BluetoothGattInterface::InitializeForTesting( new hal::FakeBluetoothGattInterface(nullptr)); new hal::FakeBluetoothGattInterface(nullptr, nullptr)); adapter_.reset(new Adapter()); adapter_.reset(new Adapter()); } } Loading Loading
system/service/hal/bluetooth_gatt_interface.cpp +65 −3 Original line number Original line Diff line number Diff line Loading @@ -37,15 +37,21 @@ BluetoothGattInterface* g_interface = nullptr; // Mutex used by callbacks to access |g_interface|. // Mutex used by callbacks to access |g_interface|. mutex g_instance_lock; mutex g_instance_lock; // Helper for obtaining the client observer list. This is forward declared here // Helper for obtaining the observer lists. This is forward declared here // and defined below since it depends on BluetoothInterfaceImpl. // and defined below since it depends on BluetoothInterfaceImpl. base::ObserverList<BluetoothGattInterface::ClientObserver>* base::ObserverList<BluetoothGattInterface::ClientObserver>* GetClientObservers(); GetClientObservers(); base::ObserverList<BluetoothGattInterface::ServerObserver>* GetServerObservers(); #define FOR_EACH_CLIENT_OBSERVER(func) \ #define FOR_EACH_CLIENT_OBSERVER(func) \ FOR_EACH_OBSERVER(BluetoothGattInterface::ClientObserver, \ FOR_EACH_OBSERVER(BluetoothGattInterface::ClientObserver, \ *GetClientObservers(), func) *GetClientObservers(), func) #define FOR_EACH_SERVER_OBSERVER(func) \ FOR_EACH_OBSERVER(BluetoothGattInterface::ServerObserver, \ *GetServerObservers(), func) #define VERIFY_INTERFACE_OR_RETURN() \ #define VERIFY_INTERFACE_OR_RETURN() \ if (!g_interface) { \ if (!g_interface) { \ LOG(WARNING) << "Callback received after |g_interface| is NULL"; \ LOG(WARNING) << "Callback received after |g_interface| is NULL"; \ Loading Loading @@ -102,6 +108,20 @@ void MultiAdvDisableCallback(int client_if, int status) { MultiAdvDisableCallback(g_interface, client_if, status)); MultiAdvDisableCallback(g_interface, client_if, status)); } } void RegisterServerCallback(int status, int server_if, bt_uuid_t* app_uuid) { lock_guard<mutex> lock(g_instance_lock); VLOG(2) << __func__ << " - status: " << status << " server_if: " << server_if; VERIFY_INTERFACE_OR_RETURN(); if (!app_uuid) { LOG(WARNING) << "|app_uuid| is NULL; ignoring RegisterServerCallback"; return; } FOR_EACH_SERVER_OBSERVER( RegisterServerCallback(g_interface, status, server_if, *app_uuid)); } // The HAL Bluetooth GATT client interface callbacks. These signal a mixture of // The HAL Bluetooth GATT client interface callbacks. These signal a mixture of // GATT client-role and GAP events. // GATT client-role and GAP events. const btgatt_client_callbacks_t gatt_client_callbacks = { const btgatt_client_callbacks_t gatt_client_callbacks = { Loading Loading @@ -141,7 +161,7 @@ const btgatt_client_callbacks_t gatt_client_callbacks = { }; }; const btgatt_server_callbacks_t gatt_server_callbacks = { const btgatt_server_callbacks_t gatt_server_callbacks = { nullptr, // register_server_cb RegisterServerCallback, nullptr, // connection_cb nullptr, // connection_cb nullptr, // service_added_cb, nullptr, // service_added_cb, nullptr, // included_service_added_cb, nullptr, // included_service_added_cb, Loading Loading @@ -197,10 +217,32 @@ class BluetoothGattInterfaceImpl : public BluetoothGattInterface { client_observers_.RemoveObserver(observer); client_observers_.RemoveObserver(observer); } } void AddServerObserver(ServerObserver* observer) override { lock_guard<mutex> lock(g_instance_lock); AddServerObserverUnsafe(observer); } void RemoveServerObserver(ServerObserver* observer) override { lock_guard<mutex> lock(g_instance_lock); RemoveServerObserverUnsafe(observer); } void AddServerObserverUnsafe(ServerObserver* observer) override { server_observers_.AddObserver(observer); } void RemoveServerObserverUnsafe(ServerObserver* observer) override { server_observers_.RemoveObserver(observer); } const btgatt_client_interface_t* GetClientHALInterface() const override { const btgatt_client_interface_t* GetClientHALInterface() const override { return hal_iface_->client; return hal_iface_->client; } } const btgatt_server_interface_t* GetServerHALInterface() const override { return hal_iface_->server; } // Initialize the interface. // Initialize the interface. bool Initialize() { bool Initialize() { const bt_interface_t* bt_iface = const bt_interface_t* bt_iface = Loading Loading @@ -230,12 +272,17 @@ class BluetoothGattInterfaceImpl : public BluetoothGattInterface { return &client_observers_; return &client_observers_; } } base::ObserverList<ServerObserver>* server_observers() { return &server_observers_; } private: private: // List of observers that are interested in client notifications from us. // List of observers that are interested in notifications from us. // We're not using a base::ObserverListThreadSafe, which it posts observer // We're not using a base::ObserverListThreadSafe, which it posts observer // events automatically on the origin threads, as we want to avoid that // events automatically on the origin threads, as we want to avoid that // overhead and simply forward the events to the upper layer. // overhead and simply forward the events to the upper layer. base::ObserverList<ClientObserver> client_observers_; base::ObserverList<ClientObserver> client_observers_; base::ObserverList<ServerObserver> server_observers_; // The HAL handle obtained from the shared library. We hold a weak reference // The HAL handle obtained from the shared library. We hold a weak reference // to this since the actual data resides in the shared Bluetooth library. // to this since the actual data resides in the shared Bluetooth library. Loading @@ -253,6 +300,13 @@ GetClientObservers() { g_interface)->client_observers(); g_interface)->client_observers(); } } base::ObserverList<BluetoothGattInterface::ServerObserver>* GetServerObservers() { CHECK(g_interface); return static_cast<BluetoothGattInterfaceImpl*>( g_interface)->server_observers(); } } // namespace } // namespace // Default observer implementations. These are provided so that the methods // Default observer implementations. These are provided so that the methods Loading Loading @@ -289,6 +343,14 @@ void BluetoothGattInterface::ClientObserver::MultiAdvDisableCallback( // Do nothing. // Do nothing. } } void BluetoothGattInterface::ServerObserver::RegisterServerCallback( BluetoothGattInterface* /* gatt_iface */, int /* status */, int /* server_if */, const bt_uuid_t& /* app_uuid */) { // Do nothing. } // static // static bool BluetoothGattInterface::Initialize() { bool BluetoothGattInterface::Initialize() { lock_guard<mutex> lock(g_instance_lock); lock_guard<mutex> lock(g_instance_lock); Loading
system/service/hal/bluetooth_gatt_interface.h +36 −1 Original line number Original line Diff line number Diff line Loading @@ -68,6 +68,19 @@ class BluetoothGattInterface { // TODO(armansito): Complete the list of callbacks. // TODO(armansito): Complete the list of callbacks. }; }; // The standard BT-GATT server callback interface. class ServerObserver { public: virtual ~ServerObserver() = default; virtual void RegisterServerCallback( BluetoothGattInterface* gatt_iface, int status, int server_if, const bt_uuid_t& app_uuid); // TODO(armansito): Complete the list of callbacks. }; // Initialize and clean up the BluetoothInterface singleton. Returns false if // Initialize and clean up the BluetoothInterface singleton. Returns false if // the underlying HAL interface failed to initialize, and true on success. // the underlying HAL interface failed to initialize, and true on success. static bool Initialize(); static bool Initialize(); Loading Loading @@ -106,6 +119,22 @@ class BluetoothGattInterface { virtual void AddClientObserverUnsafe(ClientObserver* observer) = 0; virtual void AddClientObserverUnsafe(ClientObserver* observer) = 0; virtual void RemoveClientObserverUnsafe(ClientObserver* observer) = 0; virtual void RemoveClientObserverUnsafe(ClientObserver* observer) = 0; // Add or remove an observer that is interested in GATT server interface // notifications from us. These methods are thread-safe. This implies that // this cannot be called re-entrantly from a ServerObserver event without // causing a dead-lock. If you must modify the observer list re-entrantly, use // the unsafe variants instead. virtual void AddServerObserver(ServerObserver* observer) = 0; virtual void RemoveServerObserver(ServerObserver* observer) = 0; // Unsafe variants of the Add|RemoveServerObserver methods above. The above // methods acquire an internal lock to prevent concurrent access to the // observer list while the unsafe ones don't, so use them wisely. One // recommended use of these methods is from observer methods where the // internal lock is already being held by the executing thread. virtual void AddServerObserverUnsafe(ServerObserver* observer) = 0; virtual void RemoveServerObserverUnsafe(ServerObserver* observer) = 0; // The HAL module pointer that represents the standard BT-GATT client // The HAL module pointer that represents the standard BT-GATT client // interface. This is implemented in and provided by the shared Bluetooth // interface. This is implemented in and provided by the shared Bluetooth // library, so this isn't owned by us. // library, so this isn't owned by us. Loading @@ -114,7 +143,13 @@ class BluetoothGattInterface { // structure. // structure. virtual const btgatt_client_interface_t* GetClientHALInterface() const = 0; virtual const btgatt_client_interface_t* GetClientHALInterface() const = 0; // TODO(armansito): Add getter for server handle. // The HAL module pointer that represents the standard BT-GATT server // interface. This is implemented in and provided by the shared Bluetooth // library, so this isn't owned by us. // // Upper layers can make btgatt_server_interface_t API calls through this // structure. virtual const btgatt_server_interface_t* GetServerHALInterface() const = 0; protected: protected: BluetoothGattInterface() = default; BluetoothGattInterface() = default; Loading
system/service/hal/fake_bluetooth_gatt_interface.cpp +125 −53 Original line number Original line Diff line number Diff line Loading @@ -20,21 +20,22 @@ namespace bluetooth { namespace hal { namespace hal { namespace { namespace { // The global TestHandler instance. We have to use this since the HAL interface // The global test handler instances. We have to have globals since the HAL // methods all have to be global and their signatures don't allow us to pass in // interface methods all have to be global and their signatures don't allow us // user_data. // to pass in user_data. std::shared_ptr<FakeBluetoothGattInterface::TestHandler> g_handler; std::shared_ptr<FakeBluetoothGattInterface::TestClientHandler> g_client_handler; std::shared_ptr<FakeBluetoothGattInterface::TestServerHandler> g_server_handler; bt_status_t FakeRegisterClient(bt_uuid_t* app_uuid) { bt_status_t FakeRegisterClient(bt_uuid_t* app_uuid) { if (g_handler.get()) if (g_client_handler) return g_handler->RegisterClient(app_uuid); return g_client_handler->RegisterClient(app_uuid); return BT_STATUS_FAIL; return BT_STATUS_FAIL; } } bt_status_t FakeUnregisterClient(int client_if) { bt_status_t FakeUnregisterClient(int client_if) { if (g_handler.get()) if (g_client_handler) return g_handler->UnregisterClient(client_if); return g_client_handler->UnregisterClient(client_if); return BT_STATUS_FAIL; return BT_STATUS_FAIL; } } Loading @@ -42,8 +43,8 @@ bt_status_t FakeUnregisterClient(int client_if) { bt_status_t FakeMultiAdvEnable( bt_status_t FakeMultiAdvEnable( int client_if, int min_interval, int max_interval, int adv_type, int client_if, int min_interval, int max_interval, int adv_type, int chnl_map, int tx_power, int timeout_s) { int chnl_map, int tx_power, int timeout_s) { if (g_handler.get()) if (g_client_handler) return g_handler->MultiAdvEnable(client_if, min_interval, max_interval, return g_client_handler->MultiAdvEnable(client_if, min_interval, max_interval, adv_type, chnl_map, tx_power, timeout_s); adv_type, chnl_map, tx_power, timeout_s); return BT_STATUS_FAIL; return BT_STATUS_FAIL; Loading @@ -55,8 +56,8 @@ bt_status_t FakeMultiAdvSetInstData( int manufacturer_len, char* manufacturer_data, int manufacturer_len, char* manufacturer_data, int service_data_len, char* service_data, int service_data_len, char* service_data, int service_uuid_len, char* service_uuid) { int service_uuid_len, char* service_uuid) { if (g_handler.get()) if (g_client_handler) return g_handler->MultiAdvSetInstData( return g_client_handler->MultiAdvSetInstData( client_if, set_scan_rsp, include_name, client_if, set_scan_rsp, include_name, incl_txpower, appearance, incl_txpower, appearance, manufacturer_len, manufacturer_data, manufacturer_len, manufacturer_data, Loading @@ -67,8 +68,22 @@ bt_status_t FakeMultiAdvSetInstData( } } bt_status_t FakeMultiAdvDisable(int client_if) { bt_status_t FakeMultiAdvDisable(int client_if) { if (g_handler.get()) if (g_client_handler) return g_handler->MultiAdvDisable(client_if); return g_client_handler->MultiAdvDisable(client_if); return BT_STATUS_FAIL; } bt_status_t FakeRegisterServer(bt_uuid_t* app_uuid) { if (g_server_handler) return g_server_handler->RegisterServer(app_uuid); return BT_STATUS_FAIL; } bt_status_t FakeUnregisterServer(int server_if) { if (g_server_handler) return g_server_handler->UnregisterServer(server_if); return BT_STATUS_FAIL; return BT_STATUS_FAIL; } } Loading @@ -76,58 +91,82 @@ bt_status_t FakeMultiAdvDisable(int client_if) { btgatt_client_interface_t fake_btgattc_iface = { btgatt_client_interface_t fake_btgattc_iface = { FakeRegisterClient, FakeRegisterClient, FakeUnregisterClient, FakeUnregisterClient, nullptr, /* scan */ nullptr, // scan nullptr, /* connect */ nullptr, // connect nullptr, /* disconnect */ nullptr, // disconnect nullptr, /* listen */ nullptr, // listen nullptr, /* refresh */ nullptr, // refresh nullptr, /* search_service */ nullptr, // search_service nullptr, /* get_included_service */ nullptr, // get_included_service nullptr, /* get_characteristic */ nullptr, // get_characteristic nullptr, /* get_descriptor */ nullptr, // get_descriptor nullptr, /* read_characteristic */ nullptr, // read_characteristic nullptr, /* write_characteristic */ nullptr, // write_characteristic nullptr, /* read_descriptor */ nullptr, // read_descriptor nullptr, /* write_descriptor */ nullptr, // write_descriptor nullptr, /* execute_write */ nullptr, // execute_write nullptr, /* register_for_notification */ nullptr, // register_for_notification nullptr, /* deregister_for_notification */ nullptr, // deregister_for_notification nullptr, /* read_remote_rssi */ nullptr, // read_remote_rssi nullptr, /* scan_filter_param_setup */ nullptr, // scan_filter_param_setup nullptr, /* scan_filter_add_remove */ nullptr, // scan_filter_add_remove nullptr, /* scan_filter_clear */ nullptr, // scan_filter_clear nullptr, /* scan_filter_enable */ nullptr, // scan_filter_enable nullptr, /* get_device_type */ nullptr, // get_device_type nullptr, /* set_adv_data */ nullptr, // set_adv_data nullptr, /* configure_mtu */ nullptr, // configure_mtu nullptr, /* conn_parameter_update */ nullptr, // conn_parameter_update nullptr, /* set_scan_parameters */ nullptr, // set_scan_parameters FakeMultiAdvEnable, FakeMultiAdvEnable, nullptr, /* multi_adv_update */ nullptr, // multi_adv_update FakeMultiAdvSetInstData, FakeMultiAdvSetInstData, FakeMultiAdvDisable, FakeMultiAdvDisable, nullptr, /* batchscan_cfg_storate */ nullptr, // batchscan_cfg_storate nullptr, /* batchscan_enb_batch_scan */ nullptr, // batchscan_enb_batch_scan nullptr, /* batchscan_dis_batch_scan */ nullptr, // batchscan_dis_batch_scan nullptr, /* batchscan_read_reports */ nullptr, // batchscan_read_reports nullptr, /* test_command */ nullptr, // test_command }; btgatt_server_interface_t fake_btgatts_iface = { FakeRegisterServer, FakeUnregisterServer, nullptr, // connect nullptr, // disconnect nullptr, // add_service nullptr, // add_included_service nullptr, // add_characteristic nullptr, // add_descriptor nullptr, // start_service nullptr, // stop_service nullptr, // delete_service nullptr, // send_indication nullptr, // send_response }; }; } // namespace } // namespace FakeBluetoothGattInterface::FakeBluetoothGattInterface( FakeBluetoothGattInterface::FakeBluetoothGattInterface( std::shared_ptr<TestHandler> handler) std::shared_ptr<TestClientHandler> client_handler, : handler_(handler) { std::shared_ptr<TestServerHandler> server_handler) CHECK(!g_handler.get()); : client_handler_(client_handler) { CHECK(!g_client_handler); CHECK(!g_server_handler); // We allow passing NULL. In this case all calls we fail by default. // We allow passing NULL. In this case all calls we fail by default. if (handler.get()) if (client_handler) g_handler = handler; g_client_handler = client_handler; if (server_handler) g_server_handler = server_handler; } } FakeBluetoothGattInterface::~FakeBluetoothGattInterface() { FakeBluetoothGattInterface::~FakeBluetoothGattInterface() { if (g_handler.get()) if (g_client_handler) g_handler = nullptr; g_client_handler = nullptr; if (g_server_handler) g_server_handler = nullptr; } } // The methods below can be used to notify observers with certain events and // The methods below can be used to notify observers with certain events and Loading Loading @@ -157,6 +196,13 @@ void FakeBluetoothGattInterface::NotifyMultiAdvDisableCallback( MultiAdvDisableCallback(this, client_if, status)); MultiAdvDisableCallback(this, client_if, status)); } } void FakeBluetoothGattInterface::NotifyRegisterServerCallback( int status, int server_if, const bt_uuid_t& app_uuid) { FOR_EACH_OBSERVER(ServerObserver, server_observers_, RegisterServerCallback(this, status, server_if, app_uuid)); } void FakeBluetoothGattInterface::AddClientObserver(ClientObserver* observer) { void FakeBluetoothGattInterface::AddClientObserver(ClientObserver* observer) { CHECK(observer); CHECK(observer); client_observers_.AddObserver(observer); client_observers_.AddObserver(observer); Loading @@ -178,10 +224,36 @@ void FakeBluetoothGattInterface::RemoveClientObserverUnsafe( RemoveClientObserver(observer); RemoveClientObserver(observer); } } void FakeBluetoothGattInterface::AddServerObserver(ServerObserver* observer) { CHECK(observer); server_observers_.AddObserver(observer); } void FakeBluetoothGattInterface::RemoveServerObserver( ServerObserver* observer) { CHECK(observer); server_observers_.RemoveObserver(observer); } void FakeBluetoothGattInterface::AddServerObserverUnsafe( ServerObserver* observer) { AddServerObserver(observer); } void FakeBluetoothGattInterface::RemoveServerObserverUnsafe( ServerObserver* observer) { RemoveServerObserver(observer); } const btgatt_client_interface_t* const btgatt_client_interface_t* FakeBluetoothGattInterface::GetClientHALInterface() const { FakeBluetoothGattInterface::GetClientHALInterface() const { return &fake_btgattc_iface; return &fake_btgattc_iface; } } const btgatt_server_interface_t* FakeBluetoothGattInterface::GetServerHALInterface() const { return &fake_btgatts_iface; } } // namespace hal } // namespace hal } // namespace bluetooth } // namespace bluetooth
system/service/hal/fake_bluetooth_gatt_interface.h +30 −7 Original line number Original line Diff line number Diff line Loading @@ -26,11 +26,12 @@ namespace hal { class FakeBluetoothGattInterface : public BluetoothGattInterface { class FakeBluetoothGattInterface : public BluetoothGattInterface { public: public: // Handles HAL Bluetooth API calls for testing. Test code can provide a fake // Handles HAL Bluetooth GATT client API calls for testing. Test code can // or mock implementation of this and all calls will be routed to it. // provide a fake or mock implementation of this and all calls will be routed class TestHandler { // to it. class TestClientHandler { public: public: virtual ~TestHandler() = default; virtual ~TestClientHandler() = default; virtual bt_status_t RegisterClient(bt_uuid_t* app_uuid) = 0; virtual bt_status_t RegisterClient(bt_uuid_t* app_uuid) = 0; virtual bt_status_t UnregisterClient(int client_if) = 0; virtual bt_status_t UnregisterClient(int client_if) = 0; Loading @@ -46,10 +47,22 @@ class FakeBluetoothGattInterface : public BluetoothGattInterface { virtual bt_status_t MultiAdvDisable(int client_if) = 0; virtual bt_status_t MultiAdvDisable(int client_if) = 0; }; }; // Constructs the fake with the given handler |handler|. Implementations can // Handles HAL Bluetooth GATT server API calls for testing. Test code can // provide a fake or mock implementation of this and all calls will be routed // to it. class TestServerHandler { public: virtual ~TestServerHandler() = default; virtual bt_status_t RegisterServer(bt_uuid_t* app_uuid) = 0; virtual bt_status_t UnregisterServer(int server_if) = 0; }; // Constructs the fake with the given handlers. Implementations can // provide their own handlers or simply pass "nullptr" for the default // provide their own handlers or simply pass "nullptr" for the default // behavior in which BT_STATUS_FAIL will be returned from all calls. // behavior in which BT_STATUS_FAIL will be returned from all calls. FakeBluetoothGattInterface(std::shared_ptr<TestHandler> handler); FakeBluetoothGattInterface(std::shared_ptr<TestClientHandler> client_handler, std::shared_ptr<TestServerHandler> server_handler); ~FakeBluetoothGattInterface(); ~FakeBluetoothGattInterface(); // The methods below can be used to notify observers with certain events and // The methods below can be used to notify observers with certain events and Loading @@ -60,16 +73,26 @@ class FakeBluetoothGattInterface : public BluetoothGattInterface { void NotifyMultiAdvDataCallback(int client_if, int status); void NotifyMultiAdvDataCallback(int client_if, int status); void NotifyMultiAdvDisableCallback(int client_if, int status); void NotifyMultiAdvDisableCallback(int client_if, int status); void NotifyRegisterServerCallback(int status, int server_if, const bt_uuid_t& app_uuid); // BluetoothGattInterface overrides: // BluetoothGattInterface overrides: void AddClientObserver(ClientObserver* observer) override; void AddClientObserver(ClientObserver* observer) override; void RemoveClientObserver(ClientObserver* observer) override; void RemoveClientObserver(ClientObserver* observer) override; void AddClientObserverUnsafe(ClientObserver* observer) override; void AddClientObserverUnsafe(ClientObserver* observer) override; void RemoveClientObserverUnsafe(ClientObserver* observer) override; void RemoveClientObserverUnsafe(ClientObserver* observer) override; void AddServerObserver(ServerObserver* observer) override; void RemoveServerObserver(ServerObserver* observer) override; void AddServerObserverUnsafe(ServerObserver* observer) override; void RemoveServerObserverUnsafe(ServerObserver* observer) override; const btgatt_client_interface_t* GetClientHALInterface() const override; const btgatt_client_interface_t* GetClientHALInterface() const override; const btgatt_server_interface_t* GetServerHALInterface() const override; private: private: base::ObserverList<ClientObserver> client_observers_; base::ObserverList<ClientObserver> client_observers_; std::shared_ptr<TestHandler> handler_; base::ObserverList<ServerObserver> server_observers_; std::shared_ptr<TestClientHandler> client_handler_; std::shared_ptr<TestServerHandler> server_handler_; DISALLOW_COPY_AND_ASSIGN(FakeBluetoothGattInterface); DISALLOW_COPY_AND_ASSIGN(FakeBluetoothGattInterface); }; }; Loading
system/service/test/adapter_unittest.cpp +2 −2 Original line number Original line Diff line number Diff line Loading @@ -34,9 +34,9 @@ class AdapterTest : public ::testing::Test { fake_hal_iface_ = new hal::FakeBluetoothInterface(); fake_hal_iface_ = new hal::FakeBluetoothInterface(); hal::BluetoothInterface::InitializeForTesting(fake_hal_iface_); hal::BluetoothInterface::InitializeForTesting(fake_hal_iface_); // Initialize GATT interface with default handler. // Initialize GATT interface with default handlers. hal::BluetoothGattInterface::InitializeForTesting( hal::BluetoothGattInterface::InitializeForTesting( new hal::FakeBluetoothGattInterface(nullptr)); new hal::FakeBluetoothGattInterface(nullptr, nullptr)); adapter_.reset(new Adapter()); adapter_.reset(new Adapter()); } } Loading