BLE Legacy 广播【扫描使能】

📅 2026/6/25 21:53:23
BLE Legacy 广播【扫描使能】
Description 翻译原文This command is used to start and stop scanning for legacy PDUs (but not extended PDUs, even if the device supports extended advertising). Scanning is used to discover advertising devices nearby.翻译这个命令用于启动和停止对Legacy PDU的扫描。注意它不用于扫描Extended PDU即使设备支持 Extended Advertising也不是通过这个命令来扫描 Extended Advertising。扫描用于发现附近正在发送广播的设备。也就是说LE Set Scan Enable只负责 Legacy Scanning 的开启和关闭。如果是 Bluetooth 5 之后的 Extended Scanning要看LE Set Extended Scan Enable原文The Filter_Duplicates parameter controls whether the Link Layer should filter out duplicate advertising reports (Filtering_Enabled) to the Host, or if the Link Layer should generate advertising reports for each packet received (Filtering_Disabled).翻译Filter_Duplicates参数用于控制 Link Layer 是否要向 Host 过滤重复的广播报告。如果启用重复过滤Filtering_Enabled那么 Link Layer 会过滤掉重复的 advertising report不会每次收到重复广播包都上报给 Host。如果关闭重复过滤Filtering_Disabled那么 Link Layer 会对每一个收到的广播包都生成 advertising report并上报给 Host。也就是Filter_Duplicates 0x00 不去重每收到一个广播包都可能上报 Filter_Duplicates 0x01 去重相同设备/相同广播报告可能只上报一次原文If LE_Scan_Enable is set to 0x00 then Filter_Duplicates shall be ignored.翻译如果LE_Scan_Enable被设置为0x00那么Filter_Duplicates应被忽略。也就是说当你关闭扫描时LE_Scan_Enable 0x00此时Filter_Duplicates填什么都不重要因为扫描都关闭了谈不上是否过滤重复报告。原文If the LE_Scan_Enable parameter is set to 0x01 and scanning is already enabled, any change to the Filter_Duplicates setting shall take effect.翻译如果LE_Scan_Enable被设置为0x01并且扫描已经处于启用状态那么对Filter_Duplicates的任何修改都应生效。这个点很重要。意思是扫描已经开启时虽然你不能随便改扫描参数比如LE_Scan_Type、LE_Scan_Interval、LE_Scan_Window但是你可以再次发送LE Set Scan Enable然后只改变Filter_Duplicates的设置。例如当前已经在扫描 LE_Scan_Enable 0x01 Filter_Duplicates 0x01 再次发送 LE_Scan_Enable 0x01 Filter_Duplicates 0x00这样可以在扫描过程中关闭重复过滤。原文Disabling scanning when it is disabled has no effect.翻译当扫描已经处于关闭状态时再次关闭扫描不会产生任何影响。也就是当前已经关闭扫描 再次发送 LE_Scan_Enable 0x00不会报错也不会产生额外影响可以理解为无操作。Errors 翻译原文See Section 4.5.2 for a list of error types and descriptions.翻译错误类型和描述列表请参考 4.5.2 节。错误表格翻译TypeConditionError codeRLE_Scan_Enable设置为0x01扫描参数里的Own_Address_Type设置为0x00或0x02但是设备没有 Public AddressInvalid HCI Command Parameters0x12MCLE_Scan_Enable设置为0x01扫描参数里的Own_Address_Type设置为0x01或0x03但是设备的 Random Address 还没有通过HCI_LE_Set_Random_Address命令初始化Invalid HCI Command Parameters0x12这两个错误都发生在LE_Scan_Enable 0x01也就是准备开启扫描的时候。第一种错误Own_Address_Type 0x00 或 0x02这两个模式可能需要使用 Public Address。但是设备没有 Public Address于是开启扫描失败。第二种错误Own_Address_Type 0x01 或 0x03这两个模式可能需要使用 Random Address。但是你还没有先调用HCI_LE_Set_Random_Address初始化随机地址于是开启扫描失败。LE_Scan_EnableValueParameter Description0x00关闭扫描0x01开启扫描All other values保留供将来使用也就是说LE_Scan_Enable 0x00 Stop Scanning LE_Scan_Enable 0x01 Start ScanningFilter_DuplicatesValueParameter Description0x00关闭重复过滤0x01开启重复过滤All other values保留供将来使用也就是说Filter_Duplicates 0x00 每次收到广播包都可能上报 Filter_Duplicates 0x01 过滤重复广播报告Return parametersValueParameter Description0x00HCI_LE_Set_Scan_Enable命令执行成功0x01 to 0xFFHCI_LE_Set_Scan_Enable命令执行失败。错误码和描述请参考[Vol 1] Part F, Controller Error Codes也就是说Status 0x00 开启/关闭扫描成功 Status ! 0x00 开启/关闭扫描失败Event(s) generated原文When the HCI_LE_Set_Scan_Enable command has completed, an HCI_Command_Complete event shall be generated.翻译当HCI_LE_Set_Scan_Enable命令完成后应生成一个HCI_Command_Complete Event也就是说这个命令完成后Controller 会通过 Command Complete Event 告诉 Host 命令执行结果。流程是Host → Controller: HCI_LE_Set_Scan_Enable Controller → Host: HCI_Command_Complete Event └── Status原文Zero or more HCI_LE_Advertising_Report events are generated by the Controller based on legacy advertising packets received and the duplicate filtering. More than one advertising packet may be reported in each HCI_LE_Advertising_Report event. No report shall be issued for extended advertising PDUs.翻译Controller 会根据收到的 Legacy Advertising Packet以及重复过滤设置生成零个或多个HCI_LE_Advertising_Report Event每个HCI_LE_Advertising_Report Event中可以报告多个 advertising packet。不会为 Extended Advertising PDU 生成报告。也就是说开启扫描成功后不一定马上有扫描结果。可能是0 个 Advertising Report 1 个 Advertising Report 多个 Advertising Report而且一个HCI_LE_Advertising_Report Event里面可能包含多个设备或多个广播报告。但是这个命令只对应 Legacy Advertising Report不对应 Extended Advertising。原文When the Scanning_Filter_Policy is set to 0x02 or 0x03 and a directed advertisement was received where the advertiser used a resolvable private address which the Controller is unable to resolve, an HCI_LE_Directed_Advertising_Report event shall be generated instead of an HCI_LE_Advertising_Report event.翻译当Scanning_Filter_Policy设置为0x02或0x03时如果收到一个 directed advertisement并且广播设备使用了 Controller 无法解析的 Resolvable Private Address那么 Controller 应生成HCI_LE_Directed_Advertising_Report Event而不是HCI_LE_Advertising_Report Event简单理解如果涉及定向广播、隐私地址、地址解析失败就可能不会走普通的 Advertising Report而是走 Directed Advertising Report。这部分可以先知道有这个特殊分支后面结合 Privacy、Resolving List、Directed Advertising 再深入。Tip 1LE Set Scan Parameters 是“配置”LE Set Scan Enable 是“开关”这两个命令要配合看。LE Set Scan Parameters 配置怎么扫描 LE Set Scan Enable 控制开始扫描 / 停止扫描典型流程HCI_LE_Set_Scan_Parameters ↓ HCI_LE_Set_Scan_Enable 0x01 ↓ Controller 开始扫描 Legacy Advertising PDU ↓ Controller 上报 HCI_LE_Advertising_Report Event ↓ HCI_LE_Set_Scan_Enable 0x00Tip 2这个命令只扫描 Legacy PDU不扫描 Extended PDU截图原文说得很明确legacy PDUs, but not extended PDUs所以HCI_LE_Set_Scan_Enable对应的是 Legacy Scanning。如果你想扫描 Bluetooth 5 Extended Advertising要用HCI_LE_Set_Extended_Scan_Parameters HCI_LE_Set_Extended_Scan_Enable不要把 Legacy Scan Enable 和 Extended Scan Enable 混在一起。Tip 3Filter_Duplicates 影响的是 Controller 上报给 Host 的次数Filter_Duplicates不是让空口上的广播包消失。广播设备仍然在发广播。这个参数影响的是Controller 收到广播包后要不要把重复的 advertising report 上报给 Host也就是说Filter_Duplicates 0x00 Controller 可能频繁上报同一个设备的广播 Filter_Duplicates 0x01 Controller 会过滤重复报告Host 看到的上报会少很多所以做扫描工具类 App 时如果你想实时刷新 RSSI通常不能只依赖去重后的报告。因为去重之后同一个设备可能不会频繁上报RSSI 更新就会不及时。Tip 4Filter_Duplicates 0x01 时不代表永远只上报一次很多人容易误解为Filter_Duplicates 0x01 同一个设备永远只上报一次这个理解不严谨。更准确地说它是 Controller 的重复 advertising report 过滤策略。实际什么时候认为是重复、什么时候重新上报会和 Controller 实现、扫描周期、广播数据变化、地址类型、过滤状态等有关。所以从 App 表现看可能是同一个设备上报次数明显减少但不要简单理解成“绝对只上报一次”。Tip 5关闭扫描时Filter_Duplicates 会被忽略如果LE_Scan_Enable 0x00那么Filter_Duplicates无论填0x00还是0x01都会被忽略。因为此时是在关闭扫描不涉及后续扫描报告的去重。Tip 6扫描已经开启时可以改变 Filter_Duplicates这一点很细但很重要。规范说如果 LE_Scan_Enable 0x01并且 scanning is already enabled Filter_Duplicates 的变化应生效。也就是说扫描已经开着时你可以再次发送HCI_LE_Set_Scan_Enable来切换重复过滤策略。例如// 已经开启扫描并且开启去重 LE_Scan_Enable 0x01 Filter_Duplicates 0x01 // 不停止扫描直接改成关闭去重 LE_Scan_Enable 0x01 Filter_Duplicates 0x00这种情况下新的Filter_Duplicates设置应该生效。Tip 7如果 Own_Address_Type 选 Random Address要先 Set Random Address如果之前在LE Set Scan Parameters里面配置了Own_Address_Type 0x01或者Own_Address_Type 0x03那么开启扫描前通常要先调用HCI_LE_Set_Random_Address否则开启扫描时可能失败Invalid HCI Command Parameters0x12这就是截图里第二条错误。正确顺序类似HCI_LE_Set_Random_Address ↓ HCI_LE_Set_Scan_Parameters ↓ HCI_LE_Set_Scan_Enable 0x01如果使用 Public AddressOwn_Address_Type 0x00一般不需要设置 Random Address。Tip 8Advertising Report 是扫描结果不是 Command 返回值LE Set Scan Enable的命令返回结果是HCI_Command_Complete Event └── Status这只能说明扫描开关命令是否执行成功真正的扫描结果是后续异步上报的HCI_LE_Advertising_Report Event所以不要把这两个混淆。完整理解应该是Command Complete Event 告诉你“扫描开关命令成功没有” LE Advertising Report Event 告诉你“扫到了哪些广播设备”Tip 9开启扫描后可能没有任何 Advertising Report规范写的是Zero or more HCI_LE_Advertising_Report events也就是“零个或多个”。所以即使命令返回成功也不代表一定能马上扫到设备。原因可能包括附近没有广播设备 扫描窗口没覆盖到广播包 广播包碰撞 过滤策略过滤掉了设备 开启了重复过滤 设备使用 Extended Advertising而当前命令只扫 Legacy PDU Controller / Host 事件 mask 配置影响Tip 10一个 Advertising Report Event 里可以包含多个报告规范说More than one advertising packet may be reported in each HCI_LE_Advertising_Report event.也就是说一个 HCI Event 里面可能带多个 advertising report。所以解析时不能假设一个 HCI_LE_Advertising_Report Event 一个设备更准确应该是一个 HCI_LE_Advertising_Report Event └── Num_Reports ├── Report 1 ├── Report 2 └── Report N这对后面解析LE Advertising Report Event很重要。