Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 530f58d0 authored by Arman Uguray's avatar Arman Uguray Committed by Jakub Pawlowski
Browse files

service: Add LE scan support to Binder API

Added Binder API documentation, bindings, and logic for BLE device
scans. Also added the start-le-scan and stop-le-scan commands to
bluetooth-cli for testing.

Bug: 25744656
Change-Id: I08c9d23ddd78cff1702495cf6d431cf5b9a7b894
parent d9f0f180
Loading
Loading
Loading
Loading
+65 −0
Original line number Diff line number Diff line
@@ -65,6 +65,35 @@ status_t BnBluetoothLowEnergy::onTransact(
    UnregisterAll();
    return android::NO_ERROR;
  }
  case START_SCAN_TRANSACTION: {
    int client_id = data.readInt32();
    auto settings = CreateScanSettingsFromParcel(data);
    CHECK(settings);
    std::vector<bluetooth::ScanFilter> filters;

    int list_meta_data = data.readInt32();
    CHECK(list_meta_data == kParcelValList);

    int filter_count = data.readInt32();
    if (filter_count >= 0) {  // Make sure |filter_count| isn't negative.
      for (int i = 0; i < filter_count; i++) {
        auto filter = CreateScanFilterFromParcel(data);
        CHECK(filter);
        filters.push_back(*filter);
      }
    }

    bool result = StartScan(client_id, *settings, filters);
    reply->writeInt32(result);

    return android::NO_ERROR;
  }
  case STOP_SCAN_TRANSACTION: {
    int client_id = data.readInt32();
    bool result = StopScan(client_id);
    reply->writeInt32(result);
    return android::NO_ERROR;
  }
  case START_MULTI_ADVERTISING_TRANSACTION: {
    int client_id = data.readInt32();
    std::unique_ptr<AdvertiseData> adv_data =
@@ -133,6 +162,42 @@ void BpBluetoothLowEnergy::UnregisterAll() {
                     data, &reply);
}

bool BpBluetoothLowEnergy::StartScan(
    int client_id,
    const bluetooth::ScanSettings& settings,
    const std::vector<bluetooth::ScanFilter>& filters) {
  Parcel data, reply;

  data.writeInterfaceToken(IBluetoothLowEnergy::getInterfaceDescriptor());
  data.writeInt32(client_id);
  WriteScanSettingsToParcel(settings, &data);

  // The Java equivalent of |filters| is a List<ScanFilter>. Parcel.java inserts
  // a metadata value of VAL_LIST (11) for this so I'm doing it here for
  // compatibility.
  data.writeInt32(kParcelValList);
  data.writeInt32(filters.size());
  for (const auto& filter : filters)
    WriteScanFilterToParcel(filter, &data);

  remote()->transact(IBluetoothLowEnergy::START_SCAN_TRANSACTION,
                     data, &reply);

  return reply.readInt32();
}

bool BpBluetoothLowEnergy::StopScan(int client_id) {
  Parcel data, reply;

  data.writeInterfaceToken(IBluetoothLowEnergy::getInterfaceDescriptor());
  data.writeInt32(client_id);

  remote()->transact(IBluetoothLowEnergy::STOP_SCAN_TRANSACTION,
                     data, &reply);

  return reply.readInt32();
}

bool BpBluetoothLowEnergy::StartMultiAdvertising(
    int client_id,
    const AdvertiseData& advertise_data,
+13 −0
Original line number Diff line number Diff line
@@ -22,6 +22,8 @@

#include <bluetooth/advertise_data.h>
#include <bluetooth/advertise_settings.h>
#include <bluetooth/scan_filter.h>
#include <bluetooth/scan_settings.h>
#include <bluetooth/binder/IBluetoothLowEnergyCallback.h>

namespace ipc {
@@ -70,6 +72,12 @@ class IBluetoothLowEnergy : public android::IInterface {
  virtual void UnregisterClient(int client_if) = 0;
  virtual void UnregisterAll() = 0;

  virtual bool StartScan(
      int client_id,
      const bluetooth::ScanSettings& settings,
      const std::vector<bluetooth::ScanFilter>& filters) = 0;
  virtual bool StopScan(int client_id) = 0;

  virtual bool StartMultiAdvertising(
      int client_if,
      const bluetooth::AdvertiseData& advertise_data,
@@ -111,6 +119,11 @@ class BpBluetoothLowEnergy : public android::BpInterface<IBluetoothLowEnergy> {
      const android::sp<IBluetoothLowEnergyCallback>& callback) override;
  void UnregisterClient(int client_if) override;
  void UnregisterAll() override;
  bool StartScan(
      int client_id,
      const bluetooth::ScanSettings& settings,
      const std::vector<bluetooth::ScanFilter>& filters) override;
  bool StopScan(int client_id) override;
  bool StartMultiAdvertising(
      int client_if,
      const bluetooth::AdvertiseData& advertise_data,
+17 −1
Original line number Diff line number Diff line
@@ -33,10 +33,26 @@ interface IBluetoothLowEnergy {
  void unregisterClient(in int client_if);

  /**
   * Unregisters all previous registered clients.
   * Unregisters all previously registered clients.
   */
  void unregisterAll();

  /**
   * Initiates a BLE device scan for the scan client with ID |client_id|, using
   * the parameters defined in |settings|. Scan results that are reported to the
   * application with the associated IBluetoothLowEnergyCallback event will be
   * filtered using a combination of hardware and software filtering based on
   * |filters|. Return true on success, false otherwise.
   */
  boolean startScan(in int client_id, in ScanSettings settings,
                    in ScanFilter[] filters);

  /**
   * Stops a previously initiated scan session for the client with ID
   * |client_id|. Return true on success, false otherwise.
   */
  boolean stopScan(in int client_id);

  /**
   * Starts a multi-advertising instance using |advertising_data| and
   * |scan_response_data|, both of which can be empty. Each of these parameters
+30 −0
Original line number Diff line number Diff line
@@ -54,6 +54,35 @@ void BluetoothLowEnergyBinderServer::UnregisterAll() {
  UnregisterAllBase();
}

bool BluetoothLowEnergyBinderServer::StartScan(
    int client_id,
    const bluetooth::ScanSettings& settings,
    const std::vector<bluetooth::ScanFilter>& filters) {
  VLOG(2) << __func__ << " client_id: " << client_id;
  std::lock_guard<std::mutex> lock(*maps_lock());

  auto client = GetLEClient(client_id);
  if (!client) {
    LOG(ERROR) << "Unknown client_id: " << client_id;
    return false;
  }

  return client->StartScan(settings, filters);
}

bool BluetoothLowEnergyBinderServer::StopScan(int client_id) {
  VLOG(2) << __func__ << " client_id: " << client_id;
  std::lock_guard<std::mutex> lock(*maps_lock());

  auto client = GetLEClient(client_id);
  if (!client) {
    LOG(ERROR) << "Unknown client_id: " << client_id;
    return false;
  }

  return client->StopScan();
}

bool BluetoothLowEnergyBinderServer::StartMultiAdvertising(
    int client_id,
    const bluetooth::AdvertiseData& advertise_data,
@@ -157,6 +186,7 @@ void BluetoothLowEnergyBinderServer::OnRegisterInstanceImpl(
    android::sp<IInterface> callback,
    bluetooth::BluetoothInstance* instance) {
  VLOG(1) << __func__ << " status: " << status;

  android::sp<IBluetoothLowEnergyCallback> cb(
      static_cast<IBluetoothLowEnergyCallback*>(callback.get()));
  cb->OnClientRegistered(
+8 −2
Original line number Diff line number Diff line
@@ -34,7 +34,8 @@ namespace ipc {
namespace binder {

// Implements the server side of the IBluetoothLowEnergy interface.
class BluetoothLowEnergyBinderServer : public BnBluetoothLowEnergy,
class BluetoothLowEnergyBinderServer
    : public BnBluetoothLowEnergy,
      public InterfaceWithInstancesBase {
 public:
  explicit BluetoothLowEnergyBinderServer(bluetooth::Adapter* adapter);
@@ -45,6 +46,11 @@ class BluetoothLowEnergyBinderServer : public BnBluetoothLowEnergy,
      const android::sp<IBluetoothLowEnergyCallback>& callback) override;
  void UnregisterClient(int client_id) override;
  void UnregisterAll() override;
  bool StartScan(
      int client_id,
      const bluetooth::ScanSettings& settings,
      const std::vector<bluetooth::ScanFilter>& filters) override;
  bool StopScan(int client_id) override;
  bool StartMultiAdvertising(
      int client_id,
      const bluetooth::AdvertiseData& advertise_data,