如果把蓝牙HID设备和主机的通信比作一场对话,那么协议消息就是双方交流的语言。我们日常用蓝牙键盘打字、鼠标移动、手柄操作,本质上都是设备与主机通过一系列标准化消息完成数据交换。这些消息看似繁杂,却有着严格的格式定义和交互逻辑,是保证无线人机交互流畅、可靠的核心。本文深入拆解蓝牙HID协议消息的底层设计,从消息结构、类型分类、交互规则三个维度,读懂这场无线对话的底层逻辑。
目录
[1.1 消息头(HIDP-Hdr):消息的身份标识](#1.1 消息头(HIDP-Hdr):消息的身份标识)
[1.2 消息的核心约束:MTU限制与长度规则](#1.2 消息的核心约束:MTU限制与长度规则)
[1.3 消息的传输信道:控制信道与中断信道的分工](#1.3 消息的传输信道:控制信道与中断信道的分工)
[2.1 握手消息(HANDSHAKE):通信的确认回执](#2.1 握手消息(HANDSHAKE):通信的确认回执)
[2.2 控制消息(HID_CONTROL):设备的状态切换指令](#2.2 控制消息(HID_CONTROL):设备的状态切换指令)
[2.3 报告请求消息(GET_REPORT/SET_REPORT):数据的查询与配置指令](#2.3 报告请求消息(GET_REPORT/SET_REPORT):数据的查询与配置指令)
[2.4 协议模式消息(GET_PROTOCOL/SET_PROTOCOL):通信方言的切换指令](#2.4 协议模式消息(GET_PROTOCOL/SET_PROTOCOL):通信方言的切换指令)
[2.5 数据消息(DATA):实时数据的传输载体](#2.5 数据消息(DATA):实时数据的传输载体)
[2.6 废弃消息类型(DEPRECATED):历史遗留的过时词汇](#2.6 废弃消息类型(DEPRECATED):历史遗留的过时词汇)
[3.1 请求-响应模式:控制信道的交互准则](#3.1 请求-响应模式:控制信道的交互准则)
[3.2 异步传输模式:中断信道的交互准则](#3.2 异步传输模式:中断信道的交互准则)
[3.3 消息优先级与冲突处理](#3.3 消息优先级与冲突处理)
一、协议消息的基础架构
任何语言都有语法规则,蓝牙HID协议消息也不例外。其基础架构包括消息头、消息类型、数据负载三部分,就像句子的标点符号、词性、内容,共同构成了标准化的通信格式。
1.1 消息头(HIDP-Hdr):消息的身份标识

所有蓝牙HID协议消息都以一个1字节的消息头(HIDP-Hdr)开头,这个消息头相当于消息的身份证,告诉接收方这是一条什么类型的消息、包含哪些参数。消息头的结构分为两个4位字段,具体如下:
|---------|-------------------------|------------------------|
| 比特位 | 字段名称 | 功能描述 |
| 7-4 | 消息类型(HIDP Message Type) | 定义消息的核心类型,如握手、控制、数据传输等 |
| 3-0 | 参数(Parameter) | 补充消息类型的细节信息,含义随消息类型变化 |
这种4+4的比特分配设计非常精妙,既保证了消息类型的扩展性(支持16种类型),又能通过参数字段传递关键细节,同时仅占用1字节,最大限度减少了无线传输的开销。
协议中明确规定,保留字段(Reserved)在写入时必须设为0,读取时应忽略。这一设计确保了不同版本设备的兼容性------新版本协议新增的消息类型不会影响旧版本设备的正常工作,旧版本设备只需忽略无法识别的消息类型即可。
1.2 消息的核心约束:MTU限制与长度规则
无线传输的带宽有限,为了避免消息过大导致传输延迟或丢包,协议对消息长度有严格约束:所有HIDP消息的长度不得超过L2CAP通道协商的 MTU ( 最大传输单元 )。
对于主机和设备的实现要求的是,发送方不得发送超过MTU的消息,接收方应忽略长度超过MTU或预期长度的消息。这一规则看似简单,却直接影响着设备的兼容性和传输性能。例如,Boot协议模式下的主机MTU最小为48字节,因此设备发送的Boot协议报告(含消息头和数据)不得超过46字节(预留2字节用于L2CAP头部)。
不同消息类型的长度规则也不同,主要分为固定长度和可变长度两类:
固定长度消息:如HANDSHAKE、GET_PROTOCOL等,长度固定为1字节(仅含消息头);
可变长度消息:如DATA、SET_REPORT等,长度=1字节消息头+数据负载,数据负载长度随传输内容变化。
这种长度规则的设计,既保证了简单消息的传输效率,又为复杂数据传输提供了灵活性。
1.3 消息的传输信道:控制信道与中断信道的分工
蓝牙HID协议消息通过两种逻辑信道传输,不同类型的消息对应不同的信道,分工明确,就像城市中的主干道和快车道,分别承担不同的运输任务:
|---------------|-----------------------------------|-----------------|-------------------|
| 信道 类型 | 传输消息类型 | 核心特点 | 适用场景 |
| 控制信道 | HANDSHAKE、HID_CONTROL、GET_、SET_ | 可靠传输,有确认机制,延迟较高 | 控制指令、同步数据传输、消息确认 |
| 中断信道 | DATA | 低延迟传输,无确认机制 | 异步数据传输,如鼠标移动、键盘按键 |
协议规定,部分消息类型有专属传输信道,例如HANDSHAKE消息只能通过控制信道发送,且只能由设备发送给主机;DATA消息可通过两种信道传输,但中断信道的DATA消息主要用于异步输入/输出报告,控制信道的DATA消息主要用于同步报告响应。
这种信道分工设计,是平衡传输可靠性和实时性的关键------控制指令需要确保送达,因此采用有确认机制的控制信道;而用户操作数据(如鼠标移动)需要低延迟,因此采用无确认机制的中断信道。
二、核心消息类型解析:设备与主机的对话词典
蓝牙HID协议定义了10种核心消息类型,其中部分类型已被标记为废弃(DEPRECATED),实际常用的有8种。这些消息涵盖了设备与主机交互的所有场景,从连接控制、数据传输到状态查询,形成了一套完整的对话词典。

2.1 握手消息(HANDSHAKE):通信的确认回执
HANDSHAKE消息是设备向主机发送的确认消息,相当于对话中的收到、明白,用于告知主机之前发送的指令是否成功执行。

(1)核心功能
-
确认SET_REPORT、SET_PROTOCOL等控制指令的执行结果;
-
通知主机GET_REPORT、GET_PROTOCOL等请求的参数错误;
-
告知主机收到了不支持的消息类型。
(2)参数字段解析
消息头的参数字段(3-0比特)为结果码(Result Code),定义了16种可能的结果,核心结果码如下:
0x0(SUCCESSFUL):指令成功执行,这是最常见的结果码,例如设备成功接收并执行了SET_PROTOCOL指令;
0x1(NOT_READY):设备暂时忙碌,无法接收数据,主机应稍后重发;
0x2(ERR_INVALID_REPORT_ID):报告ID无效,例如主机请求的报告ID在设备中未定义;
0x3(ERR_UNSUPPORTED_REQUEST):设备不支持该请求,例如主机发送了设备未实现的消息类型;
0x4(ERR_INVALID_PARAMETER):参数值超出范围或不适当,例如主机设置的协议模式无效;
0xF(ERR_FATAL):致命错误,设备需要重启才能恢复功能。
协议特别强调,HANDSHAKE消息只能由设备通过控制信道发送,主机不得发送该消息。这一设计符合"请求-响应"的通信逻辑------主机发起请求,设备执行后返回确认,确保主机能及时了解指令执行状态。
2.2 控制消息(HID_CONTROL):设备的状态切换指令
HID_CONTROL消息用于请求设备发生重大状态变化,相当于对话中的命令,例如让设备进入低功耗模式、断开连接等。

(1)核心功能与参数
消息头的参数字段(3-0比特)为控制操作(Control Operation),定义了6种操作,其中部分已废弃:
SUSPEND(0x3):让设备进入低功耗模式,设备可关闭非必要电路,仅保留唤醒功能;
EXIT_SUSPEND(0x4):让设备退出低功耗模式,恢复正常工作状态;
VIRTUAL_CABLE_UNPLUG(0x5):断开虚拟电缆,设备和主机应删除对方的配对信息和连接记录;
NOP、HARD_RESET、SOFT_RESET(0x0-0x2):已废弃,NOP无实际功能,复位功能通过其他机制实现。
(2)关键操作详解
-
SUSPEND与EXIT_SUSPEND:这对操作是设备功耗管理的核心。主机进入休眠状态时,会向设备发送SUSPEND指令,设备收到后可关闭LED指示灯、降低传感器采样率等,以节省电量;主机退出休眠时,发送EXIT_SUSPEND指令,设备恢复正常工作。例如,蓝牙鼠标在主机休眠后会关闭光学传感器,仅保留按键检测功能,用户按下按键时自动唤醒并向主机发送EXIT_SUSPEND响应。
-
VIRTUAL_CABLE_UNPLUG:这是唯一允许设备和主机双向发送的HID_CONTROL消息。发送方发送该消息后,应删除与接收方相关的所有持久化信息(如配对密钥、虚拟电缆配置);接收方收到后,除了删除相关信息,还应通过L2CAP断开中断信道和控制信道,最终断开ACL连接。这一操作相当于主动拔掉虚拟电缆,与普通的断开连接不同,它会彻底清除连接记录,下次连接需要重新配对。
2.3 报告请求消息(GET_REPORT/SET_REPORT):数据的查询与配置指令
GET_REPORT和SET_REPORT是数据交互的核心消息,分别用于主机查询设备状态和配置设备参数,相当于对话中的询问和设置。
(1)GET_REPORT:主机向设备询问数据

功能:主机请求设备返回指定类型的报告(输入、输出、特征),例如查询鼠标当前的按键状态、传感器的测量数据;
消息结构:长度1-4字节,包含消息头、报告类型、报告ID(可选)、缓冲区大小(可选);
报告类型参数:消息头的0-1比特定义报告类型(1=输入、2=输出、3=特征);
报告ID:当设备的报告描述符中定义了报告ID时,该字段必填,用于指定请求的具体报告;
缓冲区大小:当消息头的2比特(Size位)设为1时,该字段必填,用于告知设备主机已分配的缓冲区大小,设备返回的数据不得超过该大小。
协议规定,设备收到GET_REPORT请求后,应在控制信道返回DATA消息,包含请求的报告数据;若请求参数错误(如报告ID无效),则返回HANDSHAKE消息,携带对应的错误码。

(2)SET_REPORT:主机向设备设置数据

功能:主机向设备发送报告数据,配置设备状态或触发特定功能,例如设置游戏手柄的震动强度、键盘的LED指示灯状态;
消息结构:长度=1字节消息头+报告数据负载,包含报告类型、报告ID(可选)、报告数据;
报告类型参数:与GET_REPORT一致,0-1比特定义报告类型;
**报告数据:**需符合设备报告描述符定义的格式,否则设备会返回ERR_INVALID_PARAMETER错误。
设备收到SET_REPORT请求后,应执行相应操作并返回HANDSHAKE消息(SUCCESSFUL或错误码);若通过中断信道发送异步输出报告,则无需返回确认。
2.4 协议模式消息(GET_PROTOCOL/SET_PROTOCOL):通信方言的切换指令
这两种消息用于查询和设置设备的协议模式(报告协议模式或引导协议模式),相当于对话中切换沟通方式,确保主机和设备使用相同的方言交流。
(1)GET_PROTOCOL:查询当前协议模式

-
功能:主机请求设备返回当前使用的协议模式;
-
消息结构:固定1字节(仅含消息头),参数字段保留为0;
-
响应:设备收到后,在控制信道返回DATA消息,数据负载1字节,0=引导协议模式,1=报告协议模式。
(2)SET_PROTOCOL:设置协议模式

功能:主机要求设备切换到指定的协议模式;
消息结构:固定1字节(仅含消息头),参数字段0-0比特定义目标模式(0=引导协议模式,1=报告协议模式);
响应:设备收到后,切换模式并返回HANDSHAKE消息(SUCCESSFUL或错误码)。
协议规定,只有当设备的SDP属性HIDBootDevice设为TRUE时,才需要支持这两种消息。这意味着普通传感器等设备可以不支持协议模式切换,而键盘、鼠标等设备必须支持,以确保在BIOS等资源受限环境下正常工作。
2.5 数据消息(DATA):实时数据的传输载体
DATA消息是异步数据传输的核心,用于设备向主机发送输入报告、主机向设备发送输出报告,相当于对话中的实时反馈,例如鼠标移动的坐标数据、手柄的震动指令。

(1)核心功能与结构
消息结构:长度=1字节消息头+报告数据负载,消息头的0-1比特定义报告类型(1=输入、2=输出、3=特征);
传输信道:可通过控制信道(同步传输)或中断信道(异步传输)发送;
核心特点:无确认机制,传输优先级高,延迟低。
(2)不同信道的传输场景
中断信道DATA消息:主要用于实时性要求高的异步数据,例如键盘按键、鼠标移动、手柄操作。这类数据变化频繁,要求低延迟,无确认机制可以减少传输开销,确保操作流畅。协议规定,中断信道的DATA消息无需返回HANDSHAKE确认,接收方收到后直接处理;
控制信道DATA消息:主要用于响应GET_REPORT、GET_PROTOCOL等请求,例如设备返回主机查询的输入报告数据。这类数据传输是同步的,主机发送请求后等待设备响应,确保数据的可靠性。
2.6 废弃消息类型(DEPRECATED):历史遗留的过时词汇
协议演进过程中,部分消息类型因功能冗余或场景替代被标记为废弃,了解这些废弃类型有助于避免开发中的误区:
GET_IDLE/SET_IDLE:原本用于设置和查询设备的空闲报告率,即设备在无操作时的报告发送间隔。现在这一功能由设备自主管理,主机无需干预,因此被废弃。协议规定,主机不得发送GET_IDLE消息,应避免发送SET_IDLE消息;设备收到后应返回ERR_UNSUPPORTED_REQUEST错误;
DATC:原本用于分段传输超过MTU的报告数据,现在由L2CAP的增强重传模式(Enhanced Retransmission Mode)替代,协议规定主机和设备不得发送该消息。
这些废弃类型的存在,反映了协议的演进逻辑------去除冗余功能,强化核心能力,同时通过明确的废弃规则确保新旧设备的兼容性。
三、消息交互的核心规则
就像人与人之间的对话需要遵循社交礼仪,蓝牙HID协议消息的交互也有严格规则,这些规则确保了设备与主机之间的通信顺畅、有序、可靠。
3.1 请求-响应模式:控制信道的交互准则
控制信道的消息交互遵循**"请求-响应"**模式,即主机发起请求,设备返回响应,这是确保控制指令可靠执行的核心准则。
典型的请求-响应流程如下:
主机通过控制信道发送请求消息(如SET_PROTOCOL);
设备接收并解析请求,执行相应操作;
设备通过控制信道返回响应消息(如HANDSHAKE SUCCESSFUL);
主机接收响应,确认指令执行状态,若为错误码则进行重试或报错。
协议规定,主机在同一时间对同一设备只能有一个控制信道传输未完成,即前一个请求的响应未收到前,不得发送新的请求。这一规则避免了控制指令的冲突,确保设备能有序处理主机的请求。
唯一的例外是VIRTUAL_CABLE_UNPLUG消息------无论是否有未完成的控制信道传输,主机或设备都可随时发送该消息,优先级最高。这是因为断开虚拟电缆是紧急操作,需要立即执行,避免数据泄露或连接异常。
3.2 异步传输模式:中断信道的交互准则
中断信道的消息交互遵循异步传输模式,即发送方无需等待接收方确认,直接发送消息,这是保证实时性的核心准则。
典型的异步传输流程如下:
设备检测到用户操作(如鼠标移动),生成输入报告;
设备通过中断信道发送DATA消息,包含输入报告数据;
主机接收DATA消息,解析并处理数据(如更新光标位置);
无需返回确认消息,设备继续监测用户操作并发送后续消息。
这种模式的优势是延迟极低,适合传输变化频繁、实时性要求高的数据。但由于无确认机制,存在数据丢失的风险。为了降低丢包影响,协议推荐将高频传输的报告数据限制在12字节以内(含消息头和报告ID),这样可以通过单个DM1数据包传输(最大 payload 17字节),既减少了分段传输的开销,又利用DM1数据包的前向纠错功能提升可靠性。
3.3 消息优先级与冲突处理
当设备需要同时发送多种消息时,协议隐含了消息优先级规则,确保关键消息优先传输:
紧急消息:VIRTUAL_CABLE_UNPLUG、SUSPEND、EXIT_SUSPEND等控制消息,优先级最高,需立即发送;
确认消息:HANDSHAKE消息,优先级次之,确保主机及时了解指令执行状态;
数据消息:普通DATA消息,优先级最低,可在紧急消息和确认消息发送后传输。
冲突处理的核心原则是紧急优先、先到先得。例如,设备在发送输入报告的DATA消息时,收到主机的SUSPEND指令,应立即暂停DATA消息传输,先处理SUSPEND指令并返回HANDSHAKE确认,再继续传输数据消息。
四、实战视角:消息交互的典型场景
理论规则需要结合实际场景才能更好理解,下面通过三个典型场景,拆解协议消息的交互过程,让抽象的规则变得具体可感。
场景1:鼠标连接后的协议模式切换
-
主机与鼠标建立虚拟电缆连接,通过SDP获取鼠标的SDP属性,发现鼠标支持引导协议模式(HIDBootDevice=TRUE);
-
主机通过控制信道发送SET_PROTOCOL消息,参数字段设为0(引导协议模式);
-
鼠标接收消息,切换到引导协议模式,通过控制信道返回HANDSHAKE消息,结果码设为0x0(SUCCESSFUL);
-
主机接收HANDSHAKE消息,确认模式切换成功,后续通过引导协议模式接收鼠标的输入报告。
场景2:键盘的LED指示灯控制
-
主机需要开启键盘的Caps Lock灯,生成输出报告(包含LED控制参数);
-
主机通过控制信道发送SET_REPORT消息,报告类型设为2(输出),报告ID设为1(键盘LED报告),数据负载设为0x01(Caps Lock灯亮);
-
键盘接收消息,解析报告数据,开启Caps Lock灯,通过控制信道返回HANDSHAKE消息,结果码设为0x0(SUCCESSFUL);
-
主机接收HANDSHAKE消息,确认LED控制成功。
场景3:设备低功耗模式切换
-
主机长时间无操作,进入休眠状态,通过控制信道发送HID_CONTROL消息,参数字段设为0x3(SUSPEND);
-
设备接收消息,关闭非必要电路(如LED指示灯、传感器),进入低功耗模式,通过控制信道返回HANDSHAKE消息,结果码设为0x0(SUCCESSFUL);
-
一段时间后,用户按下设备的按键,设备自动唤醒,通过控制信道向主机发送HID_CONTROL消息,参数字段设为0x4(EXIT_SUSPEND);
-
主机接收消息,退出休眠状态,通过控制信道返回HANDSHAKE消息,结果码设为0x0(SUCCESSFUL);
-
设备恢复正常工作,继续监测用户操作并发送输入报告。
五、测验
题目:蓝牙HID协议中HANDSHAKE消息的核心作用是什么?它的传输规则和结果码分类有哪些?(某物联网企业2024年面试题)
答案:
HANDSHAKE消息的核心作用是设备向主机返回指令执行结果的确认消息,相当于通信中的回执,确保主机及时了解请求的执行状态。
传输规则:
-
发送方:仅允许蓝牙HID设备发送,主机不得发送;
-
传输信道:只能通过控制信道传输,不得在中断信道发送;
-
触发条件:设备执行完主机发送的SET_*、GET_*等请求后触发,或检测到请求参数错误时触发。
结果码分类(核心):
-
成功类:SUCCESSFUL(0x0),表示指令已成功执行;
-
临时错误类:NOT_READY(0x1),设备暂时忙碌,主机可稍后重发;
-
参数错误类:ERR_INVALID_REPORT_ID(0x2)、ERR_INVALID_PARAMETER(0x4),分别表示报告ID无效和参数值异常;
-
功能不支持类:ERR_UNSUPPORTED_REQUEST(0x3),表示设备不支持该请求;
-
致命错误类:ERR_FATAL(0xF),表示设备需重启才能恢复功能。
题目:蓝牙HID协议中VIRTUAL_CABLE_UNPLUG消息的特殊之处是什么?发送和接收该消息后,设备和主机需要执行哪些操作?(某消费电子企业2023年面试题)
答案:
VIRTUAL_CABLE_UNPLUG消息的特殊之处在于:
-
双向发送:是唯一允许蓝牙HID设备和主机双向发送的HID_CONTROL消息;
-
优先级最高:无论是否有未完成的控制信道传输,均可随时发送;
-
彻底清除连接:不仅断开当前连接,还会清除所有相关的持久化信息。
发送方操作:
-
发送VIRTUAL_CABLE_UNPLUG消息后,立即销毁或失效与接收方相关的所有蓝牙配对信息和虚拟电缆配置;
-
等待接收方断开信道连接,或主动发起信道断开流程。
接收方操作:
-
收到消息后,立即销毁或失效与发送方相关的所有持久化信息;
-
不返回HANDSHAKE消息,而是先向发送方发送L2CAP断开请求(中断信道);
-
中断信道关闭后,再发送L2CAP断开请求(控制信道);
-
若没有其他协议使用ACL连接,断开ACL连接;
-
丢弃当前所有未完成的控制信道传输。
题目:蓝牙HID协议中DATA消息的传输规则是什么?控制信道和中断信道的DATA消息有何区别?
答案:
DATA消息的核心传输规则:
-
消息结构:1字节消息头(含消息类型和报告类型)+ 报告数据负载,总长度不得超过L2CAP MTU;
-
报告类型:消息头0-1比特定义,1=输入、2=输出、3=特征、0=其他(用于协议模式查询响应);
-
传输约束:接收方应忽略长度超过MTU或不符合报告描述符格式的DATA消息。
控制信道和中断信道的DATA消息区别:
-
传输模式:控制信道为同步传输,需配合GET_*/SET_*请求触发,有隐含的确认机制;中断信道为异步传输,无需请求,发送方直接发送,无确认机制;
-
用途:控制信道DATA消息主要用于响应主机的GET_REPORT、GET_PROTOCOL等请求,传输同步数据;中断信道DATA消息主要用于传输异步输入/输出报告,如鼠标移动、键盘按键、手柄震动指令;
-
可靠性:控制信道DATA消息因配合请求-响应模式,可靠性高;中断信道DATA消息无确认,可靠性依赖于蓝牙链路质量,适合实时性要求高的场景。