#ifndef DEVICE_BLUETOOTH_FLOSS_FLOSS_LESCAN_CLIENT_H_
#define DEVICE_BLUETOOTH_FLOSS_FLOSS_LESCAN_CLIENT_H_
#include <memory>
#include <string>
#include "base/containers/queue.h"
#include "base/functional/callback.h"
#include "base/gtest_prod_util.h"
#include "base/memory/raw_ptr.h"
#include "base/memory/weak_ptr.h"
#include "base/observer_list.h"
#include "dbus/exported_object.h"
#include "dbus/object_path.h"
#include "device/bluetooth/bluetooth_device.h"
#include "device/bluetooth/bluetooth_export.h"
#include "device/bluetooth/floss/exported_callback_manager.h"
#include "device/bluetooth/floss/floss_dbus_client.h"
#include "device/bluetooth/floss/floss_gatt_manager_client.h"
namespace dbus {
class ObjectPath;
}
namespace floss {
const char kScannerCallbackPath[] =
"/org/chromium/bluetooth/scanner/callback";
const char kScannerCallbackInterfaceName[] =
"org.chromium.bluetooth.ScannerCallback";
const char kEmptyUuidStr[] = "00000000-0000-0000-0000-000000000000";
enum class ScanType {
kActive = 0,
kPassive = 1,
};
struct ScanSettings {
int32_t interval;
int32_t window;
ScanType scan_type;
};
struct DEVICE_BLUETOOTH_EXPORT ScanFilterPattern {
uint8_t start_position = 0;
uint8_t ad_type = 0;
std::vector<uint8_t> content;
ScanFilterPattern();
ScanFilterPattern(const ScanFilterPattern&);
~ScanFilterPattern();
};
struct DEVICE_BLUETOOTH_EXPORT ScanFilterCondition {
std::vector<ScanFilterPattern> patterns;
ScanFilterCondition();
ScanFilterCondition(const ScanFilterCondition&);
~ScanFilterCondition();
};
struct DEVICE_BLUETOOTH_EXPORT ScanFilter {
uint8_t rssi_high_threshold = 0;
uint8_t rssi_low_threshold = 0;
uint8_t rssi_low_timeout = 0;
uint8_t rssi_sampling_period = 0;
ScanFilterCondition condition;
ScanFilter();
ScanFilter(const ScanFilter&);
~ScanFilter();
};
struct DEVICE_BLUETOOTH_EXPORT ScanResult {
std::string name;
std::string address;
uint8_t addr_type = 0;
uint16_t event_type = 0;
uint8_t primary_phy = 0;
uint8_t secondary_phy = 0;
uint8_t advertising_sid = 0;
int8_t tx_power = 0;
int8_t rssi = 0;
uint16_t periodic_adv_int = 0;
uint8_t flags = 0;
std::vector<device::BluetoothUUID> service_uuids;
std::map<std::string, std::vector<uint8_t>> service_data;
std::map<uint16_t, std::vector<uint8_t>> manufacturer_data;
std::vector<uint8_t> adv_data;
ScanResult();
ScanResult(const ScanResult&);
~ScanResult();
};
class ScannerClientObserver : public base::CheckedObserver {
public:
ScannerClientObserver() = default;
~ScannerClientObserver() override = default;
virtual void ScannerRegistered(device::BluetoothUUID uuid,
uint8_t scanner_id,
GattStatus status) {}
virtual void ScanResultReceived(ScanResult scan_result) {}
virtual void AdvertisementFound(uint8_t scanner_id, ScanResult scan_result) {}
virtual void AdvertisementLost(uint8_t scanner_id, ScanResult scan_result) {}
};
class DEVICE_BLUETOOTH_EXPORT FlossLEScanClient : public FlossDBusClient,
public ScannerClientObserver {
public:
static const char kErrorUnknownAdapter[];
static std::unique_ptr<FlossLEScanClient> Create();
FlossLEScanClient(const FlossLEScanClient&) = delete;
FlossLEScanClient& operator=(const FlossLEScanClient&) = delete;
FlossLEScanClient();
~FlossLEScanClient() override;
void AddObserver(ScannerClientObserver* observer);
void RemoveObserver(ScannerClientObserver* observer);
void Init(dbus::Bus* bus,
const std::string& service_name,
const int adapter_index,
base::Version version,
base::OnceClosure on_ready) override;
virtual void RegisterScanner(
ResponseCallback<device::BluetoothUUID> callback);
virtual void UnregisterScanner(ResponseCallback<bool> callback,
uint8_t scanner_id);
virtual void StartScan(ResponseCallback<BtifStatus> callback,
uint8_t scanner_id,
const std::optional<ScanSettings>& scan_settings,
const std::optional<ScanFilter>& filter);
virtual void StopScan(ResponseCallback<BtifStatus> callback,
uint8_t scanner_id);
protected:
void ScannerRegistered(device::BluetoothUUID uuid,
uint8_t scanner_id,
GattStatus status) override;
void ScanResultReceived(ScanResult scan_result) override;
void AdvertisementFound(uint8_t scanner_id, ScanResult scan_result) override;
void AdvertisementLost(uint8_t scanner_id, ScanResult scan_result) override;
raw_ptr<dbus::Bus> bus_ = nullptr;
dbus::ObjectPath object_path_;
base::ObserverList<ScannerClientObserver> observers_;
std::string service_name_;
private:
std::optional<uint32_t> le_scan_callback_id_;
ExportedCallbackManager<ScannerClientObserver>
exported_scanner_callback_manager_{kScannerCallbackInterfaceName};
base::queue<ResponseCallback<device::BluetoothUUID>>
pending_register_scanners_;
void RegisterScannerCallback();
void OnRegisterScannerCallback(DBusResult<uint32_t> ret);
void OnUnregisterScannerCallback(DBusResult<bool> ret);
template <typename R, typename... Args>
void CallLEScanMethod(ResponseCallback<R> callback,
const char* member,
Args... args) {
CallMethod(std::move(callback), bus_, service_name_, kGattInterface,
object_path_, member, args...);
}
base::OnceClosure on_ready_;
base::WeakPtrFactory<FlossLEScanClient> weak_ptr_factory_{this};
};
}
#endif