Android蓝牙协议栈fluoride(七) - 设备管理(bt stack)

前面几篇文章介绍了设备管理对上层的接口和bt profile层的实现,其中涉及到蓝牙开关(初始化)、设备扫描、服务发现、安全管理、功耗管理等等模块,本文将挑选几个模块介绍bt stack层的实现,其他模块(如安全管理)将在后续专门讲述。

使能蓝牙

协议栈中使能蓝牙的入口是BTM_DeviceReset,即打开蓝牙时会复位controller,复位之后会获取controller中的信息,然后将状态上报到上层。
在这里插入图片描述
其中,controller模块和HCI的内容在HCI相关的文章中介绍。

从上至下完整梳理使能蓝牙的流程如下:
在这里插入图片描述

设备扫描

在上层介绍设备管理时包含了设备扫描和服务发现,本文介绍设备扫描,服务发现使用的SDP,在后续介绍。
在stack层中对上提供设备扫描相关的API如下:

// inquiry/inquiry scan/page/page scan设置
tBTM_STATUS BTM_SetInquiryMode(uint8_t mode);
tBTM_STATUS BTM_SetInquiryScanType(uint16_t scan_type);
tBTM_STATUS BTM_SetPageScanType(uint16_t scan_type);
extern void BTM_WritePageTimeout(uint16_t timeout);

// 设置/获取本机可被发现及参数(inquiry scan)
tBTM_STATUS BTM_SetDiscoverability(uint16_t inq_mode, uint16_t window, uint16_t interval);
uint16_t BTM_ReadDiscoverability(uint16_t* p_window, uint16_t* p_interval);
// 设置/获取本机可被连接及参数(page scan)
tBTM_STATUS BTM_SetConnectability(uint16_t page_mode, uint16_t window, uint16_t interval);
uint16_t BTM_ReadConnectability(uint16_t* p_window, uint16_t* p_interval);

// 扫描周围设备相关(inquiry)
tBTM_STATUS BTM_StartInquiry(tBTM_INQ_PARMS* p_inqparms, tBTM_INQ_RESULTS_CB* p_results_cb, tBTM_CMPL_CB* p_cmpl_cb);
uint16_t BTM_IsInquiryActive(void);
tBTM_STATUS BTM_CancelInquiry(void);
tBTM_STATUS BTM_CancelPeriodicInquiry(void);

// EIR相关
tBTM_STATUS BTM_WriteEIR(BT_HDR* p_buff);
bool BTM_HasEirService(const uint32_t* p_eir_uuid, uint16_t uuid16);
void BTM_AddEirService(uint32_t* p_eir_uuid, uint16_t uuid16);
void BTM_RemoveEirService(uint32_t* p_eir_uuid, uint16_t uuid16);
uint8_t BTM_GetEirSupportedServices(uint32_t* p_eir_uuid, uint8_t** p, uint8_t max_num_uuid16, uint8_t* p_num_uuid16);
uint8_t BTM_GetEirUuidList(uint8_t* p_eir, size_t eir_len, uint8_t uuid_size, uint8_t* p_num_uuid, uint8_t* p_uuid_list, uint8_t max_num_uuid);

inquiry和inquiry scan

蓝牙通过inquiry发现周围的设备,进入可[被]发现的设备会一直inquiry scan,它们在特殊的物理信道发起请求和回复响应。
以手机和蓝牙耳机为例:手机扫描周围设备时会一直特定信道发送inquiry,耳机进入配对模式时会一直在特定信道扫描(监听)inquiry,当扫描到inquiry之后会回复inquiry response,手机收到response后就知道扫描到了这台设备。inquiry类型和方式如下:

// 类型
#define BTM_INQ_RESULT_STANDARD 0  // 标准inquiry格式返回结果
#define BTM_INQ_RESULT_WITH_RSSI 1 // 带RSSI的格式
#define BTM_INQ_RESULT_EXTENDED 2 // 带RSSI的结果或扩展查询格式

// 方式
#define BTM_GENERAL_INQUIRY 0x01  //通用inquiry,即发现所有可发现的设备
#define BTM_LIMITED_INQUIRY 0x02  // 有限inquiry,即发现一定范围内设置了有限inquiry代码的设备

通用inquiry的交互如下:

有限inquiry的交互如下:
在这里插入图片描述

EIR

EIR是Extended Inquiry Response的缩写,EIR是基本inquiry response外还可以携带更多的信息,即可以在不需要更多通信的情况下获得更多信息,如设备名称、支持的服务等。EIR数据格式如下:
在这里插入图片描述

page和page scan

当获取到另一台蓝牙设备的蓝牙地址后可以发起连接,此时发起连接的设备将在特殊通道发生连接请求包(page),另一台设备处于可连接状态即可监听(page scan)到连接请求,进行后续的通信。

inquiry scan和page scan的类型如下:

#define BTM_SCAN_TYPE_STANDARD 0  //标准扫描,一直扫描窗口内一直处于扫描状态
#define BTM_SCAN_TYPE_INTERLACED 1 //隔行扫描,在扫描窗口内进行两次背靠背扫描,要求扫描间隔必须大于等于扫描窗口的两倍

在标准扫描的情况下,如果相关器在页面扫描期间超过触发阈值,设备应进入第 8.3.3.1 节所述的外设响应子状态。扫描设备也可使用通用隔行扫描。在这种情况下,如果相关器在第一次扫描时未超过触发阈值,则应使用 [CLKN 16-12 + interlace_offset] mod 32 所确定的序列中的相位进行第二次扫描。如果在第二次扫描中相关器超过触发阈值,则设备应进入外设响应子状态,在 Xprp 的计算中使用 [CLKN 16-12 + interlace_offset] mod 32 作为冻结 CLKN*(详见第 2.6.4.3 节)。如果相关器在正常模式下的一次扫描或隔行扫描模式下的第二次扫描中未超过触发阈值,则应返回待机或连接状态。
隔行扫描偏移值范围为 0 至 31。除非不可扫描的插槽模式意味着应使用不同的值,否则应使用 16 值。

状态转化如下:
在这里插入图片描述

从上至下完整梳理使能蓝牙的流程如下:在这里插入图片描述

  • 20
    点赞
  • 19
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
### 回答1: Linux 系统中有几种常见的蓝牙协议栈: 1. BlueZ:这是 Linux 系统中默认的蓝牙协议栈,它由 Linux 基金会开发并维护。BlueZ 提供了蓝牙的高级功能,并且可以让用户通过命令行或脚本来控制蓝牙设备。 2. Bluedroid:这是 Android 系统中的蓝牙协议栈,也可以在其他基于 Linux 的系统中使用。Bluedroid 提供了丰富的蓝牙功能,包括蓝牙协议栈、配对、连接、传输数据等。 3. BlueZ for Android:这是一个基于 BlueZ 的蓝牙协议栈,专门为 Android 系统开发。它兼容 BlueZ 命令行工具,可以让用户在 Android 系统中使用 BlueZ 命令行来控制蓝牙设备。 4. hciattach:这是 Linux 中用于驱动蓝牙硬件的工具,它可以将蓝牙硬件附加到蓝牙协议栈中,使蓝牙硬件可以与其他蓝牙设备通信。 总的来说,Linux 系统中的蓝牙协议栈主要有 BlueZ 和 Bluedroid 两种,其中 BlueZ 是 Linux 系统中的默认蓝牙协议栈,Bluedroid 则是 Android 系统中的蓝牙协议栈。 ### 回答2: Linux操作系统中有两种蓝牙协议栈可供选择。 1. BlueZ协议栈:BlueZ是Linux操作系统上最常用的蓝牙协议栈。它提供API和工具,用于在Linux设备上实现蓝牙功能。BlueZ支持几乎所有的蓝牙协议,包括传统的蓝牙核心规范(Bluetooth Core Specification)和最新的蓝牙低功耗(Bluetooth Low Energy)规范。BlueZ协议栈被广泛应用于各种Linux设备,包括智能手机、平板电脑、智能手表等。 2. Affix协议栈:Affix是一个开源的Linux蓝牙协议栈。它提供了蓝牙通信的基本功能,并可以在嵌入式系统上运行。Affix协议栈支持蓝牙核心规范,但对于蓝牙低功耗规范的支持相对有限。它适用于资源受限的嵌入式设备,如物联网设备、传感器等。 总结起来,Linux操作系统上有两种常用的蓝牙协议栈:BlueZ协议栈和Affix协议栈。其中,BlueZ协议栈是最常用和功能最全面的蓝牙协议栈,被广泛应用于各种Linux设备。而Affix协议栈则适用于资源受限的嵌入式设备。 ### 回答3: Linux操作系统支持多种蓝牙协议栈,以下是其中一些常见的蓝牙协议栈: 1. BlueZ:BlueZ是Linux操作系统上最为广泛使用的开源蓝牙协议栈。它提供了一套完整的蓝牙协议栈实现,包括蓝牙核心协议、蓝牙硬件驱动和一系列用户空间的工具和库。BlueZ支持众多的蓝牙协议和功能,如蓝牙文件传输、蓝牙耳机、蓝牙键盘等。 2. Affix:Affix是一种轻量级的蓝牙协议栈,旨在提供更小的内存占用和更低的功耗。它适用于嵌入式设备和资源受限的系统。Affix支持核心蓝牙协议,但不支持所有BlueZ的高级功能。 3. Bluedroid:Bluedroid最初是由Android平台使用的蓝牙协议栈,后来也被移植到了Linux操作系统中。Bluedroid基于BlueZ协议栈,但做了一些定制化的修改和优化,以适应移动设备的需求。 4. FluorideFluoride是谷歌开发的蓝牙协议栈,最初用于Android平台,后来也支持了Linux操作系统。Fluoride提供了一套用于开发蓝牙应用的API和工具,并且与BlueZ相比有一些特有的优化和功能。 这些蓝牙协议栈都有各自的特点和适用场景,开发者可以根据不同的需求选择合适的协议栈来进行蓝牙应用程序的开发和调试。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值