pw_bluetooth#
The pw_bluetooth
module contains APIs and utilities for the host layer of
Bluetooth Low Energy.
Host API#
Attention
This module is still under construction, the API is not yet stable.
The headers in public/pw_bluetooth constitute a Bluetooth Host API. host.h is the entry point from which all other APIs are exposed. Currently, only Low Energy APIs exist.
Host#
-
class Host#
Host is the entrypoint API for interacting with a Bluetooth host stack. Host is an abstract class that is implemented by a host stack implementation.
Public Types
-
enum class PairingSecurityLevel : uint8_t#
The security level required for this pairing. This corresponds to the security levels defined in the Security Manager Protocol in Core spec v5.3, Vol 3, Part H, Section 2.3.1
Values:
-
enumerator kEncrypted#
Encrypted without person-in-the-middle protection (unauthenticated)
-
enumerator kAuthenticated#
Encrypted with person-in-the-middle protection (authenticated), although this level of security does not fully protect against passive eavesdroppers
-
enumerator kLeSecureConnections#
Encrypted with person-in-the-middle protection (authenticated). This level of security fully protects against eavesdroppers.
-
enumerator kEncrypted#
-
enum class BondableMode : uint8_t#
Whether or not the device should form a bluetooth bond during the pairing prodecure. As described in Core Spec v5.2, Vol 3, Part C, Sec 4.3
Values:
-
enumerator kBondable#
The device will form a bond during pairing with peers.
-
enumerator kNonBondable#
The device will not form a bond during pairing with peers.
-
enumerator kBondable#
Public Functions
-
virtual void Initialize(Controller *controller, PersistentData data, Function<void(Status)> &&on_initialization_complete) = 0#
Initializes the host stack. Vendor specific controller initialization (e.g. loading firmware) must be done before initializing
Host
.- Parameters:
controller – Pointer to a concrete
Controller
that the host stack should use to communicate with the controller.data – Data to persist from a previous instance of
Host
.on_initialization_complete – Called when initialization is complete. Other methods should not be called until initialization completes.
-
virtual void Close(Closure callback) = 0#
Safely shuts down the host, ending all active Bluetooth procedures:
All objects/pointers associated with this host are destroyed/invalidated and all connections disconnected.
All scanning and advertising procedures are stopped.
The Host may send events or call callbacks as procedures get terminated.
- Parameters:
callback – Will be called once all procedures have terminated.
-
virtual low_energy::Central *Central() = 0#
Returns a pointer to the Central API, which is used to scan and connect to peers.
-
virtual low_energy::Peripheral *Peripheral() = 0#
Returns a pointer to the Peripheral API, which is used to advertise and accept connections from peers.
-
virtual gatt::Server *GattServer() = 0#
Returns a pointer to the GATT Server API, which is used to publish GATT services.
-
virtual Status ForgetPeer(PeerId peer_id) = 0#
Deletes a peer from the Bluetooth host. If the peer is connected, it will be disconnected.
peer_id
will no longer refer to any peer.Returns
OK
after no peer exists that’s identified bypeer_id
(even if it didn’t exist),ABORTED
if the peer could not be disconnected or deleted and still exists.
-
virtual void EnablePrivacy(bool enabled) = 0#
Enable or disable the LE privacy feature. When enabled, the host will use a private device address in all LE procedures. When disabled, the public identity address will be used instead (which is the default).
-
virtual void SetSecurityMode(low_energy::SecurityMode security_mode) = 0#
Set the GAP LE Security Mode of the host. Only encrypted, connection-based security modes are supported, i.e. Mode 1 and Secure Connections Only mode. If the security mode is set to Secure Connections Only, any existing encrypted connections which do not meet the security requirements of Secure Connections Only mode will be disconnected.
-
virtual void SetPairingDelegate(InputCapability input, OutputCapability output, PairingDelegate *pairing_delegate) = 0#
Assigns the pairing delegate that will respond to authentication challenges using the given I/O capabilities. Calling this method cancels any on-going pairing procedure started using a previous delegate. Pairing requests will be rejected if no PairingDelegate has been assigned.
-
virtual void Pair(PeerId peer_id, PairingOptions options, Function<void(Status)> &&callback) = 0#
NOTE: This is intended to satisfy test scenarios that require pairing procedures to be initiated without relying on service access. In normal operation, Bluetooth security is enforced during service access.
Initiates pairing to the peer with the supplied
peer_id
andoptions
. Returns an error if no connected peer withpeer_id
is found or the pairing procedure fails.If
options
specifies a higher security level than the current pairing, this method attempts to raise the security level. Otherwise this method has no effect and returns success.Returns the following errors via
callback
:NOT_FOUND
- The peerpeer_id
was not found.ABORTED
- The pairing procedure failed.
-
virtual void SetBondDataCallback(Function<void(low_energy::BondData)> &&callback) = 0#
Configures a callback to be called when new bond data for a peer has been created. This data should be persisted and used to initialize Host in the future. New bond data may be received for an already bonded peer, in which case the new data should overwrite the old data.
-
virtual std::optional<PeerId> PeerIdFromAddress(Address address) = 0#
Looks up the
PeerId
corresponding toaddress
. Ifaddress
does not correspond to a known peer, a newPeerId
will be generated for the address. If aPeerId
cannot be generated, std::nullopt will be returned.
-
virtual std::optional<Address> DeviceAddressFromPeerId(PeerId peer_id) = 0#
Looks up the Address corresponding to
peer_id
. Returns null ifpeer_id
does not correspond to a known peer.
-
struct PairingOptions#
Parameters that give a caller more fine-grained control over the pairing process.
Public Members
-
PairingSecurityLevel security_level = PairingSecurityLevel::kAuthenticated#
Determines the Security Manager security level to pair with.
-
BondableMode bondable_mode = BondableMode::kBondable#
Indicated whether the device should form a bond or not during pairing. If not present, interpreted as bondable mode.
-
PairingSecurityLevel security_level = PairingSecurityLevel::kAuthenticated#
-
struct PersistentData#
Represents the persistent configuration of a single Host instance. This is used for identity representation in advertisements & bonding secrets recall.
Public Members
-
std::optional<Key> identity_resolving_key#
The local Identity Resolving Key used by a Host to generate Resolvable Private Addresses when privacy is enabled. May be absent for hosts that do not use LE privacy, or that only use Non-Resolvable Private Addresses.
NOTE: This key is distributed to LE peers during pairing procedures. The client must take care to assign an IRK that consistent with the local Host identity.
-
span<const low_energy::BondData> bonds#
All bonds that use a public identity address must contain the same local address.
-
std::optional<Key> identity_resolving_key#
-
enum class PairingSecurityLevel : uint8_t#
low_energy::Central#
-
class Central#
Represents the LE central role. Used to scan and connect to peripherals.
Public Types
-
enum class ConnectError : uint8_t#
Possible errors returned by
Connect
.Values:
-
enumerator kUnknownPeer#
The peer ID is unknown.
-
enumerator kInvalidOptions#
The
ConnectionOptions
were invalid.
-
enumerator kAlreadyExists#
A connection to the peer already exists.
-
enumerator kCouldNotBeEstablished#
A connection could not be established.
-
enumerator kUnknownPeer#
-
using ConnectResult = Result<ConnectError, Connection::Ptr>#
The Result type returned by Connect() via the passed callback.
Public Functions
-
virtual void Connect(PeerId peer_id, ConnectionOptions options, Function<void(ConnectResult)> &&callback) = 0#
Connect to the peer with the given identifier.
The requested
Connection
represents the client’s interest in the LE connection to the peer. Destroying theConnection
will disconnect from the peer. Only 1 connection per peer may exist at a time.The
Connection
will be closed by the system if the connection to the peer is lost or an error occurs, as indicated byConnection.OnError
.Possible errors are documented in
ConnectError
.- Parameters:
peer_id – Identifier of the peer to initiate a connection to.
options – Options used to configure the connection.
callback – Called when a connection is successfully established, or an error occurs.
-
virtual void Scan(ScanOptions options, Function<void(ScanResult)> &&scan_result_callback, Function<void(Result<StartScanError, ScanHandle::Ptr>)> &&scan_started_callback) = 0#
Scans for nearby LE peripherals and broadcasters. The lifetime of the scan session is tied to the returned
ScanHandle
object. Once a scan is started,scan_result_callback
will be called with scan results. Only 1 scan may be active at a time. It is OK to destroy theScanHandle::Ptr
object inscan_result_callback
to stop scanning (no more results will be returned).- Parameters:
options – Options used to configure the scan session.
scan_result_callback – If scanning starts successfully,called for LE peers that satisfy the filters indicated in
options
. The initial calls may report recently discovered peers. Subsequent calls will be made only when peers have been scanned or updated since the last call.scan_started_callback – Called with a
ScanHandle
object if the scan successfully starts, or aScanError
otherwise.
-
struct ScanData#
Information obtained from advertising and scan response data broadcast by a peer.
Public Members
-
std::optional<uint8_t> tx_power#
The radio transmit power level.
Note
This field should NOT be confused with the “connection TX Power
Level” of a peer that is currently connected to the system obtained via the “Transmit Power reporting” feature.
-
std::optional<Appearance> appearance#
The appearance of the device.
-
Vector<std::string_view> uris#
String representing a URI to be advertised, as defined in IETF STD 66: https://tools.ietf.org/html/std66. Each entry should be a UTF-8 string including the scheme. For more information, see https://www.iana.org/assignments/uri-schemes/uri-schemes.xhtml for allowed schemes;
Note
Bluetooth advertising compresses schemas over the air to save space. See https://www.bluetooth.com/specifications/assigned-numbers/uri-scheme-name-string-mapping.
-
chrono::SystemClock::time_point timestamp#
The time when this scan data was received.
-
std::optional<uint8_t> tx_power#
-
struct ScanFilter#
Filter parameters for use during a scan. A discovered peer only matches the filter if it satisfies all of the present filter parameters.
Public Members
-
std::optional<Uuid> service_uuid#
Filter based on advertised service UUID.
-
std::optional<Uuid> service_data_uuid#
Filter based on service data containing the given UUID.
-
std::optional<uint16_t> manufacturer_id#
Filter based on a manufacturer identifier present in the manufacturer data. If this filter parameter is set, then the advertising payload must contain manufacturer specific data with the provided company identifier to satisfy this filter. Manufacturer identifiers can be found at https://www.bluetooth.com/specifications/assigned-numbers/company-identifiers/
-
std::optional<bool> connectable#
Filter based on whether or not a device is connectable. For example, a client that is only interested in peripherals that it can connect to can set this to true. Similarly a client can scan only for broadcasters by setting this to false.
-
std::optional<std::string_view> name#
Filter results based on a portion of the advertised device name. Substring matches are allowed. The name length must be at most pw::bluetooth::kMaxDeviceNameLength.
-
std::optional<uint8_t> max_path_loss#
Filter results based on the path loss of the radio wave. A device that matches this filter must satisfy the following:
Radio transmission power level and received signal strength must be available for the path loss calculation.
The calculated path loss value must be less than, or equal to,
max_path_loss
.
Note
This field is calculated using the RSSI and TX Power information obtained from advertising and scan response data during a scan procedure. It should NOT be confused with information for an active connection obtained using the “Path Loss Reporting” feature.
-
std::optional<Uuid> service_uuid#
-
class ScanHandle#
Represents an ongoing LE scan.
Public Types
-
enum class ScanError : uint8_t#
Possible errors that can cause a scan to stop prematurely.
Values:
-
enumerator kCanceled#
-
enumerator kCanceled#
-
using Ptr = internal::RaiiPtr<ScanHandle, &ScanHandle::StopScan>#
Movable ScanHandle smart pointer. The controller will continue scanning until the ScanHandle::Ptr is destroyed.
-
enum class ScanError : uint8_t#
-
struct ScanOptions#
Parameters used during a scan.
Public Members
-
Vector<ScanFilter> filters#
List of filters for use during a scan. A peripheral that satisfies any of these filters will be reported. At least 1 filter must be specified. While not recommended, clients that require that all peripherals be reported can specify an empty filter.
-
uint16_t interval = 0x0010#
The time interval between scans.
Time = N * 0.625ms
Range: 0x0004 (2.5ms) - 10.24ms (0x4000)
Default: 10ms
-
uint16_t window = 0x0010#
The duration of the scan. The window must be less than or equal to the interval.
Time = N * 0.625ms
Range: 0x0004 (2.5ms) - 10.24ms (0x4000)
Default: 10ms
-
Vector<ScanFilter> filters#
-
struct ScanResult#
Public Functions
-
ScanResult(const ScanResult&) = delete#
ScanResult is non-copyable because strings are only valid in the result callback.
Public Members
-
PeerId peer_id#
Uniquely identifies this peer on the current system.
-
bool connectable#
Whether or not this peer is connectable. Non-connectable peers are typically in the LE broadcaster role.
-
std::optional<uint8_t> rssi#
The last observed signal strength of this peer. This field is only present for a peer that is broadcasting. The RSSI can be stale if the peer has not been advertising.
Note
This field should NOT be confused with the “connection RSSI” of a peer that is currently connected to the system.
-
ScanData scan_data#
Information from advertising and scan response data broadcast by this peer. This contains the advertising data last received from the peer.
-
std::optional<std::string_view> name#
The name of this peer. The name is often obtained during a scan procedure and can get updated during the name discovery procedure following a connection.
This field is present if the name is known.
-
chrono::SystemClock::time_point last_updated#
Timestamp of when the information in this
ScanResult
was last updated.
-
ScanResult(const ScanResult&) = delete#
-
enum class ConnectError : uint8_t#
low_energy::Peripheral#
-
class Peripheral#
Represents the LE Peripheral role, which advertises and is connected to.
Public Types
-
enum class AdvertiseError#
Errors returned by
Advertise
.Values:
-
enumerator kNotSupported#
The operation or parameters requested are not supported on the current hardware.
-
enumerator kAdvertisingDataTooLong#
The provided advertising data exceeds the maximum allowed length when encoded.
-
enumerator kScanResponseDataTooLong#
The provided scan response data exceeds the maximum allowed length when encoded.
-
enumerator kInvalidParameters#
The requested parameters are invalid.
-
enumerator kNotEnoughAdvertisingSlots#
This may be called if the maximum number of simultaneous advertisements has already been reached.
-
enumerator kFailed#
Advertising could not be initiated due to a hardware or system error.
-
enumerator kNotSupported#
-
using AdvertiseCallback = Function<void(Result<AdvertiseError, AdvertisedPeripheral::Ptr>)>#
Callback for
Advertise()
method.
Public Functions
-
virtual void Advertise(const AdvertisingParameters ¶meters, AdvertiseCallback &&result_callback) = 0#
Start advertising continuously as a LE peripheral. If advertising cannot be initiated then
result_callback
will be called with an error. Once started, advertising can be stopped by destroying the returnedAdvertisedPeripheral::Ptr
.If the system supports multiple advertising, this may be called as many times as there are advertising slots. To reconfigure an advertisement, first close the original advertisement and then initiate a new advertisement.
- Parameters:
parameters – Parameters used while configuring the advertising instance.
result_callback – Called once advertising has started or failed. On success, called with an
AdvertisedPeripheral
that models the lifetime of the advertisement. Destroying it will stop advertising.
-
struct AdvertisingIntervalRange#
The range of the time interval between advertisements. Shorter intervals result in faster discovery at the cost of higher power consumption. The exact interval used is determined by the Bluetooth controller.
Time = N * 0.625ms.
Time range: 0x0020 (20ms) - 0x4000 (10.24s)
-
struct AdvertisingParameters#
Represents the parameters for configuring advertisements.
Public Members
-
AdvertisingData data#
The fields that will be encoded in the data section of advertising packets.
-
std::optional<AdvertisingData> scan_response#
The fields that are to be sent in a scan response packet. Clients may use this to send additional data that does not fit inside an advertising packet on platforms that do not support the advertising data length extensions.
If present advertisements will be configured to be scannable.
-
AdvertisingIntervalRange interval_range#
See
AdvertisingIntervalRange
documentation.
-
std::optional<ConnectionOptions> connection_options#
If present, the controller will broadcast connectable advertisements which allow peers to initiate connections to the Peripheral. The fields of
ConnectionOptions
will configure any connections set up from advertising.
-
AdvertisingData data#
-
enum class AdvertiseError#
low_energy::AdvertisedPeripheral#
-
class AdvertisedPeripheral#
AdvertisedPeripheral
instances are valid for the duration of advertising.Public Types
-
using Ptr = internal::RaiiPtr<AdvertisedPeripheral, &AdvertisedPeripheral::StopAdvertising>#
Movable AdvertisedPeripheral smart pointer. The peripheral will continue advertising until the returned AdvertisedPeripheral::Ptr is destroyed.
Public Functions
-
virtual void SetErrorCallback(Closure callback) = 0#
Set a callback that will be called when an error occurs and advertising has been stopped (invalidating this object). It is OK to destroy the
AdvertisedPeripheral::Ptr
object from withincallback
.
-
virtual void SetConnectionCallback(Function<void(Connection::Ptr)> &&callback) = 0#
For connectable advertisements, this callback will be called when an LE central connects to the advertisement. It is recommended to set this callback immediately after advertising starts to avoid dropping connections.
The returned Connection can be used to interact with the peer. It also represents a peripheral’s ownership over the connection: the client can drop the object to request a disconnection. Similarly, the Connection error handler is called by the system to indicate that the connection to the peer has been lost. While connections are exclusive among peripherals, they may be shared with centrals.
If advertising is not stopped, this callback may be called with multiple connections over the lifetime of an advertisement. It is OK to destroy the
AdvertisedPeripheral::Ptr
object from withincallback
in order to stop advertising.
-
using Ptr = internal::RaiiPtr<AdvertisedPeripheral, &AdvertisedPeripheral::StopAdvertising>#
low_energy::Connection#
-
class Connection#
Class that represents a connection to a peer. This can be used to interact with GATT services and establish LE L2CAP channels.
This lifetime of this object is tied to that of the LE connection it represents. Destroying the object results in a disconnection.
Public Types
-
enum class ConnectionParameterUpdateError : uint8_t#
Possible errors when updating the connection parameters.
Values:
-
enumerator kFailure#
-
enumerator kInvalidParameters#
-
enumerator kRejected#
-
enumerator kFailure#
-
enum class DisconnectReason : uint8_t#
Possible reasons a connection was disconnected.
Values:
-
enumerator kFailure#
-
enumerator kRemoteUserTerminatedConnection#
-
enumerator kConnectionTimeout#
This usually indicates that the link supervision timeout expired.
-
enumerator kFailure#
-
using Ptr = internal::RaiiPtr<Connection, &Connection::Disconnect>#
Movable Connection smart pointer. When Connection::Ptr is destroyed the Connection will disconnect automatically.
Public Functions
-
virtual ~Connection() = default#
If a disconnection has not occurred, destroying this object will result in disconnection.
-
virtual void SetDisconnectCallback(Function<void(DisconnectReason)> &&callback) = 0#
Sets a callback that will be called when the peer disconnects or there is a connection error that causes a disconnection. This should be configured by the client immediately after establishing the connection.
callback
will not be called for disconnections initiated by the client (e.g. by destroyingConnection
). It is OK to destroy this object from withincallback
.
-
virtual gatt::Client *GattClient() = 0#
Returns a GATT client to the connected peer that is valid for the lifetime of this connection. The client is valid for the lifetime of this connection.
-
virtual uint16_t AttMtu() = 0#
Returns the current ATT Maximum Transmission Unit. By subtracting ATT headers from the MTU, the maximum payload size of messages can be calculated.
-
virtual void SetAttMtuChangeCallback(Function<void(uint16_t)> callback) = 0#
Sets a callback that will be called with the new ATT MTU whenever it is updated.
-
virtual ConnectionParameters Parameters() = 0#
Returns the current connection parameters.
-
virtual void RequestConnectionParameterUpdate(RequestedConnectionParameters parameters, Function<void(Result<ConnectionParameterUpdateError>)> &&callback) = 0#
Requests an update to the connection parameters.
callback
will be called with the result of the request.
-
enum class ConnectionParameterUpdateError : uint8_t#
low_energy::ConnectionOptions#
-
struct ConnectionOptions#
Represents parameters that are set on a per-connection basis.
Public Members
-
bool bondable_mode = true#
When true, the connection operates in bondable mode. This means pairing will form a bond, or persist across disconnections, if the peer is also in bondable mode. When false, the connection operates in non-bondable mode, which means the local device only allows pairing that does not form a bond.
-
std::optional<Uuid> service_filter#
When present, service discovery performed following the connection is restricted to primary services that match this field. Otherwise, by default all available services are discovered.
-
std::optional<RequestedConnectionParameters> parameters#
When present, specifies the initial connection parameters. Otherwise, the connection parameters will be selected by the implementation.
-
bool bondable_mode = true#
low_energy::RequestedConnectionParameters#
-
struct RequestedConnectionParameters#
Connection parameters that either the local device or a peer device are requesting.
Public Members
-
uint16_t min_interval#
Minimum value for the connection interval. This shall be less than or equal to
max_interval
. The connection interval indicates the frequency of link layer connection events over which data channel PDUs can be transmitted. See Core Spec v5.3, Vol 6, Part B, Section 4.5.1 for more information on the link layer connection events.Range: 0x0006 to 0x0C80
Time: N * 1.25 ms
Time Range: 7.5 ms to 4 s.
-
uint16_t max_interval#
Maximum value for the connection interval. This shall be greater than or equal to
min_interval
. The connection interval indicates the frequency of link layer connection events over which data channel PDUs can be transmitted. See Core Spec v5.3, Vol 6, Part B, Section 4.5.1 for more information on the link layer connection events.Range: 0x0006 to 0x0C80
Time: N * 1.25 ms
Time Range: 7.5 ms to 4 s.
-
uint16_t max_latency#
Maximum peripheral latency for the connection in number of connection events. See Core Spec v5.3, Vol 6, Part B, Section 4.5.2.
Range: 0x0000 to 0x01F3
-
uint16_t supervision_timeout#
This defines the maximum time between two received data packet PDUs before the connection is considered lost. See Core Spec v5.3, Vol 6, Part B, Section 4.5.2.
Range: 0x000A to 0x0C80
Time: N * 10 ms
Time Range: 100 ms to 32 s
-
uint16_t min_interval#
low_energy::ConnectionParameters#
-
struct ConnectionParameters#
Actual connection parameters returned by the controller.
Public Members
-
uint16_t interval#
The connection interval indicates the frequency of link layer connection events over which data channel PDUs can be transmitted. See Core Spec v5.3, Vol 6, Part B, Section 4.5.1 for more information on the link layer connection events.
Range: 0x0006 to 0x0C80
Time: N * 1.25 ms
Time Range: 7.5 ms to 4 s.
-
uint16_t latency#
The maximum allowed peripheral connection latency in number of connection events. See Core Spec v5.3, Vol 6, Part B, Section 4.5.2.
Range: 0x0000 to 0x01F3
-
uint16_t supervision_timeout#
This defines the maximum time between two received data packet PDUs before the connection is considered lost. See Core Spec v5.3, Vol 6, Part B, Section 4.5.2.
Range: 0x000A to 0x0C80
Time: N * 10 ms
Time Range: 100 ms to 32 s
-
uint16_t interval#
gatt::Server#
-
class Server#
Interface for a GATT server that serves many GATT services.
Public Types
-
using PublishServiceResult = Result<PublishServiceError, LocalService::Ptr>#
The Result passed by PublishService.
Public Functions
-
virtual void PublishService(const LocalServiceInfo &info, LocalServiceDelegate *delegate, Function<void(PublishServiceResult)> &&result_callback) = 0#
Publishes the service defined by
info
and implemented bydelegate
so that it is available to all remote peers.The caller must assign distinct handles to the characteristics and descriptors listed in
info
. These identifiers will be used in requests sent todelegate
. On success, aLocalService::Ptr
is returned. When theLocalService::Ptr
is destroyed or an error occurs (LocalServiceDelegate.OnError), the service will be unpublished.
-
using PublishServiceResult = Result<PublishServiceError, LocalService::Ptr>#
gatt::LocalServiceInfo#
-
struct LocalServiceInfo#
Parameters for registering a local GATT service.
Public Members
-
bool primary#
Indicates whether this is a primary or secondary service.
-
Uuid type#
The UUID that identifies the type of this service. There may be multiple services with the same UUID.
-
span<const Characteristic> characteristics#
The characteristics of this service.
-
span<const Handle> includes#
Handles of other services that are included by this service.
-
bool primary#
gatt::LocalService#
-
class LocalService#
Interface provided by the backend to interact with a published service. LocalService is valid for the lifetime of a published GATT service. It is used to control the service and send notifications/indications.
Public Types
-
using ValueChangedResult = Result<Error>#
The Result type for a ValueChanged indication or notification message. The error can be locally generated for notifications and either locally or remotely generated for indications.
-
using ValueChangedCallback = Function<void(ValueChangedResult)>#
The callback type for a ValueChanged indication or notification completion.
-
using Ptr = internal::RaiiPtr<LocalService, &LocalService::UnpublishService>#
Movable LocalService smart pointer. When the LocalService::Ptr object is destroyed the service will be unpublished.
Public Functions
-
virtual void NotifyValue(const ValueChangedParameters ¶meters, ValueChangedCallback &&completion_callback) = 0#
Sends a notification to peers. Notifications should be used instead of indications when the service does not require peer confirmation of the update.
Notifications should not be sent to peers which have not enabled notifications on a particular characteristic or that have disconnected since - if they are sent, they will not be propagated and the
completion_callback
will be called with an error condition. The Bluetooth stack will track this configuration for the lifetime of the service.The maximum size of the
parameters.value
field depends on the MTU negotiated with the peer. A 3-byte header plus the value contents must fit in a packet of MTU bytes.- Parameters:
parameters – The parameters associated with the changed characteristic.
completion_callback – Called when the notification has been sent to all peers or an error is produced when trying to send the notification to any of the peers. This function is called only once when all associated work is done, if the implementation wishes to receive a call on a per-peer basis, they should send this event with a single PeerId in
parameters.peer_ids
. Additional values should not be notified until this callback is called.
-
virtual void IndicateValue(const ValueChangedParameters ¶meters, ValueChangedCallback &&confirmation) = 0#
Sends an indication to peers. Indications should be used instead of notifications when the service does require peer confirmation of the update.
Indications should not be sent to peers which have not enabled indications on a particular characteristic - if they are sent, they will not be propagated. The Bluetooth stack will track this configuration for the lifetime of the service.
If any of the peers in
parameters.peer_ids
fails to confirm the indication within the ATT transaction timeout (30 seconds per Bluetooth 5.2 Vol. 4 Part G 3.3.3), the link between the peer and the local adapter will be closed.The maximum size of the
parameters.value
field depends on the MTU negotiated with the peer. A 3-byte header plus the value contents must fit in a packet of MTU bytes.- Parameters:
parameters – The parameters associated with the changed characteristic.
confirmation – When all the peers listed in
parameters.peer_ids
have confirmed the indication,confirmation
is called. If the implementation wishes to receive indication confirmations on a per-peer basis, they should send this event with a single PeerId inparameters.peer_ids
. Additional values should not be indicated until this callback is called.
-
struct ValueChangedParameters#
The parameters used to signal a characteristic value change from a LocalService to a peer.
Public Members
-
span<const PeerId> peer_ids#
The PeerIds of the peers to signal. The LocalService should respect the Characteristic Configuration associated with a peer+handle when deciding whether to signal it. If empty, all peers are signalled.
-
Handle handle#
The handle of the characteristic value being signaled.
-
span<const std::byte> value#
The new value for the descriptor/characteristic.
-
span<const PeerId> peer_ids#
-
using ValueChangedResult = Result<Error>#
gatt::LocalServiceDelegate#
-
class LocalServiceDelegate#
Interface for serving a local GATT service. This is implemented by the API client.
Public Functions
-
virtual void OnError(Error error) = 0#
Called when there is a fatal error related to this service that forces the service to close. LocalServiceDelegate methods will no longer be called. This invalidates the associated LocalService. It is OK to destroy both
LocalServiceDelegate
and the associatedLocalService::Ptr
from within this method.
-
virtual void CharacteristicConfiguration(PeerId peer_id, Handle handle, bool notify, bool indicate) = 0#
This notifies the current configuration of a particular characteristic/descriptor for a particular peer. It will be called when the peer GATT client changes the configuration.
The Bluetooth stack maintains the state of each peer’s configuration across reconnections. As such, this method will be called with both
notify
andindicate
set to false for each characteristic when a peer disconnects. Also, when a peer reconnects this method will be called again with the initial, persisted state of the newly-connected peer’s configuration. However, clients should not rely on this state being persisted indefinitely by the Bluetooth stack.- Parameters:
peer_id – The PeerId of the GATT client associated with this particular CCC.
handle – The handle of the characteristic associated with the
notify
andindicate
parameters.notify – True if the client has enabled notifications, false otherwise.
indicate – True if the client has enabled indications, false otherwise.
-
virtual void ReadValue(PeerId peer_id, Handle handle, uint32_t offset, Function<void(Result<Error, span<const std::byte>>)> &&result_callback) = 0#
Called when a peer requests to read the value of a characteristic or descriptor. It is guaranteed that the peer satisfies the permissions associated with this attribute.
- Parameters:
peer_id – The PeerId of the GATT client making the read request.
handle – The handle of the requested descriptor/characteristic.
offset – The offset at which to start reading the requested value.
result_callback – Called with the value of the characteristic on success, or an Error on failure. The value will be truncated to fit in the MTU if necessary. It is OK to call
result_callback
inReadValue
.
-
virtual void WriteValue(PeerId peer_id, Handle handle, uint32_t offset, span<const std::byte> value, Function<void(Result<Error>)> &&status_callback) = 0#
Called when a peer issues a request to write the value of a characteristic or descriptor. It is guaranteed that the peer satisfies the permissions associated with this attribute.
- Parameters:
peer_id – The PeerId of the GATT client making the write request.
handle – The handle of the requested descriptor/characteristic.
offset – The offset at which to start writing the requested value. If the offset is 0, any existing value should be overwritten by the new value. Otherwise, the existing value between
offset:(offset + len(value))
should be changed tovalue
.value – The new value for the descriptor/characteristic.
status_callback – Called with the result of the write.
-
virtual void MtuUpdate(PeerId peer_id, uint16_t mtu) = 0#
Called when the MTU of a peer is updated. Also called for peers that are already connected when the server is published.
Notifications and indications must fit in a single packet including both the 3-byte notification/indication header and the user-provided payload. If these are not used, the MTU can be safely ignored as it is intended for use cases where the throughput needs to be optimized.
-
virtual void OnError(Error error) = 0#
gatt::Client#
-
class Client#
Represents a GATT client that interacts with services on a GATT server.
Public Functions
-
virtual void WatchServices(Vector<Uuid> uuid_allowlist, Function<void(RemoteServiceInfo)> &&updated_callback, Function<void(Handle)> &&removed_callback) = 0#
Enumerates existing services found on the peer that this Client represents, and provides a stream of updates thereafter. Results can be filtered by specifying a list of UUIDs in
uuids
. To further interact with services, clients must obtain a RemoteService protocol by calling ConnectToService().uuid_allowlist
- The allowlist of UUIDs to filter services with.updated_callback
- Will be called with services that are updated/modified.removed_callback
- Called with the handles of services that have been removed. Note that handles may be reused.
-
virtual void StopWatchingServices()#
Stops service watching if started by
WatchServices
.
-
virtual Result<Error, RemoteService::Ptr> ConnectToService(Handle handle) = 0#
Connects to a RemoteService. Only 1 connection per service is allowed.
handle
- the handle of the service to connect to.This may fail with the following errors: kInvalidParameters -
handle
does not correspond to a known service.
-
struct RemoteServiceInfo#
Represents a remote GATT service.
-
virtual void WatchServices(Vector<Uuid> uuid_allowlist, Function<void(RemoteServiceInfo)> &&updated_callback, Function<void(Handle)> &&removed_callback) = 0#
gatt::RemoteService#
-
class RemoteService#
Represents a GATT service on a remote GATT server. Clients should call
SetErrorCallback
before using in order to handle fatal errors.Public Types
-
enum class WriteMode : uint8_t#
Represents the supported write modes for writing characteristics & descriptors to the server.
Values:
-
enumerator kDefault#
Wait for a response from the server before returning but do not verify the echo response. Supported for both characteristics and descriptors.
-
enumerator kReliable#
Every value blob is verified against an echo response from the server. The procedure is aborted if a value blob has not been reliably delivered to the peer. Only supported for characteristics.
-
enumerator kWithoutResponse#
Delivery will not be confirmed before returning. Writing without a response is only supported for short characteristics with the
WRITE_WITHOUT_RESPONSE
property. The value must fit into a single message. It is guaranteed that at least 20 bytes will fit into a single message. If the value does not fit, akFailure
error will be produced. The value will be written at offset 0. Only supported for characteristics.
-
enumerator kDefault#
-
using Ptr = internal::RaiiPtr<RemoteService, &RemoteService::Disconnect>#
Movable RemoteService smart pointer. The remote server will remain connected until the returned RemoteService::Ptr is destroyed.
Public Functions
-
void SetErrorCallback(Function<void(RemoteServiceError)> &&error_callback)#
Set a callback that will be called when there is an error with this RemoteService, after which this RemoteService will be invalid.
-
void DiscoverCharacteristics(Function<void(Characteristic)> &&characteristic_callback)#
Calls
characteristic_callback
with the characteristics and descriptors in this service.
-
void ReadByType(Uuid uuid, ReadByTypeCallback &&result_callback)#
Reads characteristics and descriptors with the specified type. This method is useful for reading values before discovery has completed, thereby reducing latency.
This may fail with the following errors:
kInvalidParameters: if
uuid
refers to an internally reserved descriptor type (e.g. the Client Characteristic Configuration descriptor).kTooManyResults: More results were read than can fit in a Vector. Consider reading characteristics/descriptors individually after performing discovery.
kFailure: The server returned an error not specific to a single result.
- Parameters:
uuid – The UUID of the characteristics/descriptors to read.
result_callback – Results are returned via this callback. Results may be empty if no matching values are read. If reading a value results in a permission error, the handle and error will be included.
-
void ReadCharacteristic(Handle handle, std::optional<LongReadOptions> options, ReadCallback &&result_callback)#
Reads the value of a characteristic.
- retval kInvalidHandle:
handle
is invalid.- retval kInvalidParameters:
options
is invalid.- retval kReadNotPermitted:
The server rejected the request.
- retval kInsufficient*:
The server rejected the request.
- retval kFailure:
The server returned an error not covered by the above.
- Parameters:
handle – The handle of the characteristic to be read.
options – If null, a short read will be performed, which may be truncated to what fits in a single message (at least 22 bytes). If long read options are present, performs a long read with the indicated options.
result_callback – called with the result of the read and the value of the characteristic if successful.
-
void WriteCharacteristic(Handle handle, span<const std::byte> value, WriteOptions options, Function<void(Result<Error>)> &&result_callback)#
Writes
value
to the characteristic withhandle
using the providedoptions
. It is not recommended to send additional writes while a write is already in progress (the server may receive simultaneous writes in any order).- retval kInvalidHandle:
handle
is invalid.- retval kInvalidParameters`options:
is invalid.
- retval kWriteNotPermitted:
The server rejected the request.
- retval kInsufficient*:
The server rejected the request.
- retval kFailure:
The server returned an error not covered by the above errors.
- Parameters:
handle – Handle of the characteristic to be written to
value – The value to be written.
options – Options that apply to the write.
result_callback – Returns a result upon completion of the write.
-
void ReadDescriptor(Handle handle, std::optional<LongReadOptions> options, ReadCallback &&result_callback)#
Reads the value of the characteristic descriptor with
handle
and returns it in the reply.- retval kInvalidHandle:
handle
is invalid.- retval kInvalidParameters`options`:
is invalid.
- retval kReadNotPermitted:
- retval kInsufficient*:
The server rejected the request.
- retval kFailure:
The server returned an error not covered by the above errors.
- Parameters:
handle – The descriptor handle to read.
options – Options that apply to the read.
result_callback – Returns a result containing the value of the descriptor on success.
-
void WriteDescriptor(Handle handle, span<const std::byte> value, WriteOptions options, Function<void(Result<Error>)> &&result_callback)#
Writes
value
to the descriptor withhandle
using the providedoptions
. It is not recommended to send additional writes while a write is already in progress (the server may receive simultaneous writes in any order).- retval kInvalidHandle:
handle
is invalid.- retval kInvalidParameters:
`options is invalid
- retval kWriteNotPermitted:
The server rejected the request.
- retval kInsufficient*:
The server rejected the request.
- retval kFailure:
The server returned an error not covered by the above errors.
- Parameters:
handle – Handle of the descriptor to be written to
value – The value to be written.
options – Options that apply to the write.
result_callback – Returns a result upon completion of the write.
-
void RegisterNotificationCallback(Handle handle, NotificationCallback &¬ification_callback, Function<void(Result<Error>)> &&result_callback)#
Subscribe to notifications & indications from the characteristic with the given
handle
.Either notifications or indications will be enabled depending on characteristic properties. Indications will be preferred if they are supported. This operation fails if the characteristic does not have the “notify” or “indicate” property.
A write request will be issued to configure the characteristic for notifications/indications if it contains a Client Characteristic Configuration descriptor. This method fails if an error occurs while writing to the descriptor.
On success,
notification_callback
will be called when the peer sends a notification or indication. Indications are automatically confirmed.Subscriptions can be canceled with
StopNotifications
.- retval kFailure:
The characteristic does not support notifications or indications.
- retval kInvalidHandle:
handle
is invalid.- retval kWriteNotPermitted:
CCC descriptor write error.
- retval Insufficient*:
CCC descriptor write error.
- Parameters:
handle – the handle of the characteristic to subscribe to.
notification_callback – will be called with the values of notifications/indications when received.
result_callback – called with the result of enabling notifications/indications.
-
void StopNotifications(Handle handle)#
Stops notifications for the characteristic with the given
handle
.
-
struct LongReadOptions#
Represents the supported options to read a long characteristic or descriptor value from a server. Long values are those that may not fit in a single message (longer than 22 bytes).
-
struct ReadByTypeResult#
A result returned by
ReadByType
.
-
struct ReadValue#
Wrapper around a possible truncated value received from the server.
Public Members
-
Handle handle#
Characteristic or descriptor handle.
-
Vector<std::byte> value#
The value of the characteristic or descriptor.
-
bool maybe_truncated#
True if
value
might be truncated (the buffer was completely filled by the server and the read was a short read).ReadCharacteristic
orReadDescriptor
should be used to read the complete value.
-
Handle handle#
-
struct WriteOptions#
Represents the supported options to write a characteristic/descriptor value to a server.
Public Members
-
WriteMode mode = WriteMode::kDefault#
The mode of the write operation. For descriptors, only
WriteMode::kDefault
is supported
-
uint16_t offset = 0#
Request a write starting at the byte indicated. Must be 0 if
mode
isWriteMode.kWithoutResponse
.
-
WriteMode mode = WriteMode::kDefault#
-
enum class WriteMode : uint8_t#
Callbacks#
Pigweed AI summary: The "Callbacks" module has APIs that heavily rely on callbacks. It is important to note that callbacks should not call back into the "pw_bluetooth" APIs, unless specified otherwise. This also applies to calls made by destroying objects returned by the API. Furthermore, callbacks should not block.
This module contains callback-heavy APIs. Callbacks must not call back into the
pw_bluetooth
APIs unless otherwise noted. This includes calls made by
destroying objects returned by the API. Additionally, callbacks must not block.
Emboss Packet Definitions#
Pigweed AI summary: This paragraph describes the Emboss Packet Definitions, which contains packet definitions for various protocols, including HCI. The usage of Emboss is explained, including setting GN variables and adding dependencies. The paragraph also includes code examples for constructing an Emboss view over a buffer and a note about building the project to resolve issues with generated header files. Finally, a size report is provided, showing the delta when constructing and reading/writing fields for the first and second packet views.
pw_bluetooth
contains Emboss packet
definitions. So far, packets from the following protocols are defined:
HCI
Usage#
Pigweed AI summary: This section provides instructions on how to use Emboss with Bluetooth in a C++ project. It includes steps such as setting the GN variable, adding dependencies, including generated header files, and constructing an Emboss view over a buffer. The section also includes a note about resolving issues with generated header files by building the project.
1. Set the dir_pw_third_party_emboss GN variable to the path of your Emboss checkout.
2. Add $dir_pw_bluetooth/emboss_hci (for HCI packets) or $dir_pw_bluetooth/emboss_vendor (for vendor packets) to your dependency list.
Include the generated header files.
#include "pw_bluetooth/hci.emb.h"
#include "pw_bluetooth/vendor.emb.h"
Construct an Emboss view over a buffer.
std::array<uint8_t, 4> buffer = {0x00, 0x01, 0x02, 0x03};
auto view = pw::bluetooth::emboss::MakeTestCommandPacketView(&buffer);
EXPECT_EQ(view.payload().Read(), 0x03);
Note
clangd will complain that the generated header file does not exist. You need to build your project to resolve this. Similarly, you need to build in order for .emb file updates to be reflected in the generated headers.
Size Report#
Pigweed AI summary: The Size Report section shows the delta of +972 when constructing the first packet view and reading/writing a field, including the runtime library and 4-byte buffer. There is also a delta of +96 when adding a second packet view and reading/writing a field. The table shows that Emboss is not configured and there is no delta for it.
Delta of +972 when constructing the first packet view and reading/writing a field. This includes the runtime library and the 4-byte buffer.
Label |
Segment |
Delta |
---|---|---|
Emboss not configured. |
(ALL) |
0 |
Delta of +96 when adding a second packet view and reading/writing a field.
Label |
Segment |
Delta |
---|---|---|
Emboss not configured. |
(ALL) |
0 |
Roadmap#
Pigweed AI summary: The roadmap for Fuchsia's Bluetooth API includes creating a backend using the sapphire Bluetooth stack, stabilizing the API, adding BR/EDR APIs, and adding support for Bazel and CMake.
Create a backend for the Bluetooth API using Fuchsia’s Bluetooth stack (sapphire).
Stabilize the Bluetooth API.
Add BR/EDR APIs.
Bazel support
CMake support