Separate LE scanner from GATT client (4/4)

Right now, LE scanning functionality is combined with the GATT client.
This is the source of various bugs, like scans suddenly stoppinging when
a GATT client is killed. It also increases memory consumption, because
we associate many structures with a GATT client, which are not necessary
when just scanning.

Test: sl4a BleScanApiTest ConcurrentBleScanTest
Bug: 30622771
Change-Id: I23b71255c459b185257654f68ea251b41ed2a14b
diff --git a/btif/src/btif_gatt_client.cc b/btif/src/btif_gatt_client.cc
index cd20ce5..a83fc09 100644
--- a/btif/src/btif_gatt_client.cc
+++ b/btif/src/btif_gatt_client.cc
@@ -297,6 +297,40 @@
   ASSERTC(status == BT_STATUS_SUCCESS, "Context transfer failed!", status);
 }
 
+void btif_gatts_upstreams_evt(uint16_t event, char* p_param) {
+  LOG_VERBOSE(LOG_TAG, "%s: Event %d", __func__, event);
+
+  tBTA_GATTC* p_data = (tBTA_GATTC*)p_param;
+  switch (event) {
+    case BTA_GATTC_REG_EVT: {
+      bt_uuid_t app_uuid;
+      bta_to_btif_uuid(&app_uuid, &p_data->reg_oper.app_uuid);
+      HAL_CBACK(bt_gatt_callbacks, client->register_scanner_cb,
+                p_data->reg_oper.status, p_data->reg_oper.client_if, &app_uuid);
+      break;
+    }
+
+    case BTA_GATTC_DEREG_EVT:
+      break;
+
+    case BTA_GATTC_SEARCH_CMPL_EVT: {
+      HAL_CBACK(bt_gatt_callbacks, client->search_complete_cb,
+                p_data->search_cmpl.conn_id, p_data->search_cmpl.status);
+      break;
+    }
+
+    default:
+      LOG_ERROR(LOG_TAG, "%s: Unhandled event (%d)!", __func__, event);
+      break;
+  }
+}
+
+void bta_gatts_cback(tBTA_GATTC_EVT event, tBTA_GATTC* p_data) {
+  bt_status_t status =
+      btif_transfer_context(btif_gatts_upstreams_evt, (uint16_t)event,
+                            (char*)p_data, sizeof(tBTA_GATTC), NULL);
+  ASSERTC(status == BT_STATUS_SUCCESS, "Context transfer failed!", status);
+}
 void bta_batch_scan_setup_cb(tBTA_BLE_BATCH_SCAN_EVT evt,
                              tBTA_DM_BLE_REF_VALUE ref_value,
                              tBTA_STATUS status) {
@@ -504,6 +538,29 @@
   return do_in_jni_thread(Bind(&btif_gattc_unregister_app_impl, client_if));
 }
 
+
+void btif_gattc_register_scanner_impl(tBT_UUID uuid) {
+  BTA_GATTC_AppRegister(&uuid, bta_gatts_cback);
+}
+
+bt_status_t btif_gattc_register_scanner(bt_uuid_t* uuid) {
+  CHECK_BTGATT_INIT();
+
+  tBT_UUID bt_uuid;
+  btif_to_bta_uuid(&bt_uuid, uuid);
+  return do_in_jni_thread(Bind(&btif_gattc_register_scanner_impl, bt_uuid));
+}
+
+void btif_gattc_unregister_scanner_impl(int client_if) {
+  BTA_GATTC_AppDeregister(client_if);
+}
+
+bt_status_t btif_gattc_unregister_scanner(int scanner_id) {
+  CHECK_BTGATT_INIT();
+  return do_in_jni_thread(Bind(&btif_gattc_unregister_scanner_impl, scanner_id));
+}
+
+
 bt_status_t btif_gattc_scan(bool start) {
   CHECK_BTGATT_INIT();
   if (start) {
@@ -1073,6 +1130,8 @@
 const btgatt_client_interface_t btgattClientInterface = {
     btif_gattc_register_app,
     btif_gattc_unregister_app,
+    btif_gattc_register_scanner,
+    btif_gattc_unregister_scanner,
     btif_gattc_scan,
     btif_gattc_open,
     btif_gattc_close,
diff --git a/service/gatt_server_old.cc b/service/gatt_server_old.cc
index 7eb5b06..9622a00 100644
--- a/service/gatt_server_old.cc
+++ b/service/gatt_server_old.cc
@@ -351,6 +351,11 @@
   }
 }
 
+void RegisterScannerCallback(int status, int scanner_id, bt_uuid_t *app_uuid) {
+  LOG_INFO(LOG_TAG, "%s: status:%d scanner_id:%d uuid[0]:%u", __func__, status,
+      scanner_id, app_uuid->uu[0]);
+}
+
 void ListenCallback(int status, int client_if) {
   LOG_INFO(LOG_TAG, "%s: status:%d client_if:%d", __func__, status, client_if);
   // This terminates a Start call.
@@ -419,6 +424,7 @@
 // to refer to the client interface.
 const btgatt_client_callbacks_t gatt_client_callbacks = {
     RegisterClientCallback,
+    RegisterScannerCallback,
     ScanResultCallback,
     ClientConnectCallback,
     ClientDisconnectCallback,
diff --git a/service/hal/bluetooth_gatt_interface.cc b/service/hal/bluetooth_gatt_interface.cc
index 677b6fa..dfc85b5 100644
--- a/service/hal/bluetooth_gatt_interface.cc
+++ b/service/hal/bluetooth_gatt_interface.cc
@@ -80,6 +80,16 @@
       RegisterClientCallback(g_interface, status, client_if, *app_uuid));
 }
 
+void RegisterScannerCallback(int status, int scanner_id, bt_uuid_t* app_uuid) {
+  shared_lock<shared_timed_mutex> lock(g_instance_lock);
+  VLOG(2) << __func__ << " - status: " << status << " scanner_id: " << scanner_id;
+  VERIFY_INTERFACE_OR_RETURN();
+  CHECK(app_uuid);
+
+  FOR_EACH_CLIENT_OBSERVER(
+      RegisterScannerCallback(g_interface, status, scanner_id, *app_uuid));
+}
+
 void ScanResultCallback(bt_bdaddr_t* bda, int rssi, vector<uint8_t> adv_data) {  // NOLINT(pass-by-value)
   shared_lock<shared_timed_mutex> lock(g_instance_lock);
   VERIFY_INTERFACE_OR_RETURN();
@@ -387,6 +397,7 @@
 // GATT client-role and GAP events.
 const btgatt_client_callbacks_t gatt_client_callbacks = {
     RegisterClientCallback,
+    RegisterScannerCallback,
     ScanResultCallback,
     ConnectCallback,
     DisconnectCallback,
@@ -555,6 +566,15 @@
     const bt_uuid_t& /* app_uuid */) {
   // Do nothing.
 }
+
+void BluetoothGattInterface::ClientObserver::RegisterScannerCallback(
+    BluetoothGattInterface* /* gatt_iface */,
+    int /* status */,
+    int /* scanner_id */,
+    const bt_uuid_t& /* app_uuid */) {
+  // Do nothing.
+}
+
 void BluetoothGattInterface::ClientObserver::ScanResultCallback(
     BluetoothGattInterface* /* gatt_iface */,
     const bt_bdaddr_t& /* bda */,
diff --git a/service/hal/bluetooth_gatt_interface.h b/service/hal/bluetooth_gatt_interface.h
index 8d43eff..5a0e989 100644
--- a/service/hal/bluetooth_gatt_interface.h
+++ b/service/hal/bluetooth_gatt_interface.h
@@ -57,6 +57,11 @@
         int status, int client_if,
         const bt_uuid_t& app_uuid);
 
+    virtual void RegisterScannerCallback(
+        BluetoothGattInterface* gatt_iface,
+        int status, int scanner_id,
+        const bt_uuid_t& app_uuid);
+
     virtual void ScanResultCallback(
         BluetoothGattInterface* gatt_iface,
         const bt_bdaddr_t& bda, int rssi,
diff --git a/service/hal/fake_bluetooth_gatt_interface.cc b/service/hal/fake_bluetooth_gatt_interface.cc
index 4a772b7..b19a216 100644
--- a/service/hal/fake_bluetooth_gatt_interface.cc
+++ b/service/hal/fake_bluetooth_gatt_interface.cc
@@ -41,6 +41,20 @@
   return BT_STATUS_FAIL;
 }
 
+bt_status_t FakeRegisterScanner(bt_uuid_t* app_uuid) {
+  if (g_client_handler)
+    return g_client_handler->RegisterClient(app_uuid);
+
+  return BT_STATUS_FAIL;
+}
+
+bt_status_t FakeUnregisterScanner(int client_if) {
+  if (g_client_handler)
+    return g_client_handler->UnregisterClient(client_if);
+
+  return BT_STATUS_FAIL;
+}
+
 bt_status_t FakeScan(bool start) {
   if (g_client_handler)
     return g_client_handler->Scan(start);
@@ -114,6 +128,8 @@
 btgatt_client_interface_t fake_btgattc_iface = {
   FakeRegisterClient,
   FakeUnregisterClient,
+  FakeRegisterScanner,
+  FakeUnregisterScanner,
   FakeScan,
   FakeConnect,
   FakeDisconnect,