2、CAN FD帧格式与差异归纳总结
CAN FD 的帧格式,说白了就是经典 CAN 帧的「升级版」。你想想看,经典 CAN 跑了好几十年,数据场才 8 字节,带宽也越来越不够用。所以 CAN FD 在帧结构上做了几处关键改动——不改动的话,也没办法兼容老控制器了。
我刚开始接触 CAN FD 时,最头疼的就是控制场里那几个新加的位:EDL、BRS、ESI。搞混它们,调试时能折腾你一整天。下面我把帧格式从头到尾捋一遍,同时把和经典 CAN 的差异标出来,你对照着看会清晰很多。
CAN FD 数据帧格式
一个完整的 CAN FD 数据帧,由以下几个段组成(以标准帧为例):
- SOF(起始帧):1 个显性位,和经典 CAN 完全一样。
- 仲裁场:11 位标识符 + RTR(远程发送请求)位。注意:CAN FD 的 RTR 位必须为显性(0),因为 CAN FD 不推荐使用远程帧。
- 控制场:这里变化最大。经典 CAN 是 IDE + 保留位 + DLC(4 位);CAN FD 改成了:IDE + EDL + BRS + ESI + DLC。
- 数据场:0~64 字节,经典 CAN 最多 8 字节。
- CRC 场:17 位或 21 位 CRC,取决于数据长度;经典 CAN 是 15 位。
- ACK 场、EOF、ITM:与经典 CAN 基本一致。
控制场中的关键标志位
| 位名 | 位置 | 功能 | 我踩过的坑 |
|---|---|---|---|
| EDL | 控制场 bit7 | 1 表示 CAN FD 帧,0 表示经典 CAN 帧 | 有些老设备会把 EDL=1 误判为错误帧,导致总线关闭 |
| BRS | 控制场 bit6 | 1 启用更高位速率(数据段加速) | 如果收发器不支持变速,BRS=1 会导致采样错位 |
| ESI | 控制场 bit5 | 发送节点错误状态标识 | 常用在诊断中判断节点健康,我一般把它映射到状态机 |
经典 CAN 与 CAN FD 差异对照
直接上表,你看着会更直观。这张表我调了好几次才把关键差异列全,项目中对比着用很方便。
| 对比项 | 经典 CAN | CAN FD |
|---|---|---|
| 最大数据长度 | 8 字节 | 64 字节 |
| 位速率(数据段) | 最高 1 Mbps | 最高 8 Mbps(取决于收发器) |
| 位速率(仲裁段) | 与数据段相同 | 可不同,通过 BRS 切换 |
| CRC 长度 | 15 位 | 17 位(≤16 字节)或 21 位(>16 字节) |
| CRC 计算覆盖 | SOF~数据场 | SOF~数据场 + 填充位计数 |
| 远程帧 | 支持 | 不推荐(CIA 规范建议禁用) |
| 填充位规则 | 固定每 5 个相同位插 1 个反相位 | 数据段可取消填充,由 CRC 奇偶校验替代 |
| 错误状态响应 | 无 ESI 位 | ESI 位指示发送节点是否处于被动错误 |
帧结构对比图
下面这张 SVG 把经典 CAN 和 CAN FD 的帧结构放在一起对比。左边是经典 CAN 数据帧,右边是 CAN FD 数据帧,差异字段用红色标出。你一眼就能看出控制场和数据场的变化。
避坑指南
我曾经在一个项目中,把 CAN FD 节点的 BRS 位置了 1,但收发器是普通的 CAN 收发器,结果总线直接报错。后来我查了 datasheet 才发现,必须用支持 CAN FD 变速的收发器(比如 TJA1044GT)才能让 BRS 生效。
说到填充位,CAN FD 在数据段可以取消填充。为什么?因为 CRC 覆盖了填充位计数(stuff-bit count),用奇偶校验替代了传统填充。这会减少数据段长度,但同时也要求 CAN 控制器加上填充位计数逻辑。嗯,这里要注意:如果你的 MCU 的 CAN FD 外设不支持这种 CRC 模式,记得把它关掉,否则会 CRC 错误。
我个人习惯在调试 CAN FD 通信时,先用示波器抓一下总线波形。重点看控制场里 EDL 和 BRS 的电平切换是否干净。如果边沿不陡,很可能是收发器速率切换太慢,这时候调一下收发器的 slew rate 参数能解决。