1. 连接断开基础概念
做 BLE 开发的朋友,十有八九都被「连接断开」折磨过。设备连上没几秒就掉了,或者跑着跑着突然断连,日志里就留下一串错误码。说实话,我刚入行那会儿,看到断连日志就头大,完全不知道从哪查起。
这一章,我们就从最底层开始,把连接断开这件事彻底讲清楚。你理解了 BLE 的连接状态机,看懂了 HCI Disconnection Complete 事件,后面排查问题就会顺手很多。
BLE 连接状态机
BLE 的连接,说白了就是两个设备之间建立了一个「会话」。这个会话有生命周期,从建立到结束,中间会经历几个固定的状态。我习惯把这几个状态画成一张图,每次调试时对照着看,思路会清晰很多。
这张图里,我最想让你记住的是那个红色的「断开连接」箭头。它从「已连接」状态出发,直接回到「待机」。这意味着什么?意味着一旦断开,所有连接参数、缓冲区、服务句柄全部清零,设备得重新开始。
断开连接的原因分类
断开连接,不是只有一种死法。我把它分成三大类:本地断开、远端断开、超时断开。每一类的根因和排查方向都不一样。
| 分类 | 触发方 | 典型原因 | HCI 错误码 |
|---|---|---|---|
| 本地断开 | 本端主动调用 Disconnect API | 应用层主动断开、GATT 操作异常、资源不足 | 0x16 (Connection Terminated by Local Host) |
| 远端断开 | 对端设备主动断开 | 对端应用关闭连接、对端掉电、对端进入深度睡眠 | 0x13 (Connection Terminated by Remote User) 等 |
| 超时断开 | 链路层监控定时器 | 连接间隔内未收到包、干扰严重、距离过远 | 0x08 (Connection Timeout) |
你看这个表格,三种断开方式的 HCI 错误码是不一样的。我个人觉得,最让人头疼的是超时断开,因为它往往不是单次事件,而是链路质量持续恶化的结果。
HCI Disconnection Complete 事件
当连接断开时,蓝牙控制器会向主机发送一个 HCI Disconnection Complete 事件。这个事件,就是断连的「尸检报告」。你读懂了它,就知道连接是怎么死的。
事件的结构是这样的:
HCI Disconnection Complete Event
├── Event Code: 0x05
├── Parameter Total Length: 4 bytes
├── Status: 0x00 (成功)
├── Connection Handle: 0x0001 (连接句柄)
├── Reason: 0x08 (断开原因)
└── (结束)
这里面最重要的字段就是 Reason。它用一个字节告诉你断开的具体原因。我整理了一份常用的 Reason 值对照表,你调试时可以直接查:
| Reason 值 | 含义 | 常见场景 |
|---|---|---|
| 0x08 | Connection Timeout | 链路超时,最常见 |
| 0x13 | Remote User Terminated Connection | 对端主动断开 |
| 0x14 | Remote Device Terminated Connection due to Low Resources | 对端资源不足 |
| 0x15 | Remote Device Terminated Connection due to Power Off | 对端关机或掉电 |
| 0x16 | Connection Terminated by Local Host | 本端主动断开 |
| 0x22 | LL Procedure Collision | 链路层流程冲突 |
| 0x3E | Connection Failed to be Established | 连接建立失败 |
核心要点:拿到 HCI 日志后,第一件事就是看 Reason 字段。0x08 和 0x16 占了断连原因的 80% 以上。0x08 查链路质量,0x16 查应用层逻辑。
举个例子。有一次,我调试一个手环项目,手机 App 总是提示「设备已断开」。我抓了 HCI 日志,发现 Reason 是 0x14(Remote Device Terminated Connection due to Low Resources)。这说明手环端资源不够了。后来一查,是手环的 GATT 数据库太大,内存分配失败,导致连接被强制断开。
你看,如果没有 HCI 事件,我可能还在手机端瞎找原因。所以我的建议是:调试断连问题,先抓 HCI 日志,先看 Reason 字段。这是最高效的排查路径。
嗯,这一章的内容就到这里。你理解了 BLE 连接状态机,知道了断连的三种分类,也学会了读 HCI Disconnection Complete 事件。后面几章,我们会深入每种断连原因的具体排查方法。