目录
可收获
一、详细分析广播数据
1.1 图一
1.2 图二
1.3 详细分析广播数据
1.4 补充
二、学习示例代码
可收获
1.BLE广播的应用:蓝牙标签 2.使用nrf connect 查看广播信息,详解广播数据 3.讲解代码,了解 Assigned_Numbers 4.掌握使用 NimBLE 主机层协议栈构建Beacon
源自:IDF_5.2.6\v5.2.6\esp-idf\examples\bluetooth\ble_get_started\nimble\NimBLE_Beacon
蓝牙标签应用:室内定位、自动打卡、自动跳转网站
一、详细分析广播数据
1.1 图一
图一可以直观的看出很多信息,这些信息来源于广播数据,是根据广播数据整理后便于我们查看的
1.2 图二
点击RAW 会展示原始的广播数据,我们重点分析
1.3 详细分析广播数据
在前面04章节有提及过广播数据格式,如下:
| 序号 | 名称 | 字节数 | 备注 |
| 1 | 数据长度 (AD Length) | 1 | |
| 2 | 数据类型 (AD Type) | n | 大部分数据类型占用 1 字节 |
| 3 | 数据 (AD Data) | (AD Length - n) |
先说数据类型 (AD Type),就是一个值对应一个类型,所有蓝牙设备都遵循这个标准,比如0x01就代表Flags 在《Assigned_Numbers.pdf》 第12页 开始 列出了Common Data Types
| 字段 | 对应 AD Type | 说明 |
| Flags | 0x01 | 标志位,说明设备是 LE only、不支持经典蓝牙等 |
| Complete Local Name | 0x09 | 设备全名,就是 NimBLE_Beacon |
| Tx Power Level | 0x0A | 发射功率 |
| Appearance | 0x19 | 外观类别 |
| LE Role | 0x1C | 设备支持的角色,“Only Peripheral Role supported” |
| URL (https://espressif.com) | 0x24 | URI 数据 |
| 隐含在 Raw data 里 | 0x1B | Service Data,这里是 Eddystone 信标服务数据 |
那么数据又代表什么呢,比如原始数据中flags中的value为0x06是什么意思? 查找官方协议文档,几千页的文档怎么查?在我们不熟悉的情况下,用点“投机取巧”的办法 在第一张图flags:BR/EDR Not Supported, 在文档搜索 BR/EDR Not Supported,找到P2094:
《Core_v5.0》要我们去找Core Specification Supplement,ctrl+左键点击跳转到:https://www.bluetooth.com/specifications/specs/core-specification-6-2/ 没有找到?别慌,点击下图红框:
再搜索:
可能会有小伙伴有疑问,为啥bit位置1就代表有效呢? 结合下图,以及nrf中0x06代表的也是LE General Discoverable、BR/EDR Not Supported 文档中其他地方也有说明,这个问题就到这里了;
接下来看第二组:
Type 09 对应的数据 4E696D424C455F426561636F6E 为啥这个数据代表NimBLE_Beacon? 需要用ASCII解码,首先数据格式是十六进制的,0x4E对应的字符是 'N' ...
说完了第1、2组 广播数据结构,其他的也是类似的; 大家可以尝试按照上面的方法去查询蓝牙协议文档,带着目的去翻阅是一种熟悉文档很好的方式
1.4 补充
不知道小伙伴们有没有发现图一显示的数据,除了RAW data中的数据,还有3项是广播数据中没有的。
Device type: LE only 这是一个综合判断。nrf 看到设备标志位里有BR/EDR Not Supported,所以直接给出了“LE only”这个结论。
Advertising type: Legacy
这指的是广播包本身的协议类型,即“传统广播”。
这个信息是由芯片固件决定的,体现在链路层的广播包头部(Header),不在 AD payload 里面 LE Bluetooth Device Address:在04章节有讲过,是PDU有效负载的一部分(广播地址) 这个MAC地址在蓝牙协议里有个专门的称呼,叫 AdvA (Advertiser Address,即广播设备地址,
二、学习示例代码
在深入代码细节前,我们先对程序的行为有一个宏观的认识,这是一个很好的习惯! 2.1 第一步,我们会对程序中使用到的各个模块进行初始化,主要包括 NVS Flash、NimBLE 主机层协议栈以及 GAP 服务的初始化。
2.2 第二步,在 NimBLE 主机层协议栈与蓝牙控制器完成同步时,我们先确认蓝牙地址可用,然后发起 不定向、不可连接、可扫描的广播。之后持续处于广播状态,直到设备重启。
我们从入口函数 app_main()开始 app_main主要做以下几件事情:
初始化 NVS Flash 与 NimBLE 主机层协议栈
初始化 GAP 服务
启动 NimBLE 主机层的 FreeRTOS 线程,负责从底层控制器(Controller)接收 HCI 事件、处理 BLE 协议栈逻辑(如连接管理、GATT 事务、安全配对等)并分发到相应的回调函数
使用 NimBLE 主机层协议栈进行应用开发时的编程模型为事件驱动编程,例如:在 NimBLE 主机层协议栈与蓝牙控制器完成同步以后,将会触发同步完成事件,调用 ble_hs_cfg.sync_cb 函数。在回调函数设定时,我们令该函数指针指向 on_stack_sync 函数,所以这是同步完成时实际被调用的函数。 // 注意,暂时不要关注如何触发事件的,只需要知道蓝牙底层完成某个事情后会触发一个事件给我们使用
注意:Bluetooth LE 的空中数据包遵循小端 (Little Endian) 传输的顺序,所以低字节的数据会在靠前的位置。
static void start_advertising(void)
准备数据:调用 ble_gap_adv_set_fields 和 ble_gap_adv_rsp_set_fields 配置内容。
配置行为:配置 adv_params(如不可连接、通用发现模式)。
启动广播:调用 ble_gap_adv_start,此时手机才能搜索到这个设备。