blob: a6b917589156407c0bffdb7d28d87b124c3aaa8e [file] [view]
# bt-broadcast-assistant
This crate implements the **Broadcast Assistant** role defined in the Bluetooth SIG [Basic Audio Profile (BAP) v1.0.2][bap] specification.
A Broadcast Assistant is a Bluetooth Low Energy (LE) device (typically a smartphone or tablet) that discovers Broadcast Sources and assists Broadcast Sinks (Scan Delegators) in synchronizing to LE Audio broadcast streams.
## Overview
The `bt-broadcast-assistant` crate handles:
1. **Broadcast Source Discovery & Synchronization:**
- **Extended Advertising (EA) Scanning:** Scans for advertisements containing the Broadcast Audio Announcement Service UUID (`0x1852`) to extract the `Broadcast_ID` and `Broadcast_Name`.
- **Periodic Advertising (PA) Synchronization:** Automatically establishes Periodic Advertising sync using the platform's `bt_gatt::periodic_advertising::PeriodicAdvertising` trait when the Basic Audio Announcement Endpoint (BASE) structure (`0x1851`) is needed.
- **BASE Extraction:** Parses subgroups, Codec IDs, Codec Specific Configurations, Metadata, and BIS indices from the PA train data.
- **Resource Management:** Automatically cancels the PA sync once complete broadcast source information is gathered.
2. **Scan Delegator Management:**
- Scans for peers advertising the Broadcast Audio Scan Service (BASS, `0x184F`).
- Establishes GATT connections to Scan Delegators and provides high-level control operations via `bt_bass::BroadcastAudioScanServiceClient`:
- Add Broadcast Source
- Modify Broadcast Source
- Remove Broadcast Source
- Set Broadcast Code
3. **Platform Independence:**
- Uses the [`bt-gatt`][bt-gatt] crate interface to remain Bluetooth stack- and async executor-agnostic.
- On Fuchsia, integrated via `bt-gatt-fuchsia` (`FuchsiaTypes`).
## Architecture
```text
+--------------------------------+
| BroadcastAssistant<T> |
+--------------------------------+
/ \
+-----------------------+ +-----------------------+
| EventStream<T> | | Peer<T> |
| (Source Discovery & | | (BASS Client for |
| PA Sync via BASE) | | Scan Delegator) |
+-----------------------+ +-----------------------+
\ /
+--------------------------------+
| T: bt_gatt::GattTypes |
+--------------------------------+
```
## Usage Example
```rust,no_run
# use futures::StreamExt;
# use bt_broadcast_assistant::assistant::Error;
use bt_broadcast_assistant::{event::Event, BroadcastAssistant};
use bt_gatt::central::Central;
async fn run_assistant<T: bt_gatt::GattTypes + 'static>(central: T::Central) -> Result<(), Error> {
let mut assistant = BroadcastAssistant::<T>::new(central);
// Start scanning for broadcast sources (EA + PA sync)
let mut event_stream = assistant.start()?;
while let Some(event_res) = event_stream.next().await {
match event_res? {
Event::FoundBroadcastSource { peer, advertising_sid, source } => {
println!("Discovered complete broadcast source: {:?}", source);
// Can now add this source to a connected scan delegator peer!
}
Event::CouldNotParseAdvertisingData { peer, error } => {
eprintln!("Failed to parse advertisement from peer {:?}: {:?}", peer, error);
}
}
}
Ok(())
}
```
[bap]: https://www.bluetooth.com/specifications/specs/basic-audio-profile-1-0-2/
[bt-gatt]: ../bt-gatt/README.md