2. CAN总线基础
DroneCAN 与 Cyphal 都构建在经典 CAN 总线之上,因此理解 CAN 的底层行为,是后续调试节点通信、分析总线负载、定位丢帧与错误帧的前提。本节从物理层电气特性出发,逐层向上梳理帧格式、仲裁机制、错误处理与位定时,形成一条完整的“信号—位—帧—仲裁—容错—时序”认知链。
一、物理层:差分信号与终端电阻
经典 CAN 使用两根差分信号线 CAN_H 与 CAN_L,采用“显性位”和“隐性位”两种电平状态。显性位(逻辑 0)驱动总线到约 2.5V 以上的差分电压,隐性位(逻辑 1)差分电压接近 0V。显性位具有“覆盖”隐性位的特性,这正是仲裁机制能够工作的电气基础。
总线两端必须各接一个 120Ω 终端电阻,用于吸收信号反射、稳定差分阻抗。若缺少终端电阻,波形会出现振铃,采样点误判概率显著上升;若只在一端接电阻,阻抗不匹配同样会导致通信不稳定。无人机中常见的 4 针 CAN 接口(CAN_H、CAN_L、GND、VCC)在布线时需保证双绞、等长、短分支。
二、帧格式:标准帧与扩展帧
CAN 2.0B 定义了标准帧(11 位标识符)与扩展帧(29 位标识符)。一帧数据帧主要由以下字段组成:
- SOF:帧起始,1 个显性位,用于硬同步。
- 仲裁场:标准帧为 11 位 ID + RTR;扩展帧为 11 位基本 ID + SRR + IDE + 18 位扩展 ID + RTR。
- 控制场:IDE、r0、DLC(数据长度码,0~8 字节)。
- 数据场:0~8 字节有效载荷。
- CRC 场:15 位 CRC + 1 位界定符,用于检错。
- ACK 场:发送方发隐性位,任一正确接收的节点拉低为显性位表示应答。
- EOF:7 个隐性位,帧结束。
DroneCAN 使用扩展帧,29 位 ID 中承载了源节点、目标节点、消息类型等信息;Cyphal 同样基于扩展帧,通过 ID 编码优先级、服务/消息类型与节点标识。因此,抓包工具中看到的 ID 并非“地址”,而是被协议层重新解释的复合字段。
三、仲裁机制:非破坏性逐位仲裁
当多个节点同时发送时,CAN 采用 CSMA/CR(载波侦听多路访问/冲突解决)机制。每个节点在发送每一位的同时回读总线电平:若自己发送隐性位而读回显性位,说明有更高优先级节点正在发送,该节点立即退出仲裁,转为接收状态,且不会破坏已获胜帧的数据。
仲裁按 ID 逐位比较,ID 数值越小(显性位越多)优先级越高。这意味着在 DroneCAN/Cyphal 中,优先级字段的设计直接决定了哪些消息在总线拥塞时先被发送。例如,飞控的姿态控制消息通常配置为高优先级,而调试日志类消息配置为低优先级。
四、错误处理:五类错误与状态机
CAN 定义了五种错误类型:位错误、填充错误、CRC 错误、格式错误、应答错误。任一节点检测到错误后,会发送错误帧(6 个连续显性位)通知全网,发送方随后自动重发。为限制故障节点持续破坏总线,CAN 引入 TEC(发送错误计数器)与 REC(接收错误计数器),并据此划分三种状态:
| 状态 | 进入条件 | 行为 | 退出条件 |
|---|---|---|---|
| 错误主动 Error Active | TEC ≤ 127 且 REC ≤ 127 | 正常收发,可发送主动错误帧 | — |
| 错误被动 Error Passive | TEC > 127 或 REC > 127 | 仍可通信,但只发被动错误帧,发送后需额外挂起 | TEC 与 REC 均降至 127 以下 |
| 总线关闭 Bus Off | TEC > 255 | 主动断开总线,停止收发 | 检测到 128 次连续 11 个隐性位后恢复 |
五、位定时:采样点与同步
CAN 位时间被划分为四个段:同步段(SYNC_SEG)、传播段(PROP_SEG)、相位缓冲段 1(PHASE_SEG1)和相位缓冲段 2(PHASE_SEG2)。采样点位于 PHASE_SEG1 结束处,通常建议设置在位时间的 75%~87.5% 之间。位时间由若干时间份额 Tq 组成,Tq 由系统时钟分频得到。
位时间 = SYNC_SEG + PROP_SEG + PHASE_SEG1 + PHASE_SEG2
= 1 Tq + PROP_SEG + PHASE_SEG1 + PHASE_SEG2
采样点位置 = (1 + PROP_SEG + PHASE_SEG1) / 总 Tq 数 × 100%
示例(1 Mbps,采样点 87.5%):
总 Tq = 8
SYNC_SEG = 1 Tq
PROP_SEG = 2 Tq
PHASE_SEG1 = 4 Tq
PHASE_SEG2 = 1 Tq
采样点 = (1+2+4)/8 = 87.5%
硬同步发生在 SOF 下降沿,使节点位时间对齐;重同步则通过 SJW(同步跳转宽度)在检测到边沿相位误差时微调 PHASE_SEG1 或 PHASE_SEG2。SJW 通常设为 1~4 Tq,过大易受噪声影响,过小则难以补偿晶振偏差。
六、案例与复盘:总线偶发丢帧排查
某四旋翼在 1 Mbps 下偶发 DroneCAN 节点掉线。抓包显示错误帧集中在电机启动瞬间,TEC 快速上升。排查发现:电机电源线与 CAN 双绞线并行捆扎,且飞控端终端电阻未焊接。整改措施:
- CAN 线远离动力线,交叉时保持 90°;
- 补齐两端 120Ω 终端电阻;
- 将采样点从 75% 调整到 87.5%,提高抗反射能力;
- 确认所有节点波特率与 SJW 配置一致。
整改后错误帧消失,总线负载稳定在 35% 以下。该案例说明:CAN 的物理层、位定时与错误处理并非孤立知识点,而是共同决定总线可靠性的整体。理解仲裁如何保证高优先级消息优先、错误计数器如何隔离故障节点、采样点如何影响误码率,才能在 DroneCAN 与 Cyphal 开发中快速定位底层问题,而不是停留在协议层反复猜测。