Home | History | Annotate | Download | only in hal
      1 //
      2 //  Copyright (C) 2015 Google, Inc.
      3 //
      4 //  Licensed under the Apache License, Version 2.0 (the "License");
      5 //  you may not use this file except in compliance with the License.
      6 //  You may obtain a copy of the License at:
      7 //
      8 //  http://www.apache.org/licenses/LICENSE-2.0
      9 //
     10 //  Unless required by applicable law or agreed to in writing, software
     11 //  distributed under the License is distributed on an "AS IS" BASIS,
     12 //  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
     13 //  See the License for the specific language governing permissions and
     14 //  limitations under the License.
     15 //
     16 
     17 #include "service/hal/bluetooth_interface.h"
     18 
     19 #include <mutex>
     20 #define _LIBCPP_BUILDING_SHARED_MUTEX
     21 #include <shared_mutex>
     22 #undef _LIBCPP_BUILDING_SHARED_MUTEX
     23 
     24 #include <base/logging.h>
     25 #include <base/observer_list.h>
     26 
     27 #include "service/logging_helpers.h"
     28 
     29 extern "C" {
     30 #include "btcore/include/hal_util.h"
     31 }  // extern "C"
     32 
     33 using std::lock_guard;
     34 using std::unique_lock;
     35 using std::shared_lock;
     36 using std::mutex;
     37 using std::shared_timed_mutex;
     38 
     39 namespace bluetooth {
     40 namespace hal {
     41 
     42 namespace {
     43 
     44 // The global BluetoothInterface instance.
     45 BluetoothInterface* g_bluetooth_interface = nullptr;
     46 
     47 // Mutex used by callbacks to access |g_interface|. If we initialize or clean it
     48 // use unique_lock. If only accessing |g_interface| use shared lock.
     49 //TODO(jpawlowski): this should be just shared_mutex, as we currently don't use
     50 // timed methods. Change to shared_mutex when we upgrade to C++14
     51 shared_timed_mutex g_instance_lock;
     52 
     53 // Helper for obtaining the observer list. This is forward declared here and
     54 // defined below since it depends on BluetoothInterfaceImpl.
     55 base::ObserverList<BluetoothInterface::Observer>* GetObservers();
     56 
     57 #define FOR_EACH_BLUETOOTH_OBSERVER(func) \
     58   FOR_EACH_OBSERVER(BluetoothInterface::Observer, *GetObservers(), func)
     59 
     60 #define VERIFY_INTERFACE_OR_RETURN() \
     61   do { \
     62     if (!g_bluetooth_interface) { \
     63       LOG(WARNING) << "Callback received while |g_interface| is NULL"; \
     64       return; \
     65     } \
     66   } while (0)
     67 
     68 void AdapterStateChangedCallback(bt_state_t state) {
     69   shared_lock<shared_timed_mutex> lock(g_instance_lock);
     70   VERIFY_INTERFACE_OR_RETURN();
     71   VLOG(1) << "Adapter state changed: " << BtStateText(state);
     72   FOR_EACH_BLUETOOTH_OBSERVER(AdapterStateChangedCallback(state));
     73 }
     74 
     75 void AdapterPropertiesCallback(bt_status_t status,
     76                                int num_properties,
     77                                bt_property_t* properties) {
     78   shared_lock<shared_timed_mutex> lock(g_instance_lock);
     79   VERIFY_INTERFACE_OR_RETURN();
     80   VLOG(1) << "Adapter properties changed - status: " << BtStatusText(status)
     81           << ", num_properties: " << num_properties;
     82   FOR_EACH_BLUETOOTH_OBSERVER(
     83       AdapterPropertiesCallback(status, num_properties, properties));
     84 }
     85 
     86 void RemoteDevicePropertiesCallback(bt_status_t status,
     87                                bt_bdaddr_t *remote_bd_addr,
     88                                int num_properties,
     89                                bt_property_t* properties) {
     90   shared_lock<shared_timed_mutex> lock(g_instance_lock);
     91   VERIFY_INTERFACE_OR_RETURN();
     92   VLOG(1) << " Remote device properties changed - status: " << BtStatusText(status)
     93           << " - BD_ADDR: " << BtAddrString(remote_bd_addr)
     94           << ", num_properties: " << num_properties;
     95   FOR_EACH_BLUETOOTH_OBSERVER(
     96       RemoteDevicePropertiesCallback(status, remote_bd_addr, num_properties,
     97                                      properties));
     98 }
     99 
    100 void DiscoveryStateChangedCallback(bt_discovery_state_t state) {
    101   shared_lock<shared_timed_mutex> lock(g_instance_lock);
    102   VERIFY_INTERFACE_OR_RETURN();
    103   VLOG(1) << "Discovery state changed - state: " << BtDiscoveryStateText(state);
    104   FOR_EACH_BLUETOOTH_OBSERVER(DiscoveryStateChangedCallback(state));
    105 }
    106 
    107 void PinRequestCallback(bt_bdaddr_t *remote_bd_addr, bt_bdname_t *bd_name,
    108     uint32_t cod, bool min_16_digit) {
    109   shared_lock<shared_timed_mutex> lock(g_instance_lock);
    110   VERIFY_INTERFACE_OR_RETURN();
    111   VLOG(2) << __func__
    112           << " - remote_bd_addr: " << remote_bd_addr
    113           << " - bd_name: " << bd_name
    114           << " - cod: " << cod
    115           << " - min_16_digit: " << min_16_digit;
    116   FOR_EACH_BLUETOOTH_OBSERVER(PinRequestCallback(remote_bd_addr, bd_name, cod, min_16_digit));
    117 }
    118 
    119 void SSPRequestCallback(bt_bdaddr_t *remote_bd_addr,
    120     bt_bdname_t *bd_name, uint32_t cod, bt_ssp_variant_t pairing_variant, uint32_t pass_key) {
    121   shared_lock<shared_timed_mutex> lock(g_instance_lock);
    122   VERIFY_INTERFACE_OR_RETURN();
    123   VLOG(2) << __func__
    124           << " - remote_bd_addr: " << remote_bd_addr
    125           << " - bd_name: " << bd_name
    126           << " - cod: " << cod
    127           << " - pairing_variant: " << pairing_variant;
    128   FOR_EACH_BLUETOOTH_OBSERVER(SSPRequestCallback(remote_bd_addr, bd_name, cod,
    129       pairing_variant, pass_key));
    130 }
    131 
    132 void BondStateChangedCallback(
    133     bt_status_t status,
    134     bt_bdaddr_t *remote_bd_addr,
    135     bt_bond_state_t state) {
    136   shared_lock<shared_timed_mutex> lock(g_instance_lock);
    137   VERIFY_INTERFACE_OR_RETURN();
    138   VLOG(2) << __func__
    139           << " - remote_bd_addr: " << BtAddrString(remote_bd_addr)
    140           << " - status: " << status
    141           << " - state: " << state;
    142   FOR_EACH_BLUETOOTH_OBSERVER(BondStateChangedCallback(status, remote_bd_addr, state));
    143 }
    144 
    145 void AclStateChangedCallback(bt_status_t status,
    146                              bt_bdaddr_t *remote_bd_addr,
    147                              bt_acl_state_t state) {
    148   shared_lock<shared_timed_mutex> lock(g_instance_lock);
    149   VERIFY_INTERFACE_OR_RETURN();
    150   CHECK(remote_bd_addr);
    151   VLOG(1) << "Remote device ACL state changed - status: "
    152           << BtStatusText(status)
    153           << " - BD_ADDR: " << BtAddrString(remote_bd_addr)
    154           << " - state: "
    155           << ((state == BT_ACL_STATE_CONNECTED) ? "CONNECTED" : "DISCONNECTED");
    156   FOR_EACH_BLUETOOTH_OBSERVER(
    157       AclStateChangedCallback(status, *remote_bd_addr, state));
    158 }
    159 
    160 void ThreadEventCallback(bt_cb_thread_evt evt) {
    161   VLOG(1) << "ThreadEventCallback" << BtEventText(evt);
    162 
    163   // TODO(armansito): This callback is completely useless to us but btif borks
    164   // out if this is not set. Consider making this optional.
    165 }
    166 
    167 bool SetWakeAlarmCallout(uint64_t /* delay_millis */,
    168                          bool /* should_wake */,
    169                          alarm_cb /* cb */,
    170                          void* /* data */) {
    171   // TODO(armansito): According to sharvil@, this interface doesn't even need to
    172   // exist and can be done entirely from within osi by interfacing directly with
    173   // the kernel. Remove these stubs once that's fixed. (See http://b/23390297)
    174   return false;
    175 }
    176 
    177 int AcquireWakeLockCallout(const char* /* lock_name */) {
    178   // TODO(armansito): According to sharvil@, this interface doesn't even need to
    179   // exist and can be done entirely from within osi by interfacing directly with
    180   // the kernel. Remove these stubs once that's fixed. (See http://b/23390297)
    181   // Lie here and return success so that enabling and disabling the controller
    182   // works before this is properly implemented.
    183   return BT_STATUS_SUCCESS;
    184 }
    185 
    186 int ReleaseWakeLockCallout(const char* /* lock_name */) {
    187   // TODO(armansito): According to sharvil@, this interface doesn't even need to
    188   // exist and can be done entirely from within osi by interfacing directly with
    189   // the kernel. Remove these stubs once that's fixed. (See http://b/23390297)
    190   // Lie here and return success so that enabling and disabling the controller
    191   // works before this is properly implemented.
    192   return BT_STATUS_SUCCESS;
    193 }
    194 
    195 // The HAL Bluetooth DM callbacks.
    196 bt_callbacks_t bt_callbacks = {
    197   sizeof(bt_callbacks_t),
    198   AdapterStateChangedCallback,
    199   AdapterPropertiesCallback,
    200   RemoteDevicePropertiesCallback,
    201   nullptr, /* device_found_cb */
    202   DiscoveryStateChangedCallback,
    203   PinRequestCallback,
    204   SSPRequestCallback,
    205   BondStateChangedCallback,
    206   AclStateChangedCallback,
    207   ThreadEventCallback,
    208   nullptr, /* dut_mode_recv_cb */
    209   nullptr, /* le_test_mode_cb */
    210   nullptr  /* energy_info_cb */
    211 };
    212 
    213 bt_os_callouts_t bt_os_callouts = {
    214   sizeof(bt_os_callouts_t),
    215   SetWakeAlarmCallout,
    216   AcquireWakeLockCallout,
    217   ReleaseWakeLockCallout
    218 };
    219 
    220 }  // namespace
    221 
    222 // BluetoothInterface implementation for production.
    223 class BluetoothInterfaceImpl : public BluetoothInterface {
    224  public:
    225   BluetoothInterfaceImpl()
    226       : hal_iface_(nullptr),
    227         hal_adapter_(nullptr) {
    228   }
    229 
    230   ~BluetoothInterfaceImpl() override {
    231     if (hal_iface_)
    232         hal_iface_->cleanup();
    233   }
    234 
    235   // BluetoothInterface overrides.
    236   void AddObserver(Observer* observer) override {
    237     shared_lock<shared_timed_mutex> lock(g_instance_lock);
    238     observers_.AddObserver(observer);
    239   }
    240 
    241   void RemoveObserver(Observer* observer) override {
    242     shared_lock<shared_timed_mutex> lock(g_instance_lock);
    243     observers_.RemoveObserver(observer);
    244   }
    245 
    246   const bt_interface_t* GetHALInterface() const override {
    247     return hal_iface_;
    248   }
    249 
    250   const bluetooth_device_t* GetHALAdapter() const override {
    251     return hal_adapter_;
    252   }
    253 
    254   // Initialize the interface. This loads the shared Bluetooth library and sets
    255   // up the callbacks.
    256   bool Initialize() {
    257     // Load the Bluetooth shared library module.
    258     const hw_module_t* module;
    259     int status = hal_util_load_bt_library(&module);
    260     if (status) {
    261       LOG(ERROR) << "Failed to load Bluetooth library: " << status;
    262       return false;
    263     }
    264 
    265     // Open the Bluetooth adapter.
    266     hw_device_t* device;
    267     status = module->methods->open(module, BT_HARDWARE_MODULE_ID, &device);
    268     if (status) {
    269       LOG(ERROR) << "Failed to open the Bluetooth module";
    270       return false;
    271     }
    272 
    273     hal_adapter_ = reinterpret_cast<bluetooth_device_t*>(device);
    274     hal_iface_ = hal_adapter_->get_bluetooth_interface();
    275 
    276     // Initialize the Bluetooth interface. Set up the adapter (Bluetooth DM) API
    277     // callbacks.
    278     status = hal_iface_->init(&bt_callbacks);
    279     if (status != BT_STATUS_SUCCESS) {
    280       LOG(ERROR) << "Failed to initialize Bluetooth stack";
    281       return false;
    282     }
    283 
    284     status = hal_iface_->set_os_callouts(&bt_os_callouts);
    285     if (status != BT_STATUS_SUCCESS) {
    286       LOG(ERROR) << "Failed to set up Bluetooth OS callouts";
    287       return false;
    288     }
    289 
    290     return true;
    291   }
    292 
    293   base::ObserverList<Observer>* observers() { return &observers_; }
    294 
    295  private:
    296   // List of observers that are interested in notifications from us. We're not
    297   // using a base::ObserverListThreadSafe, which it posts observer events
    298   // automatically on the origin threads, as we want to avoid that overhead and
    299   // simply forward the events to the upper layer.
    300   base::ObserverList<Observer> observers_;
    301 
    302   // The HAL handle obtained from the shared library. We hold a weak reference
    303   // to this since the actual data resides in the shared Bluetooth library.
    304   const bt_interface_t* hal_iface_;
    305 
    306   // The HAL handle that represents the underlying Bluetooth adapter. We hold a
    307   // weak reference to this since the actual data resides in the shared
    308   // Bluetooth library.
    309   const bluetooth_device_t* hal_adapter_;
    310 
    311   DISALLOW_COPY_AND_ASSIGN(BluetoothInterfaceImpl);
    312 };
    313 
    314 namespace {
    315 
    316 // Helper for obtaining the observer list from the global instance. This
    317 // function is NOT thread safe.
    318 base::ObserverList<BluetoothInterface::Observer>* GetObservers() {
    319   CHECK(g_bluetooth_interface);
    320   return static_cast<BluetoothInterfaceImpl*>(
    321       g_bluetooth_interface)->observers();
    322 }
    323 
    324 }  // namespace
    325 
    326 // Default observer implementations. These are provided so that the methods
    327 // themselves are optional.
    328 void BluetoothInterface::Observer::AdapterStateChangedCallback(
    329     bt_state_t /* state*/) {
    330   // Do nothing.
    331 }
    332 
    333 void BluetoothInterface::Observer::AdapterPropertiesCallback(
    334     bt_status_t /* status */,
    335     int /* num_properties */,
    336     bt_property_t* /* properties */) {
    337   // Do nothing.
    338 }
    339 
    340 void BluetoothInterface::Observer::RemoteDevicePropertiesCallback(
    341     bt_status_t /* status */,
    342     bt_bdaddr_t* /* remote_bd_addr */,
    343     int /* num_properties */,
    344     bt_property_t* /* properties */) {
    345   // Do nothing.
    346 }
    347 
    348 void BluetoothInterface::Observer::DiscoveryStateChangedCallback(
    349     bt_discovery_state_t /* state */) {
    350   // Do nothing.
    351 }
    352 
    353 void BluetoothInterface::Observer::PinRequestCallback(
    354     bt_bdaddr_t *remote_bd_addr,
    355     bt_bdname_t *bd_name,
    356     uint32_t cod,
    357     bool min_16_digit) {
    358   // Do nothing.
    359 }
    360 
    361 void BluetoothInterface::Observer::SSPRequestCallback(
    362     bt_bdaddr_t *remote_bd_addr,
    363     bt_bdname_t *bd_name,
    364     uint32_t cod,
    365     bt_ssp_variant_t pairing_variant,
    366     uint32_t pass_key) {
    367   // Do nothing.
    368 }
    369 
    370 void BluetoothInterface::Observer::BondStateChangedCallback(
    371     bt_status_t status,
    372     bt_bdaddr_t *remote_bd_addr,
    373     bt_bond_state_t state) {
    374   // Do nothing.
    375 }
    376 
    377 void BluetoothInterface::Observer::AclStateChangedCallback(
    378     bt_status_t /* status */,
    379     const bt_bdaddr_t& /* remote_bdaddr */,
    380     bt_acl_state_t /* state */) {
    381   // Do nothing.
    382 }
    383 
    384 // static
    385 bool BluetoothInterface::Initialize() {
    386   unique_lock<shared_timed_mutex> lock(g_instance_lock);
    387   CHECK(!g_bluetooth_interface);
    388 
    389   std::unique_ptr<BluetoothInterfaceImpl> impl(new BluetoothInterfaceImpl());
    390   if (!impl->Initialize()) {
    391     LOG(ERROR) << "Failed to initialize BluetoothInterface";
    392     return false;
    393   }
    394 
    395   g_bluetooth_interface = impl.release();
    396 
    397   return true;
    398 }
    399 
    400 // static
    401 void BluetoothInterface::CleanUp() {
    402   unique_lock<shared_timed_mutex> lock(g_instance_lock);
    403   CHECK(g_bluetooth_interface);
    404 
    405   delete g_bluetooth_interface;
    406   g_bluetooth_interface = nullptr;
    407 }
    408 
    409 // static
    410 bool BluetoothInterface::IsInitialized() {
    411   shared_lock<shared_timed_mutex> lock(g_instance_lock);
    412 
    413   return g_bluetooth_interface != nullptr;
    414 }
    415 
    416 // static
    417 BluetoothInterface* BluetoothInterface::Get() {
    418   shared_lock<shared_timed_mutex> lock(g_instance_lock);
    419   CHECK(g_bluetooth_interface);
    420   return g_bluetooth_interface;
    421 }
    422 
    423 // static
    424 void BluetoothInterface::InitializeForTesting(
    425     BluetoothInterface* test_instance) {
    426   unique_lock<shared_timed_mutex> lock(g_instance_lock);
    427   CHECK(test_instance);
    428   CHECK(!g_bluetooth_interface);
    429 
    430   g_bluetooth_interface = test_instance;
    431 }
    432 
    433 }  // namespace hal
    434 }  // namespace bluetooth
    435