现在低功耗蓝牙(BLE)连接都是建立在 GATT (Generic Attribute Profile) 协议之上。GATT 是一个在蓝牙连接之上的发送和接收很短的数据段的通用规范,这些很短的数据段被称为属性(Attribute)。
详细介绍 GATT 之前,需要了解 GAP(Generic Access Profile),它用来控制设备连接和广播。GAP 使你的设备被其他设备可见,并决定了你的设备是否可以或者怎样与合同设备进行交互。例如 Beacon 设备就只是向外广播,不支持连接,小米手环等设备就可以与中心设备连接。
GAP 给设备定义了若干角色,其中主要的两个是:外围设备(Peripheral)和中心设备(Central)。
外围设备:这一般就是非常小或者简单的低功耗设备,用来提供数据,并连接到一个更加相对强大的中心设备。例如小米手环。
中心设备:中心设备相对比较强大,用来连接其他外围设备。例如手机等。
在 GAP 中外围设备通过两种方式向外广播数据:Advertising Data Payload(广播数据)和 Scan Response Data Payload(扫描回复),每种数据最长可以包含 31 byte。这里广播数据是必需的,因为外设必需不停的向外广播,让中心设备知道它的存在。扫描回复是可选的,中心设备可以向外设请求扫描回复,这里包含一些设备额外的信息,例如设备的名字。
GAP 的广播工作流程如下图所示。
从图中我们可以清晰看出广播数据和扫描回复数据是怎么工作的。外围设备会设定一个广播间隔,每个广播间隔中,它会重新发送自己的广播数据。广播间隔越长,越省电,同时也不太容易扫描到。
大部分情况下,外设通过广播自己来让中心设备发现自己,并建立 GATT 连接,从而进行更多的数据交换。也有些情况是不需要连接的,只要外设广播自己的数据即可。用这种方式主要目的是让外围设备,把自己的信息发送给多个中心设备。因为基于 GATT 连接的方式,只能是一个外设连接一个中心设备。使用广播这种方式最典型的应用就是苹果的 iBeacon。广播工作模式下的网络拓扑图如下:
GATT 的全名是 Generic Attribute Profile(姑且翻译成:普通属性协议),它定义两个 BLE 设备通过叫做 Service 和 Characteristic 的东西进行通信。GATT 就是使用了 ATT(Attribute Protocol)协议,ATT 协议把 Service, Characteristic 以及对应的数据保存在一个查找表中,此查找表使用 16 bit ID 作为每一项的索引。
一旦两个设备建立起了连接,GATT 就开始起作用了,这也意味着,你必需完成前面的 GAP 协议。这里需要说明的是,GATT 连接,必需先经过 GAP 协议。实际上,在 Android 开发中,可以直接使用设备的 MAC 地址,发起连接,可以不经过扫描的步骤。这并不意味不需要经过 GAP,实际上在芯片级别已经给你做好了,蓝牙芯片发起连接,总是先扫描设备,扫描到了才会发起连接。
GATT 连接需要特别注意的是:GATT 连接是独占的。也就是一个 BLE 外设同时只能被一个中心设备连接。一旦外设被连接,它就会马上停止广播,这样它就对其他设备不可见了。当设备断开,它又开始广播。
中心设备和外设需要双向通信的话,唯一的方式就是建立 GATT 连接。
下图展示了 GATT 连接网络拓扑结构。这里很清楚的显示,一个外设只能连接一个中心设备,而一个中心设备可以连接多个外设。
一旦建立起了连接,通信就是双向的了,对比前面的 GAP 广播的网络拓扑,GAP 通信是单向的。如果你要让两个设备外设能通信,就只能通过中心设备中转。
GATT 通信的双方是 C/S 关系。外设作为 GATT 服务端(Server),它维持了 ATT 的查找表以及 service 和 characteristic 的定义。中心设备是 GATT 客户端(Client),它向 Server 发起请求。需要注意的是,所有的通信事件,都是由客户端(也叫主设备,Master)发起,并且接收服务端(也叫从设备,Slave)的响应。
一旦连接建立,外设将会给中心设备建议一个连接间隔(Connection Interval),这样,中心设备就会在每个连接间隔尝试去重新连接,检查是否有新的数据。但是,这个连接间隔只是一个建议,你的中心设备可能并不会严格按照这个间隔来执行,例如你的中心设备正在忙于连接其他的外设,或者中心设备资源太忙。
下图展示一个外设(GATT 服务端)和中心设备(GATT 客户端)之间的数据交换流程,可以看到的是,每次都是主设备发起请求:
GATT 事务是建立在嵌套的 Profiles, Services 和 Characteristics 之上的的,如下图所示:
1、Profile 并不是实际存在于 BLE 外设上的,它只是一个被 Bluetooth SIG 或者外设设计者预先定义的 Service 的集合。例如心率 Profile(Heart Rate Profile)就是结合了 Heart Rate Service 和 Device Information Service。所有官方通过 GATT Profile 的列表可以从这里找到。
2、Service 是把数据分成一个个的独立逻辑项,它包含一个或者多个 Characteristic。每个 Service 有一个 UUID 唯一标识。 UUID 有 16 bit 的,或者 128 bit 的。16 bit 的 UUID 是官方通过认证的,需要花钱购买,128 bit 是自定义的,这个就可以自己随便设置。
官方通过了一些标准 Service,完整列表在这里。以 Heart Rate Service 为例,可以看到它的官方通过 16 bit UUID 是 0x180D,包含 3 个 Characteristic:Heart Rate Measurement, Body Sensor Location 和 Heart Rate Control Point,并且定义了只有第一个是必须的,其它是可选实现的。
3、Characteristic 是在 GATT 事务中的最低界别的,Characteristic 是最小的逻辑数据单元,当然它可能包含一组关联的数据,例如加速度计的 X/Y/Z 三轴值。
与 Service 类似,每个 Characteristic 用 16 bit 或者 128 bit 的 UUID 唯一标识。你可以免费使用 Bluetooth SIG 官方定义的标准 Characteristic,使用官方定义的,可以确保 BLE 的软件和硬件能相互理解。当然,你可以自定义 Characteristic,这样的话,就只有你自己的软件和外设能够相互理解。
举个例子,Heart Rate Measurement Characteristic,这是上面提到的 Heart Rate Service 必需实现的 Characteristic,它的 UUID 是 0x2A37。它的数据结构是,开始 8 bit 定义心率数据格式,接下来就是对应格式的实际心率数据。
实际上,和 BLE 外设打交道,主要是通过 Characteristic。你可以从 Characteristic 读取数据,也可以往 Characteristic 写数据。这样就实现了双向的通信。所以你可以自己实现一个类似串口(UART)的 Sevice,这个 Service 中包含两个 Characteristic,一个被配置只读的通道(RX),另一个配置为只写的通道(TX)。
原文链接:https://learn.adafruit.com/introduction-to-bluetooth-low-energy?view=all
基于Recorder.js 和百度平台的语音识别功能实现1.准备工作下载Recorder.js , 实现录音功能,做准备,在Gitee 上搜索Recorder.js ,会出现很多搜索结果,我推荐两个人的,第一个是超级清晰的介绍了Recorder.js 属性、事件等 清晰版本点此下载。还有一个是比较实用的版本实用版本点此下载,很多初始化比较方便、API也很好懂,比较适合第一次写的同学。打开VS,创建一个Web项目,在项目里面创建一个HTML文件(服务器控件太慢了,不想使用)。我用的是实用版本的,
描述:win10系统excel2019计算两个日期相差具体天数时分秒方法步骤:原数据计算两个日期相差时间选择结果,右键设置单元格格式选择数字->自定义->类型输入d h:mm:ss->确定计算结果即为两个日期相差时间...
[[email protected] ~]# df -hFilesystem Size Used Avail Use% Mounted on/dev/mapper/VolGroup-l...
前言在《论文创新的常见思路总结》(点击标题阅读)一文中,提到过一些新的数据集或者新方向比较容易出论文。因此纠结于选择课题方向的读者可以考虑以下几个新方向。文末附相关论文获取方式。本文来自公众号CV技术指南的技术总结系列关注公众号CV技术指南 ,专注于计算机视觉的技术总结、最新技术跟踪、经典论文解读。一些新发布的数据集可以提供一个窗口,通过这些数据集可以了解试图解决的问题的复杂程度。公共领域中新发布的数据集可以很好地代表理解计算机视觉的发展以及有待解决的问题的新途径。本文简要总结.
一、准备工具:Apache2.4,JDK1.7,Tomcat7(最少两个)二、Apache安装好后配置1.首先打开一些必要的Module注释(把前面的#号去掉就行),在conf/httpd这个文件中LoadModule proxy_module modules/mod_proxy.soLoadModule proxy_ajp_module modules/mod_proxy_ajp.soLoa...
需要在数据库连接参数加上allowMultiQueries=true
数据库redis使用优点使用方法redis的简单类型String字符串注意一个键最大能存储512MB哈希list列表set集合注意redis安全可以通过以下命令查看是否设置了密码验证用python实现链接数据库redis-connectredis密码破解redis使用设置数据添加数据redis查看服务器配置插入值追加数据setget数据导出dumprdb 这个即为
1、问题描述设计一个学生成绩管理系统,通过此系统可以实现如下功能:(1)能输入并显示n个学生信息和m门考试科目的成绩,计算各个学生的总分和平均分,结果写入原始数据文件并按格式打...1、问题描述设计一个学生成绩管理系统,通过此系统可以实现如下功能:(1) 能输入并显示n个学生信息和m门考试科目的成绩,计算各个学生的总分和平均分,结果写入原始数据文件并按格式打印在屏幕上;(成绩查看1)(2) 任意输...
Spring1.1、简介Spring:春天------>给软件行业带来了春天2002,首次推出了Spring框架的雏形:interface 21框架!Spring框架即以interface21框架为基础,经过重新设计,并不断丰富内涵,于2004年3月24日,发布了1.0正式版。Rod Johnson,Spring Framework创始人spring理念:使现有的技术更加容易使用,本身是一个大杂烩,整合了现有的技术框架!SSH : Struct2 + Spring
一个超级简单的方法,直接使用第三方接口即可。一个快速的解决方法:如果项目需求只要求预览内容而不要求对文档进行编辑的操作,则可以选择在线预览的方式进行处理;现附上两个在线预览office文档的地址:(浏览器都需要chrome的内核)1、 https://docs.google.com/viewer?url=(输入你的文档在服务器中的地址)2、 https://view.offi...
数据处理Tedu Python 教学部Author:吕泽文章目录数据处理数据处理1. 文件处理1.1 引入1.2 文件读写操作1.2.1 打开文件1.2.2 读取文件1.2.3 写入文件1.2.4 关闭文件1.2.5 with操作1.2.6 缓冲区1.2.7 文件偏移量1.3 os模块2. 正则表达式2.1 概述2.2 元字符使用2.3 匹配规则2.3.1 特殊字符匹配2.3.2 贪婪模式和非贪婪模式2.3.3 正则表达式分组2.3.4 正则表达式匹配原则2.4 Python r
1. Android 9.0 之前的亮度控制接口import android.os.IPowerManager;import android.provider.Settings;import android.content.Context; /** * Used by the settings application and brightness control wid...