blob: e4ed4cebab2a8e11f58bc1e06f0175e06640cd53 [file] [log] [blame]
// Copyright 2021 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#ifndef DEVICE_BLUETOOTH_BLUETOOTH_LOW_ENERGY_SCAN_FILTER_H_
#define DEVICE_BLUETOOTH_BLUETOOTH_LOW_ENERGY_SCAN_FILTER_H_
#include <stddef.h>
#include <stdint.h>
#include <memory>
#include <vector>
#include "base/time/time.h"
#include "device/bluetooth/bluetooth_export.h"
#include "third_party/abseil-cpp/absl/types/optional.h"
namespace device {
class DEVICE_BLUETOOTH_EXPORT BluetoothLowEnergyScanFilter {
public:
// Standard data types found in the Bluetooth Assigned Numbers Specification
// for Generic Access Profile (GAP).
enum class AdvertisementDataType {
kFlags = 0x01,
kShortenedLocalName = 0x08,
kCompleteLocalName = 0x09,
kListOf16BitServiceSolicitationUUIDs = 0x14,
kListOf128BitServiceSolicitationUUIDs = 0x15,
kServiceData = 0x16,
kServiceData32BitUUID = 0x20,
kServiceData128BitUUID = 0x21,
kListOf32BitServiceSolicitationUUIDs = 0x1F,
kBroadcastCode = 0x2D,
kManufacturerSpecificData = 0xFF
};
// Used as an alternative to specifying RSSI threshold values directly. Since
// measured signal strength will vary with different combinations of devices
// and environmental conditions, distances are provided as rough guidelines.
// However the goal is that there will be no false negatives at the listed
// distance.
enum class Range {
// Roughly 1.5 ft.
kImmediate,
// Roughly 6 ft.
kNear,
// Roughly 20 ft.
kFar
};
class Pattern {
public:
explicit Pattern(uint8_t start_position,
AdvertisementDataType data_type,
const std::vector<uint8_t>& value);
Pattern(const Pattern&);
~Pattern();
bool IsValid() const;
uint8_t start_position() const { return start_position_; }
AdvertisementDataType data_type() const { return data_type_; }
const std::vector<uint8_t>& value() const { return value_; }
private:
uint8_t start_position_;
AdvertisementDataType data_type_;
std::vector<uint8_t> value_;
};
// Returns nullptr if the provided parameters fail validation. See
// documentation on instance variables for details.
static std::unique_ptr<BluetoothLowEnergyScanFilter> Create(
Range device_range,
base::TimeDelta device_found_timeout,
base::TimeDelta device_lost_timeout,
const std::vector<Pattern>& patterns,
absl::optional<base::TimeDelta> rssi_sampling_period);
static std::unique_ptr<BluetoothLowEnergyScanFilter> Create(
int16_t device_found_rssi_threshold,
int16_t device_lost_rssi_threshold,
base::TimeDelta device_found_timeout,
base::TimeDelta device_lost_timeout,
const std::vector<Pattern>& patterns,
absl::optional<base::TimeDelta> rssi_sampling_period);
BluetoothLowEnergyScanFilter(const BluetoothLowEnergyScanFilter&) = delete;
BluetoothLowEnergyScanFilter& operator=(const BluetoothLowEnergyScanFilter&) =
delete;
~BluetoothLowEnergyScanFilter();
int16_t device_found_rssi_threshold() const {
return device_found_rssi_threshold_;
}
int16_t device_lost_rssi_threshold() const {
return device_lost_rssi_threshold_;
}
base::TimeDelta device_found_timeout() const { return device_found_timeout_; }
base::TimeDelta device_lost_timeout() const { return device_lost_timeout_; }
const std::vector<Pattern>& patterns() const { return patterns_; }
const absl::optional<base::TimeDelta>& rssi_sampling_period() const {
return rssi_sampling_period_;
}
private:
BluetoothLowEnergyScanFilter(
int16_t device_found_rssi_threshold,
int16_t device_lost_rssi_threshold,
base::TimeDelta device_found_timeout,
base::TimeDelta device_lost_timeout,
std::vector<Pattern> patterns,
absl::optional<base::TimeDelta> rssi_sampling_period);
bool IsValid() const;
// Must be between -127 and 20, inclusive, and must be greater than to
// |device_lost_rssi_threshold_|.
int16_t device_found_rssi_threshold_;
// Must be between -127 and 20, inclusive, and must be less than
// |device_found_rssi_threshold_|.
int16_t device_lost_rssi_threshold_;
// Must be between 1 and 300 seconds, inclusive. A device must be above
// |device_found_rssi_threshold_| for |device_found_timeout_| seconds before
// it is reported as found.
base::TimeDelta device_found_timeout_;
// Must be between 1 and 300 seconds, inclusive. A device must be below
// |device_lost_rssi_threshold_| for |device_lost_timeout_| seconds before it
// is reported as lost.
base::TimeDelta device_lost_timeout_;
// Must not be empty. For each pattern, Pattern::IsValid() must also pass.
std::vector<Pattern> patterns_;
// Must be between 0 and 254000 ms, inclusive. Will be rounded up to the
// nearest 100 ms. If set to 0 all advertisement packets from in-range devices
// are propagated. If unset only the first advertisement packet of in-range
// devices are propagated. If set between 1 and 254000 ms advertisements are
// propagated after the specified time period (rounded up to the nearest 100
// ms). A lower sampling period will result in higher power consumption, with
// the default setting being the most power-efficient.
absl::optional<base::TimeDelta> rssi_sampling_period_;
};
} // namespace device
#endif // DEVICE_BLUETOOTH_BLUETOOTH_LOW_ENERGY_SCAN_FILTER_H_