蓝牙学习十(扫描)
一、简介
从之前的文章中我们知道,蓝牙GAP层定义了四种角色,广播者(Broadcaster)、观察者(Observer)、外围设备(Peripheral)、中央设备(Central)。

之前的学习一直都是 外围设备(Peripheral)。这篇文章,介绍下中央设备(Central)。
外围设备主要是通过广播向外发送数据,而中央设备如何发现外围设备,就需要通过扫描了。
扫描是一个在一定范围内用来寻址其他低功耗蓝牙设备广播的过程。扫描者设备在扫描过程中会使用广播信道。与广播过程不同的是,扫描过程中没有严格的时间定义和信道规则。
扫描分为主动扫描和被动扫描。
不管是主动还是被动扫描,扫描的基本流程为:设置扫描参数 -> 使能扫描 -> Controller上报扫描结果 -> 停止扫描。
二、主动扫描
主动扫描不单单可以捕获到对端设备的广播数据包,还可以捕获扫描响应数据包。
设备不断发送广播信号给主机(Observer),如果主机不开启扫描窗口,是收不到设备的广播的。主机不仅要开启射频接收窗口,而且还要主机的射频接收窗口跟广播发送的发射窗口匹配成功,主机才能收到设备的广播信号。由于这种匹配成功是一个概率事件,所以主机扫描到设备也是一个概率事件。也就是说,主机有时会很快扫描到设备,比如只需要一个广播事件。主机有时也会很慢才能扫到设备,比如需要10个广播事件甚至更多。
下图为主机主动扫描广播的过程:

控制器收到扫描数据包后,将向应用层发送一个广播报告事件(adv_report),该事件同样包括了链路层数据包的广播类型。因此,主机能够判断对端设备是否可以连接或扫描。并区分出广播数据包和扫描响应数据包。
扫描是集中器监听广播数据包和发送扫描请求的过程,它有2个定时参数需要特别注意:扫描窗口和扫描间隔。
对于每一个扫描间隔,集中器扫描的时间等于一个扫描窗口,这就意味着如果扫描窗口等于扫描间隔,那么集中器将处于连续扫描之中。
如果集中器想建立一个连接。当扫描监听到广播数据包后,将会发送连接请求。
主动扫描流程图大致如下:
2.1 、扫描参数
Host 设置BLE扫描所必须得参数到Controller。这样Controller才知晓扫描上报哪类低功耗设备信息。

LE_Scan_Type:扫描类型,主动扫描还是被动扫描。
LE_Scan_Interval:扫描间隔,控制器多久扫描一次。也就是两个连续扫描的间隔。
LE_Scan_Window:扫描窗口。每次扫描所持续的时间,在持续时间内,扫描设备一直在刚播信道上监听。
注:扫描窗口和扫描间隔这两个参数非常重要。扫描窗口的设置要小于或等于扫描间隔,并且都是0.625ms的整数倍。这两个参数决定了控制器的扫描占空比。如果把两者的时间间隔设置为相同的大小,那么控制器会进行连续扫描。每个间隔会改变扫描频率,也就是切换扫描信道。
Own_Address_Type:本端设备的扫描请求数据包中使用的地址类型。
Scanning_Filter_Policy:BLE扫描的过滤策略,也就是说接受任何广播数据或者仅仅接受报名单设备的广播数据包。实际上就是决定是否使用白名单过滤广播数据包。需要注意的是,如果定向广播数据包中的目的地址并非自己,那么该数据必须被抛弃。即使广播数据包的发送者在自己的报名单内也不例外。官方对筛选定义了如下四种情况
- #define BLE_GAP_SCAN_FP_ACCEPT_ALL 0x00:接收所有的广播包,除去广播地址不是指向该设备的定向广播
- #define BLE_GAP_SCAN_FP_WHITELIST 0x01:接收在白名单里的所有广播,除去广播地址不是指向该设备的定向广播。
- #define BLE_GAP_SCAN_FP_ALL_NOT_RESOLVED_DIRECTED 0x02:接收所有的广播包,包含定向广播包。如果广播MAC地址是私密地址,这里无法被解析。
- #define BLE_GAP_SCAN_FP_WHITELIST_NOT_RESOLVED_DIRECTED 0x03:接收白名单里所有的广播包,包含定向广播包。如果广播MAC地址是私密地址,这里无法被解析。
2.2、使能/停止扫描
Host启动和停止广播,启动扫描后,控制端发现周围环境中的广播设备。

- LE_Scan_Enable:使能还是停止扫描。
- Filter_Duplicates:是否开启广播重复过滤。开启后可避免主机在BLE扫描期间接收到重复的低功耗设备信息,该值只有在扫描使能才会生效。
2.3、上报扫描结果
BLE扫描过程中一个或多个低功耗蓝牙设备对主动扫描作出响应,或者在被动扫描期间收到了广播。控制器一次将扫描到的信息上报给应用层。

三、被动扫描
在被动扫描中,扫描者仅仅去监听广播包,而不向广播者发送任何数据。
一旦扫描参数设置完成,主机就可以启动扫描。扫描过程中,如果控制器接收到符合过滤策略和其他规则的广播数据包,则发送一个LE Advertising Report事件给主机。除了广播者的设备地址外,报告事件还包括广播数据包中的数据,以及接受广播数据包时的信号接受强度(RSSI)。可以利用该信号强度以及位于广播数据包中的发送功率,共同确定信号的路径损失,从而给出大致的范围。这个应用就是防丢器和蓝牙定位。被动扫描不需要向从机发送任何数据。
下图是被动扫描的过程:

相关文章:
蓝牙学习十(扫描)
一、简介 从之前的文章中我们知道,蓝牙GAP层定义了四种角色,广播者(Broadcaster)、观察者(Observer)、外围设备(Peripheral)、中央设备(Central)。 之前的学习…...
(26)4.7 字符函数和字符串函数
#include<stdio.h> #include<string.h> #include<assert.h> //int my_strcmp(const char* str1, const char* str2) //{ // assert(str1 && str2);//指针有效性,不能为空指针 // while (*str1 *str2) // { // if (*str1…...
交换机与队列的简介
1.流程 首先先介绍一个简单的一个消息推送到接收的流程,提供一个简单的图 黄色的圈圈就是我们的消息推送服务,将消息推送到 中间方框里面也就是 rabbitMq的服务器,然后经过服务器里面的交换机、队列等各种关系(后面会详细讲&…...
1.docker
Docker 是一种容器化平台,可以在不同的操作系统中轻松运行和管理应用程序。它使用容器技术来打包应用程序及其所有依赖关系,使其可以在任何环境中运行。 Docker 的基本概念包括以下几个部分: 镜像(Image):…...
ThinkPHP审计(2) Thinkphp反序列化链5.1.X原理分析从0编写POC
ThinkPHP审计(2) Thinkphp反序列化链子5.1.X原理分析&从0编写POC 文章目录 ThinkPHP审计(2) Thinkphp反序列化链子5.1.X原理分析&从0编写POC动态调试环境配置Thinkphp反序列化链5.1.X原理分析一.实现任意文件删除二.实现任意命令执行真正的难点 Thinkphp反序列化链5.1.…...
KingbsaeES数据库分区表的详细用法
数据库版本:KingbaseES V008R006C008B0014 简介 分区表是一种将大型数据库表拆分为更小、更可管理的部分的技术。它通过将表数据分散存储到多个物理存储单元中,可以提高查询和数据维护的性能,并优化对大型数据集的处理。本篇文章以kingbase为…...
MySQL 索引底层探索:为什么是B+树?
MySQL 索引底层探索:为什么是B树? 1. 由一个例子总结索引的特点2. 基于哈希表实现的哈希索引3. 高效的查找方式:二分查找4. 基于二分查找思想的二叉查找树5. 升级版的BST树:AVL 树6. 更加符合磁盘特征的B树7. 不断优化的B树&#…...
XML HTTP传输 小结
what’s XML XML 指可扩展标记语言(eXtensible Markup Language)。 XML 被设计用来传输和存储数据,不用于表现和展示数据,HTML 则用来表现数据。 XML 是独立于软件和硬件的信息传输工具。 应该掌握的基础知识 HTMLJavaScript…...
相机标定——四个坐标系介绍
世界坐标系(Xw,Yw,Zw) 世界坐标系是一个用于描述和定位三维空间中物体位置的坐标系,通常反映真实世界下物体的位置和方向。它是一个惯性坐标系,被用作整个场景或系统的参考框架。在很多情况下,世界坐标系被认为是固定不变的,即它…...
C++:MySQL数据库的增删改(三)
1、相关API 执行所有的sql语句都是mysql_query或者mysql_real_query mysql_query无法处理带有特殊字符的sql语句(如:反斜杠0)mysql_real_query则可以避免,一般使用这个。 mysql_affected_rows:获取sql语句执行结果影响…...
golang - 简单实现linux上的which命令
本文提供了在环境变量$PATH设置的目录里查找符合条件的文件的方法。 实现函数 import ("fmt""os""path""strings" )// 实现 unix whtich 命令功能 func Which(cmd string) (filepath string, err error) {// 获得当前PATH环境变量en…...
推荐一个好用的数据库映射架构
SqlSugar ORM 优点: SqlSugar 是 .NET 开源 ORM 框架,由 Fructose 大数据技术团队维护和更新,是开箱即用最易用的 ORM 优点: 【低代码】【高性能】【超简单】【功能综合】【多数据库兼容】【适用产品】 支持 .NET .NET framework.net core3.1.ne5.net6.net7.net8 .net…...
(013)window的Idea运行程序 Amazon java.nio.file.AccessDeniedException
解决方法一 在资源管理器中删除该目录, 在程序中使用代码,重新建立该目录: if (!FileUtil.exist(destinationPath)){FileUtil.mkdir(destinationPath); }解决方法二 JDK 的版本有问题,换个JDK。 解决方法三 网络不好…...
LeetCode 1684. 统计一致字符串的数目
解题思路 首先用set把allowed中的字符保存,然后一一判断。 相关代码 class Solution {public int countConsistentStrings(String allowed, String[] words) {Set<Character> set new HashSet<>();int reswords.length;for(int i0;i<allowed.len…...
uniapp-设置UrlSchemes从外部浏览器H5打开app
需求:外部浏览器H5页面,跳转到uniapp开发的原生app内部。 1、uniapp内部的配置: (1)打开manifest->App常用其他设置,如下,按照提示输入您要设置的urlSchemes: (2&am…...
校园圈子小程序,大学校园圈子,三段交付,源码交付,支持二开
介绍 在当今的数字化时代,校园社交媒体和在线论坛成为了学生交流思想、讨论问题以及分享信息的常用平台。特别是微信小程序,因其便捷性、用户基数庞大等特点,已逐渐成为构建校园社区不可或缺的一部分。以下是基于现有资料的校园小程序帖子发…...
基于kmeans的聚类微博舆情分析系统
第一章绪论 1.1研究背景 如今在我们的生活与生产的每个角落都可以见到数据与信息的身影。自从上十世纪八十年代的中后期开始,我们使用的互联网技术已经开始快速发展,近些年来云计算、大数据和物联网等与互联网有相领域的发展让互联网技术达到了史无前例…...
【Docker常用命令(四)】
目录 Docker常用命令(四)注意 Docker常用命令(四) docker pause docker pause 命令用于暂停容器中的所有进程。docker pause CONTAINER [CONTAINER...]常用子命令和选项:无特定常用选项。docker port docker port 命令…...
黑豹程序员-Spring Task实现定时任务
定时任务 项目中,我们有一个特殊的要求,无需人为去触发,而是自动去触发程序。通常有一定的频率,每天,某时等。 实现的四种方式 1、java自身提供定时任务java.util.Timer类,但太过简单,几乎无…...
云原生安全当前的挑战与解决办法
云原生安全作为一种新兴的安全理念,不仅解决云计算普及带来的安全问题,更强调以原生的思维构建云上安全建设、部署与应用,推动安全与云计算深度融合。所以现在云原生安全在云安全领域越来受到重视,云安全厂商在这块的投入也是越来…...
RestClient
什么是RestClient RestClient 是 Elasticsearch 官方提供的 Java 低级 REST 客户端,它允许HTTP与Elasticsearch 集群通信,而无需处理 JSON 序列化/反序列化等底层细节。它是 Elasticsearch Java API 客户端的基础。 RestClient 主要特点 轻量级ÿ…...
云原生核心技术 (7/12): K8s 核心概念白话解读(上):Pod 和 Deployment 究竟是什么?
大家好,欢迎来到《云原生核心技术》系列的第七篇! 在上一篇,我们成功地使用 Minikube 或 kind 在自己的电脑上搭建起了一个迷你但功能完备的 Kubernetes 集群。现在,我们就像一个拥有了一块崭新数字土地的农场主,是时…...
【kafka】Golang实现分布式Masscan任务调度系统
要求: 输出两个程序,一个命令行程序(命令行参数用flag)和一个服务端程序。 命令行程序支持通过命令行参数配置下发IP或IP段、端口、扫描带宽,然后将消息推送到kafka里面。 服务端程序: 从kafka消费者接收…...
iOS 26 携众系统重磅更新,但“苹果智能”仍与国行无缘
美国西海岸的夏天,再次被苹果点燃。一年一度的全球开发者大会 WWDC25 如期而至,这不仅是开发者的盛宴,更是全球数亿苹果用户翘首以盼的科技春晚。今年,苹果依旧为我们带来了全家桶式的系统更新,包括 iOS 26、iPadOS 26…...
TDengine 快速体验(Docker 镜像方式)
简介 TDengine 可以通过安装包、Docker 镜像 及云服务快速体验 TDengine 的功能,本节首先介绍如何通过 Docker 快速体验 TDengine,然后介绍如何在 Docker 环境下体验 TDengine 的写入和查询功能。如果你不熟悉 Docker,请使用 安装包的方式快…...
进程地址空间(比特课总结)
一、进程地址空间 1. 环境变量 1 )⽤户级环境变量与系统级环境变量 全局属性:环境变量具有全局属性,会被⼦进程继承。例如当bash启动⼦进程时,环 境变量会⾃动传递给⼦进程。 本地变量限制:本地变量只在当前进程(ba…...
反向工程与模型迁移:打造未来商品详情API的可持续创新体系
在电商行业蓬勃发展的当下,商品详情API作为连接电商平台与开发者、商家及用户的关键纽带,其重要性日益凸显。传统商品详情API主要聚焦于商品基本信息(如名称、价格、库存等)的获取与展示,已难以满足市场对个性化、智能…...
HTML 列表、表格、表单
1 列表标签 作用:布局内容排列整齐的区域 列表分类:无序列表、有序列表、定义列表。 例如: 1.1 无序列表 标签:ul 嵌套 li,ul是无序列表,li是列表条目。 注意事项: ul 标签里面只能包裹 li…...
Python如何给视频添加音频和字幕
在Python中,给视频添加音频和字幕可以使用电影文件处理库MoviePy和字幕处理库Subtitles。下面将详细介绍如何使用这些库来实现视频的音频和字幕添加,包括必要的代码示例和详细解释。 环境准备 在开始之前,需要安装以下Python库:…...
【Oracle】分区表
个人主页:Guiat 归属专栏:Oracle 文章目录 1. 分区表基础概述1.1 分区表的概念与优势1.2 分区类型概览1.3 分区表的工作原理 2. 范围分区 (RANGE Partitioning)2.1 基础范围分区2.1.1 按日期范围分区2.1.2 按数值范围分区 2.2 间隔分区 (INTERVAL Partit…...
