当前位置: 首页 > news >正文

BLE Legacy 广播【广播使能】

在 BLE Legacy 广播流程中,前面几个 HCI Command 主要负责“配置”:

HCI_LE_Set_Advertising_Parameters HCI_LE_Set_Advertising_Data HCI_LE_Set_Scan_Response_Data

但是这些命令只是把广播参数、广播数据、扫描响应数据配置到 Controller 中,并不会真正让 Controller 开始发送广播包。

真正用于“开始广播”或“停止广播”的命令是:

HCI_LE_Set_Advertising_Enable

也就是本文要讲的:

7.8.9 LE Set Advertising Enable command

这个命令可以理解为 BLE Legacy 广播流程中的“启动 / 停止开关”。


一、命令概览

官方文档中该命令的信息如下:

Command: HCI_LE_Set_Advertising_Enable OCF: 0x000A Command Parameters: Advertising_Enable Return Parameters: Status

需要注意,文档中还有一句说明:

This command was formerly called “LE Set Advertise Enable”.

翻译:

该命令以前被称为 “LE Set Advertise Enable”。

也就是说,在一些旧资料、旧代码或厂商文档中,你可能会看到:

LE Set Advertise Enable

它和现在的:

LE Set Advertising Enable

指的是同一个命令。


二、Description 翻译

官方描述第一段:

This command is used to request the Controller to start or stop advertising. The Controller manages the timing of advertisements as per the advertising parameters given in the HCI_LE_Set_Advertising_Parameters command.

翻译:

该命令用于请求 Controller 开始或停止广播。Controller 会根据 HCI_LE_Set_Advertising_Parameters command 中给定的广播参数来管理广播的时序。

这句话非常关键。

它说明:

HCI_LE_Set_Advertising_Enable 只负责请求 Controller 开始或停止广播。

而广播怎么发,比如:

广播间隔是多少 广播类型是什么 使用什么地址类型 在哪些广播信道上发 广播过滤策略是什么

这些不是由本命令决定的,而是由前面的:

HCI_LE_Set_Advertising_Parameters

决定。

所以可以这样理解:

HCI_LE_Set_Advertising_Parameters 负责告诉 Controller:广播应该怎么发。 HCI_LE_Set_Advertising_Enable 负责告诉 Controller:现在开始发,或者停止发。

官方描述第二段:

The Controller shall continue advertising until the Host issues an HCI_LE_Set_Advertising_Enable command with Advertising_Enable set to 0x00 (Advertising is disabled), a connection is created using the advertising, or the Advertising is timed out due to high duty cycle Directed Advertising. In these cases, advertising is then disabled.

翻译:

Controller 会持续进行广播,直到 Host 发送 HCI_LE_Set_Advertising_Enable command 并将 Advertising_Enable 设置为 0x00,也就是禁用广播;或者通过该广播建立了连接;或者由于高占空比定向广播超时。在这些情况下,广播随后会被禁用。

这段说明了广播会在几种情况下停止:

1. Host 主动关闭广播 2. 通过该广播建立了连接 3. 高占空比定向广播超时

对于普通 Legacy 广播来说,我们最常见的是第一种:

Host 发送 Advertising_Enable = 0x00

主动关闭广播。

如果广播类型是可连接广播,比如:

ADV_IND ADV_DIRECT_IND

当连接建立成功后,Controller 也会停止广播。


官方描述第三段:

Enabling advertising when it is already enabled can cause the random address to change. Disabling advertising when it is already disabled has no effect.

翻译:

当广播已经使能时再次使能广播,可能会导致随机地址发生变化。当广播已经禁用时再次禁用广播,不会产生影响。

这里有两个点。

第一:

广播已经开启时,再次执行 Enable,可能导致随机地址变化。

这个和地址类型有关,尤其是使用随机地址、可解析私有地址等场景时需要注意。

第二:

广播已经关闭时,再次执行 Disable,没有效果。

也就是说,重复关闭广播通常是安全的,不会产生额外行为。


三、Command Parameters 翻译

该命令只有一个参数:

Advertising_Enable

大小:

1 octet

取值如下:

ValueParameter Description
0x00Advertising is disabled,禁用广播,默认值
0x01Advertising is enabled,使能广播
All other valuesReserved for future use,保留,供将来使用

也就是说:

Advertising_Enable = 0x00

表示关闭广播。

Advertising_Enable = 0x01

表示开启广播。

其他值不能使用。


四、Return Parameters 翻译

该命令返回一个参数:

Status

大小:

1 octet

取值如下:

ValueParameter Description
0x00HCI_LE_Set_Advertising_Enable command 执行成功
0x01 to 0xFFHCI_LE_Set_Advertising_Enable command 执行失败,具体错误码见 Controller Error Codes

也就是说:

Status = 0x00

表示命令执行成功。

如果返回:

Status = 0x01 ~ 0xFF

表示命令失败,需要结合具体错误码分析。


五、Event(s) generated 翻译

官方文档中提到:

When the HCI_LE_Set_Advertising_Enable command has completed, an HCI_Command_Complete event shall be generated.

翻译:

当 HCI_LE_Set_Advertising_Enable command 完成后,应当生成一个 HCI_Command_Complete event。

也就是说,这个命令执行完成后,Controller 会通过:

HCI_Command_Complete event

告诉 Host 命令完成,并返回 Status。

注意,它不是通过 LE Advertising Report event 返回结果。

LE Advertising Report event 是扫描端收到广播后上报扫描结果用的,不是广播端配置命令的返回事件。


六、特殊情况:高占空比定向广播超时

官方文档还提到:

If the Advertising_Type parameter is 0x01 (ADV_DIRECT_IND, high duty cycle) and the directed advertising fails to create a connection, an HCI_LE_Connection_Complete or HCI_LE_Enhanced_Connection_Complete event shall be generated with the Status code set to Advertising Timeout (0x3C).

翻译:

如果 Advertising_Type 参数是 0x01,也就是高占空比定向广播 ADV_DIRECT_IND,并且该定向广播未能建立连接,则会生成 HCI_LE_Connection_Complete 或 HCI_LE_Enhanced_Connection_Complete event,并且 Status code 设置为 Advertising Timeout,错误码为 0x3C。

这里要理解的是:

高占空比定向广播不是一直无限广播。

它是为了快速连接某个指定设备而设计的广播类型。

如果在规定时间内没有建立连接,就会超时,然后广播停止,并产生连接完成相关事件,只是这个事件的状态是:

Advertising Timeout 0x3C

七、连接建立后广播会停止

官方文档还提到:

If the Advertising_Type parameter is 0x00 (ADV_IND), 0x01 (ADV_DIRECT_IND, high duty cycle), or 0x04 (ADV_DIRECT_IND, low duty cycle) and a connection is created, an HCI_LE_Connection_Complete or HCI_LE_Enhanced_Connection_Complete event shall be generated.

翻译:

如果 Advertising_Type 参数是 0x00,也就是 ADV_IND;或者 0x01,也就是高占空比定向广播 ADV_DIRECT_IND;或者 0x04,也就是低占空比定向广播 ADV_DIRECT_IND,并且连接被建立,则会生成 HCI_LE_Connection_Complete 或 HCI_LE_Enhanced_Connection_Complete event。

这说明:

对于可连接广播,如果连接建立成功,Controller 会产生连接完成事件。

常见可连接广播包括:

ADV_IND ADV_DIRECT_IND

连接建立后,广播会停止。

这也很好理解:设备已经进入连接状态,就不再继续以同一个广播实例对外广播。


八、Race Condition:竞态条件

官方文档最后有一个 Note:

There is a possible race condition if the Advertising_Enable parameter is set to 0x00 (Disable) and the Advertising_Type parameter is 0x00, 0x01, or 0x04. The advertisements might not be stopped before a connection is created, and therefore both the HCI_Command_Complete event and either an HCI_LE_Connection_Complete event or an HCI_LE_Enhanced_Connection_Complete event could be generated.

翻译:

如果 Advertising_Enable 参数设置为 0x00,也就是禁用广播,并且 Advertising_Type 参数是 0x00、0x01 或 0x04,则可能存在竞态条件。广播可能还没来得及停止,连接就已经建立了。因此,可能同时产生 HCI_Command_Complete event,以及 HCI_LE_Connection_Complete event 或 HCI_LE_Enhanced_Connection_Complete event。

这个点非常重要。

意思是:

Host 正准备关闭广播。 但是关闭广播命令还没完全生效时,某个中心设备已经发起连接并成功建立了连接。

于是 Controller 可能既上报:

HCI_Command_Complete

又上报:

HCI_LE_Connection_Complete

或者:

HCI_LE_Enhanced_Connection_Complete

这就是竞态条件。

在 App 或 Host 协议栈中,如果看到“关闭广播”和“连接建立”几乎同时发生,不要误以为一定是异常,也可能是规范允许的竞态行为。


九、Error 情况翻译与解释

官方文档列出了一些可能返回:

Invalid HCI Command Parameters 0x12

的情况。

这些错误主要和:

Own_Address_Type Random Address Resolving List Public Address

有关。

也就是说,广播使能失败,很多时候不是 Advertising_Enable 这个参数本身的问题,而是前面配置的地址类型不满足条件。


1. Own_Address_Type = 0x00,但设备没有 Public Address

错误条件:

Advertising_Enable is set to 0x01, the advertising parameters' Own_Address_Type parameter is set to 0x00, and the device does not have a public address.

翻译:

Advertising_Enable 设置为 0x01,也就是使能广播; 广播参数中的 Own_Address_Type 设置为 0x00; 但是设备没有 Public Address。

错误码:

Invalid HCI Command Parameters 0x12

解释:

Own_Address_Type = 0x00表示使用 Public Device Address。

但是如果设备本身没有公共地址,那么 Controller 就无法用 Public Address 去发广播。

所以开启广播会失败。


2. Own_Address_Type = 0x01,但 Random Address 没有初始化

错误条件:

Advertising_Enable is set to 0x01, the advertising parameters' Own_Address_Type parameter is set to 0x01, and the random address for the device has not been initialized using the HCI_LE_Set_Random_Address command.

翻译:

Advertising_Enable 设置为 0x01; 广播参数中的 Own_Address_Type 设置为 0x01; 但是设备的随机地址还没有通过 HCI_LE_Set_Random_Address command 初始化。

错误码:

Invalid HCI Command Parameters 0x12

解释:

Own_Address_Type = 0x01表示使用 Random Device Address。

但是在使用随机地址之前,需要先通过:

HCI_LE_Set_Random_Address

设置随机地址。

如果没有设置,就直接开启广播,Controller 不知道该用哪个随机地址发广播,因此会返回参数错误。


3. Own_Address_Type = 0x02,但解析列表没有匹配项,且设备没有 Public Address

错误条件:

Advertising_Enable is set to 0x01, the advertising parameters' Own_Address_Type parameter is set to 0x02, the Controller's resolving list does not contain a matching entry, and the device does not have a public address.

翻译:

Advertising_Enable 设置为 0x01; 广播参数中的 Own_Address_Type 设置为 0x02; Controller 的 resolving list 中没有匹配项; 并且设备没有 Public Address。

错误码:

Invalid HCI Command Parameters 0x12

解释:

Own_Address_Type = 0x02一般和可解析私有地址,也就是 Resolvable Private Address,相关。

如果解析列表里没有匹配项,并且设备又没有 Public Address 可以作为备用,那么 Controller 就无法确定应该使用什么地址进行广播。

因此开启广播失败。


4. Own_Address_Type = 0x03,但解析列表没有匹配项,且 Random Address 没有初始化

错误条件:

Advertising_Enable is set to 0x01, the advertising parameters' Own_Address_Type parameter is set to 0x03, the Controller's resolving list does not contain a matching entry, and the random address for the device has not been initialized using the HCI_LE_Set_Random_Address command.

翻译:

Advertising_Enable 设置为 0x01; 广播参数中的 Own_Address_Type 设置为 0x03; Controller 的 resolving list 中没有匹配项; 并且设备的随机地址还没有通过 HCI_LE_Set_Random_Address command 初始化。

错误码:

Invalid HCI Command Parameters 0x12

解释:

这也是地址配置相关的问题。

如果使用的地址类型依赖 resolving list,但 resolving list 中没有匹配项,同时随机地址又没有初始化,那么 Controller 无法确定广播时使用的地址,所以开启广播失败。


十、R 和 MC 是什么意思?

错误表中 Type 一栏出现了:

R MC

可以这样理解:

R = Remote MC = Module / Controller,也可以理解为本地 Controller 侧条件

在这里,我们不需要过度纠结这个 Type 字段,重点是看 Condition。

这些错误的核心原因都是:

开启广播时,Own_Address_Type 对应的地址条件没有满足。

所以如果执行:

HCI_LE_Set_Advertising_Enable

返回:

Invalid HCI Command Parameters 0x12

就应该优先检查:

Own_Address_Type 配置是否正确 是否有 Public Address 是否已经设置 Random Address Resolving List 是否有匹配项

十一、广播使能命令在 Legacy 广播流程中的位置

完整的 BLE Legacy 广播配置流程通常是:

1. HCI_LE_Set_Advertising_Parameters 配置广播参数 2. HCI_LE_Set_Advertising_Data 配置广播数据 3. HCI_LE_Set_Scan_Response_Data 配置扫描响应数据 4. HCI_LE_Set_Advertising_Enable 开启广播

如果使用 Random Address,可能还需要在前面加上:

HCI_LE_Set_Random_Address

也就是:

1. HCI_LE_Set_Random_Address 设置随机地址 2. HCI_LE_Set_Advertising_Parameters 配置广播参数 3. HCI_LE_Set_Advertising_Data 配置广播数据 4. HCI_LE_Set_Scan_Response_Data 配置扫描响应数据 5. HCI_LE_Set_Advertising_Enable 开启广播

所以HCI_LE_Set_Advertising_Enable是广播配置链路中的最后一步。

前面命令只是配置,只有这个命令执行成功后,Controller 才真正开始在空口上发送 Legacy 广播包。


十二、开启广播后,Controller 做了什么?

当 Host 发送:

HCI_LE_Set_Advertising_Enable Advertising_Enable = 0x01

并且命令执行成功后,Controller 会根据之前配置的参数开始广播。

这些参数主要来自:

HCI_LE_Set_Advertising_Parameters

包括:

Advertising_Interval_Min Advertising_Interval_Max Advertising_Type Own_Address_Type Peer_Address_Type Peer_Address Advertising_Channel_Map Advertising_Filter_Policy

然后 Controller 会按照广播事件时序,在指定的 advertising channels 上发送广播 PDU。

例如:

Channel 37 Channel 38 Channel 39

如果广播类型是:

ADV_IND

那么 Controller 会发送可连接、可扫描的非定向广播。

如果扫描方是主动扫描,并且过滤策略允许,扫描方可以发送:

SCAN_REQ

广播方收到后可以回复:

SCAN_RSP

如果中心设备发起连接,并且广播类型允许连接,则可能进入连接建立流程。


十三、关闭广播后,Controller 做了什么?

当 Host 发送:

HCI_LE_Set_Advertising_Enable Advertising_Enable = 0x00

并且命令执行成功后,Controller 会停止广播。

这意味着 Controller 不再继续发送 Legacy advertising PDU。

但要注意,关闭广播不等于清空广播参数。

也就是说,之前通过下面这些命令设置的参数和数据:

HCI_LE_Set_Advertising_Parameters HCI_LE_Set_Advertising_Data HCI_LE_Set_Scan_Response_Data

不一定会因为关闭广播而全部消失。

通常可以理解为:

Disable advertising 是停止当前广播行为; 不是清空所有广播配置。

如果后续再次 Enable,Controller 可能继续使用已有配置重新开始广播。

当然,具体细节也可能受 Controller 实现或厂商模块封装影响。


十四、为什么修改广播参数前通常要先关闭广播?

实际开发中,如果要修改广播参数、广播数据或扫描响应数据,通常建议先关闭广播,再修改配置,然后重新开启广播。

也就是:

1. Disable Advertising 2. Set Advertising Parameters 3. Set Advertising Data 4. Set Scan Response Data 5. Enable Advertising

这样做比较稳妥。

因为很多参数在广播已经开启时可能不允许修改,或者修改行为存在限制。

例如你想修改:

Advertising_Type Own_Address_Type Advertising_Channel_Map Advertising_Data Scan_Response_Data

最好先停止广播。

否则可能会遇到:

Command Disallowed Invalid HCI Command Parameters

或者某些厂商 Controller 行为不一致的问题。

所以从实践角度看:

配置前先关闭,配置后再开启

是更稳妥的流程。


十五、它和 App 端“开始广播”的关系

如果你在 Android 或 iOS 上调用系统 API 开启 BLE 广播,App 层通常不会直接接触 HCI Command。

例如 Android 里可能调用:

BluetoothLeAdvertiser.startAdvertising()

或者:

BluetoothLeAdvertiser.startAdvertisingSet()

iOS 里可能调用:

CBPeripheralManager.startAdvertising()

但在系统蓝牙协议栈内部,最终会转换为 Controller 能理解的 HCI 命令。

对于 Legacy 广播场景,核心思想仍然类似:

配置广播参数 配置广播数据 开启广播

其中开启广播这个动作,在 HCI 层就对应:

HCI_LE_Set_Advertising_Enable

当然,实际手机系统可能做了很多封装、权限检查、参数适配和兼容处理,App 开发者通常看不到这些 HCI 命令。


十六、必要 Tip 总结

Tip 1:它是 Legacy 广播的启动 / 停止开关

HCI_LE_Set_Advertising_Enable

最核心作用就是:

开始广播 停止广播

它不负责配置广播内容,也不负责配置广播类型。


Tip 2:广播怎么发,由 Set Advertising Parameters 决定

广播使能命令只是开关。

广播的具体行为由:

HCI_LE_Set_Advertising_Parameters

决定。

例如:

广播间隔 广播类型 地址类型 信道 Map 过滤策略

都不是本命令配置的。


Tip 3:Advertising_Enable 只有两个有效值

0x00 = Disable advertising 0x01 = Enable advertising

其他值都是保留值,不应该使用。


Tip 4:开启广播前要确保地址条件满足

如果使用 Public Address,设备必须有 Public Address。

如果使用 Random Address,必须先执行:

HCI_LE_Set_Random_Address

如果使用和隐私相关的地址类型,还要考虑 resolving list 是否存在匹配项。

否则开启广播时可能返回:

Invalid HCI Command Parameters 0x12

Tip 5:广播已经开启时再次开启,可能导致随机地址变化

规范中明确说:

Enabling advertising when it is already enabled can cause the random address to change.

所以不要随便重复 Enable。

如果确实要重新配置广播,建议流程是:

Disable Configure Enable

Tip 6:广播已经关闭时再次关闭,没有影响

规范中也说明:

Disabling advertising when it is already disabled has no effect.

所以重复 Disable 一般不会产生额外影响。


Tip 7:连接建立后,广播会停止

对于可连接广播,如果通过该广播建立了连接,Controller 会停止广播,并上报连接完成事件:

HCI_LE_Connection_Complete

或者:

HCI_LE_Enhanced_Connection_Complete

Tip 8:Disable 和连接建立可能发生竞态

如果 Host 正在关闭广播,但连接刚好在关闭前建立成功,那么可能同时看到:

HCI_Command_Complete

和:

HCI_LE_Connection_Complete

这不一定是异常,而是规范允许的竞态情况。


十七、一句话总结

HCI_LE_Set_Advertising_Enable 是 BLE Legacy 广播中的启动 / 停止开关。

它通过:

Advertising_Enable = 0x01

请求 Controller 开始广播。

通过:

Advertising_Enable = 0x00

请求 Controller 停止广播。

但是广播的具体参数和数据不是由它决定的,而是由前面的:

HCI_LE_Set_Advertising_Parameters HCI_LE_Set_Advertising_Data HCI_LE_Set_Scan_Response_Data

决定。

所以在 BLE Legacy 广播流程中,可以这样理解:

Set Advertising Parameters:配置广播怎么发 Set Advertising Data:配置广播包里放什么 Set Scan Response Data:配置扫描响应包里放什么 Set Advertising Enable:真正开始或停止广播

http://www.jsqmd.com/news/1078860/

相关文章:

  • Aeroblade空气动力学设计:从原理到工程实践
  • 代码质量工具静态分析与动态检测
  • 文件包含漏洞之原理、探测、利用、绕过、防御
  • VMware虚拟机导出OVF:绕过ovftool命令行的3种GUI替代方案,小白也能10分钟完成合规打包
  • Spring Cloud 服务注册与发现原理
  • 嵌入式无线通信自动化测试与协议分析实战指南
  • GEO服务商与SEO服务商有什么区别?2026年企业必须搞清的五个关键差异
  • Gemma 4多模态轻量模型实战指南:边缘部署与跨语言推理
  • 多维空间索引结构R树与KD树性能对比研究的技术8
  • 太吾绘卷:天幕心帷下载2026最新带破解
  • 数字取证实战:从系统日志到内存分析,还原安全事件真相
  • 如何快速掌握LangFlow:3步搞定AI应用可视化开发
  • MoE模型推理优化:动态调度与缓存管理实践
  • Gemini 3.1 Pro三层推理与Veo+Lyria多模态协同实战指南
  • CLIP实战避坑指南:图文对齐、零样本迁移与生产部署关键断点
  • 3分钟开启记忆守护:微信聊天记录永久保存的智能方案
  • 智码 AICoder · 桌面桌宠(Desktop Pet)功能完全介绍
  • Product Hunt 每日热榜 | 2026-06-25
  • Streamlit+Heroku部署GAN模型:零运维Web应用实战
  • 机器学习模型评估实战:从accuracy陷阱到AUC-ROC与PR曲线深度解析
  • 3个核心技术突破:Windows系统下LG Ultrafine显示器亮度控制终极方案
  • SpringSecurity 静态资源放行深度详解(解决401认证失败、文件无法访问、URL拦截问题)
  • 分布式算力容器与连续张量拓扑:基于 Gunicorn 多进程套接字复用与 NumPy 共享内存的 IPC 通信架构
  • 从脱靶量最小化到杀伤概率最大化:导弹制导新范式解析
  • MWC26上海 | 移远首款MediaTek平台旗舰级AI算力模组震撼登场
  • 如何在10分钟内搭建AI驱动的无代码测试平台:Testsigma完整实战指南
  • 文本转换(Transforming)
  • 存个对象到localStorage,结果[object Object]?
  • 【C++面经】1-5
  • 服务定位器中的依赖查找与实例管理