Сверхширокополосная связь – это технология радиосвязи, которая позволяет точно определять расстояние между устройствами (с погрешностью до 10 см). Эта технология позволяет измерять расстояния в небольшом диапазоне при низкой плотности энергии и передавать сигналы с высокой пропускной способностью в широком спектре радиочастот. Пропускная способность СШП превышает 500 МГц (или 20% относительной пропускной способности).
Контроллер/инициатор и управляемое устройство/ответчик
Связь по СШП устанавливается между двумя устройствами, одно из которых является контроллером, а другое – управляемым устройством. Контроллер определяет комплексный канал (UwbComplexChannel), который будут использовать оба устройства, и инициирует подключение, а контролируемое устройство отвечает на запрос.
Контроллер может управлять несколькими устройствами, но управляемое устройство может быть подписано только на один контроллер. Поддерживаются конфигурации контроллера/инициатора и управляемого устройства/ответчика.
Параметры ранжирования
Чтобы начать измерение расстояния, контроллер и контролируемое устройство должны идентифицировать друг друга и обменяться параметрами измерения. Этот обмен выполняется приложениями с помощью безопасного механизма внеполосной передачи данных (OOB), например Bluetooth с низким энергопотреблением (BLE).
Параметры определения расстояния включают локальный адрес, комплексный канал, сеансовый ключ и т. д. Обратите внимание, что эти параметры могут меняться после завершения сеанса определения расстояния. Чтобы начать новый сеанс, их нужно передать заново.
Определение расстояния в фоновом режиме
Приложение, работающее в фоновом режиме, может запустить сеанс измерения расстояния с помощью СШП, если устройство поддерживает эту технологию. Чтобы узнать, какие возможности поддерживает ваше устройство, ознакомьтесь со статьей RangingCapabilities.
Приложение не получает отчеты о дальности, когда работает в фоновом режиме. Отчеты поступают, когда приложение переходит в активный режим.
Конфигурации STS
Приложение или сервис предоставляет сеансовый ключ для каждого сеанса, используя зашифрованную последовательность временных меток (STS). Инициализированная конфигурация STS более безопасна, чем статическая. Инициализированная STS поддерживается на всех устройствах с поддержкой СШП и Android 14 или более поздней версии.
| Категория угрозы | Статический STS | Предоставленный STS |
|---|---|---|
| Воздух: пассивный наблюдатель | Риск нейтрализован | Риск нейтрализован |
| Воздух: усиление сигнала | Риск нейтрализован | Риск нейтрализован |
| Воздух: атака повторного воспроизведения/ретрансляции | Восприимчивость | Риск нейтрализован |
Для инициализированных STS:
Используйте
uwbConfigTypeвRangingParameters, который поддерживает подготовленный STS.Укажите 16-байтовый ключ в поле
sessionKeyInfo.
Для статического STS:
Используйте
uwbConfigTypeвRangingParameters, который поддерживает статический STS.Укажите 8-байтовый ключ в поле
sessionKeyInfo.
Шаги
Чтобы использовать UWB API, выполните следующие действия:
- Убедитесь, что на устройствах Android установлена ОС Android 12 или более поздней версии и что они поддерживают СШП, используя
PackageManager#hasSystemFeature("android.hardware.uwb"). - Если вы измеряете расстояние до устройств IoT, убедитесь, что они соответствуют стандарту FiRa MAC 1.3.
- Обнаружьте устройства с поддержкой СШП, используя выбранный вами механизм OOB, например
BluetoothLeScanner. - Обменяйтесь параметрами измерения расстояния, используя выбранный вами безопасный механизм OOB, например
BluetoothGatt. - Если пользователь хочет остановить сеанс, отмените область действия сеанса.
Ограничения на использование
При использовании UWB API действуют следующие ограничения:
- Приложение, инициирующее новые сеансы определения расстояния с помощью СШП, должно быть активным приложением или службой, если только не поддерживается определение расстояния в фоновом режиме, как показано выше.
- Когда приложение переходит в фоновый режим (пока сеанс продолжается), оно может перестать получать отчеты о дальности. Однако сеанс UWB будет поддерживаться на нижних уровнях. Когда приложение снова перейдет в активный режим, отчеты о дальности возобновятся.
Образцы кода
Пример приложения
Чтобы узнать, как использовать библиотеку UWB Jetpack, ознакомьтесь с примером приложения на GitHub. В этом примере приложения рассматривается проверка совместимости СШП на устройстве Android, включение процесса обнаружения с помощью механизма OOB и настройка СШП-диапазона между двумя устройствами с поддержкой СШП. В примере также рассматриваются варианты использования управления устройствами и обмена медиафайлами.
СШП-дальнометрия
В этом примере кода показано, как запустить и завершить измерение расстояния с помощью СШП для управляемого устройства.
// The coroutineScope responsible for handling uwb ranging.
// This will be initialized when startRanging is called.
var job: Job?
// A code snippet that initiates uwb ranging for a Controlee.
suspend fun startRanging() {
// Get the ranging parameter of a partnering Controller using an OOB mechanism of choice.
val partnerAddress : Pair<UwbAddress, UwbComplexChannel> = listenForPartnersAddress()
// Create the ranging parameters.
val partnerParameters = RangingParameters(
uwbConfigType = UwbRangingParameters.UWB_CONFIG_ID_1,
// SessionKeyInfo is used to encrypt the ranging session.
sessionKeyInfo = null,
complexChannel = partnerAddress.second,
peerDevices = listOf(UwbDevice.createForAddress(partnerAddress.first)),
updateRateType = UwbRangingParameters.RANGING_UPDATE_RATE_AUTOMATIC
)
// Initiate a session that will be valid for a single ranging session.
val clientSession = uwbManager.clientSessionScope()
// Share the localAddress of the current session to the partner device.
broadcastMyParameters(clientSession.localAddress)
val sessionFlow = clientSession.prepareSession(partnerParameters)
// Start a coroutine scope that initiates ranging.
CoroutineScope(Dispatchers.Main.immediate).launch {
sessionFlow.collect {
when(it) {
is RangingResultPosition -> doSomethingWithPosition(it.position)
is RangingResultPeerDisconnected -> peerDisconnected(it)
}
}
}
}
// A code snippet that cancels uwb ranging.
fun cancelRanging() {
// Canceling the CoroutineScope will stop the ranging.
job?.let {
it.cancel()
}
}
Поддержка RxJava3
Добавлена поддержка Rxjava3 для обеспечения совместимости с клиентами Java. Эта библиотека позволяет получать результаты измерения расстояния в виде потока Observable или Flowable, а также получать UwbClientSessionScope в виде объекта Single.
private final UwbManager uwbManager;
// Retrieve uwbManager.clientSessionScope as a Single object
Single<UwbClientSessionScope> clientSessionScopeSingle =
UwbManagerRx.clientSessionScopeSingle(uwbManager);
UwbClientSessionScope uwbClientSessionScope = clientSessionScopeSingle.blockingGet();
// Retrieve uwbClientSessionScope.prepareSession Flow as an Observable object
Observable<RangingResult> rangingResultObservable =
UwbClientSessionScopeRx.rangingResultsObservable(clientSessionScope,
rangingParameters);
// Consume ranging results from Observable
rangingResultObservable.subscribe(
rangingResult -> doSomethingWithRangingResult(result), // onNext
(error) -> doSomethingWithError(error), // onError
() -> doSomethingOnResultEventsCompleted(), //onCompleted
);
// Unsubscribe
rangingResultObservable.unsubscribe();
// Retrieve uwbClientSessionScope.prepareSession Flow as a Flowable object
Flowable<RangingResult> rangingResultFlowable =
UwbClientSessionScopeRx.rangingResultsFlowable(clientSessionScope,
rangingParameters);
// Consume ranging results from Flowable using Disposable
Disposable disposable = rangingResultFlowable
.delay(1, TimeUnit.SECONDS)
.subscribeWith(new DisposableSubscriber<RangingResult> () {
@Override public void onStart() {
request(1);
}
@Override public void onNext(RangingResult rangingResult) {
doSomethingWithRangingResult(rangingResult);
request(1);
}
@Override public void onError(Throwable t) {
t.printStackTrace();
}
@Override public void onComplete() {
doSomethingOnEventsCompleted();
}
});
// Stop subscription
disposable.dispose();
Поддержка экосистемы
Ниже перечислены поддерживаемые партнерские устройства и сторонние SDK.
Мобильные устройства с поддержкой СШП
По состоянию на январь 2025 года библиотеку Android UWB Jetpack поддерживают следующие устройства:
| Поставщик | Модель устройства |
|---|---|
| Pixel Pro (6 Pro и более новые модели), Fold, Tablet | |
| Motorola | edge 50 ultra |
| Samsung | Galaxy Note 20, Galaxy Plus и Ultra (S21 и более новые модели), Galaxy Z Fold (Fold2 и более новые модели). |
Примечание. Фоновое измерение расстояния с помощью СШП поддерживается на всех устройствах, кроме следующих:
- Pixel 6 Pro, Pixel 7 Pro и Pixel Fold.
- Телефоны Samsung с Android 13 или более ранней версии.
- Телефоны Samsung, выпущенные для Китая, с Android 14 или более ранней версией.
Сторонние SDK
По состоянию на апрель 2023 года эти партнерские решения совместимы с текущей версией библиотеки Jetpack.
- UWB Development Kit от Estimote.
- Mobile Knowledge MK UWB Kit Mobile Edition 2.0.
Известная проблема: обратный порядок байтов для MAC-адреса и полей идентификатора поставщика статического STS
В Android 13 и более ранних версиях стек СШП неправильно меняет порядок байтов для следующих полей:
- MAC-адрес устройства
- MAC-адрес получателя
- Статический идентификатор поставщика STS
Обратный порядок байтов происходит потому, что стек Android обрабатывает эти поля как значения, а не массивы. Мы работаем с FiRa над обновлением спецификации UCI (CR-1112), чтобы явно указать, что эти поля должны обрабатываться как массивы.
Эта проблема будет устранена в обновлении GMS Core в выпуске за 2320XXXX.
Чтобы обеспечить совместимость с устройствами Android, поставщикам IoT-устройств нужно изменить реализацию и не менять порядок байтов в этих полях.