4. XCP on CAN的报文结构与标识符分配

XCP on CAN 的所有交互最终都落在标准 CAN 或 CAN FD 数据帧上。理解报文结构,核心是抓住两件事:一是每一帧的 8 字节(CAN FD 可更长)里,哪些字节属于 XCP 协议头、哪些属于数据;二是不同用途的报文如何分配 CAN ID,才能既满足实时性,又不把总线压垮。本节围绕命令、响应、事件、DAQ 四类报文展开,并给出一个多 ECU 台架的 CAN ID 分配表。

一、XCP 报文在 CAN 帧中的封装结构

XCP 帧的第一个字节是 PID(Packet Identifier),它决定了这一帧是命令、响应、事件还是 DAQ 数据。PID 的高 4 位表示包类型,低 4 位表示具体子类型或计数器。常见取值如下:

  • 0xC0~0xFF:命令包(CMD),主机(标定工具)发给 ECU。
  • 0x80~0xBF:响应包(RES),ECU 回给主机,其中 0xFF 表示肯定响应,0xFE 表示错误响应。
  • 0x00~0x3F:DAQ 数据包,低 4 位是 DAQ 列表编号或时间戳标志。
  • 0x40~0x7F:事件包(EV),ECU 主动上报,如错误、状态变化。

以 CAN 经典帧为例,一帧 8 字节的典型布局是:字节 0 为 PID,字节 1~7 为数据。对于命令包,字节 1 通常是命令码(如 0xF5 表示 SHORT_UPLOAD),后续字节是参数。对于 DAQ 包,字节 1 开始就是按 ODT 条目顺序排列的测量数据,没有额外命令码。CAN FD 下数据段可扩展到 64 字节,DAQ 包能一次携带更多信号,但 PID 仍占首字节。

判断一帧属于哪类报文,先看 PID 高 4 位:0xC 开头是命令,0x8 开头是响应,0x0~0x3 是 DAQ,0x4~0x7 是事件。这个规则在抓包分析时非常实用。

二、四类报文的 CAN ID 规划原则

CAN ID 不仅标识报文,还决定总线仲裁优先级:数值越小优先级越高。规划时通常遵循以下原则:

  1. 命令与响应:属于请求-应答式交互,实时性要求中等,但必须保证不丢。一般给每个 ECU 分配一对 ID,命令 ID 和响应 ID 相邻,便于识别。
  2. 事件报文:ECU 主动上报,发生频率低但重要,优先级应高于普通 DAQ,避免被大量数据帧阻塞。
  3. DAQ 报文:周期性或高速上传,数量最多、负载最大。应按采样率和重要性分层,高速 DAQ 用较小 ID,低速 DAQ 用较大 ID。
  4. 多 ECU 隔离:同一台架上多个 ECU 的 ID 段应划分清晰,避免冲突,也方便按 ECU 过滤抓包。

一个常用的做法是按 ID 区间分段:0x100~0x1FF 给 ECU1,0x200~0x2FF 给 ECU2,依此类推。每个 ECU 内部再细分:命令、响应、事件、DAQ 各占一小段。

三、多 ECU 台架 CAN ID 分配表示例

假设台架上有 3 个 ECU:ECU1 为电机控制器,ECU2 为电池管理,ECU3 为整车控制器。标定工具通过一个 CAN 接口同时连接三个 ECU。以下是一份可直接参考的分配表(示例参数,实际项目需按总线负载和实时性调整):

ECU报文类型CAN ID方向说明
ECU1命令 CMD0x101工具→ECU1标定命令、上传请求
ECU1响应 RES0x102ECU1→工具肯定/错误响应
ECU1事件 EV0x103ECU1→工具错误、状态变化
ECU1DAQ 高速0x110~0x11FECU1→工具电流、转速,1ms
ECU1DAQ 低速0x120~0x12FECU1→工具温度,10ms
ECU2命令 CMD0x201工具→ECU2标定命令
ECU2响应 RES0x202ECU2→工具响应
ECU2事件 EV0x203ECU2→工具过压、过温事件
ECU2DAQ 高速0x210~0x21FECU2→工具单体电压,10ms
ECU2DAQ 低速0x220~0x22FECU2→工具SOC,100ms
ECU3命令 CMD0x301工具→ECU3标定命令
ECU3响应 RES0x302ECU3→工具响应
ECU3事件 EV0x303ECU3→工具故障事件
ECU3DAQ 高速0x310~0x31FECU3→工具车速、踏板,10ms

注意:命令 ID 和响应 ID 成对出现,且命令 ID 略小于响应 ID,保证命令优先发出。事件 ID 紧跟在响应之后,优先级高于 DAQ。DAQ 段按速率分层,高速段 ID 更小。

四、总线负载评估

分配完 ID 后必须估算总线负载。CAN 经典帧一帧约 130 位(含仲裁、控制、数据和 CRC 等),在 500 kbps 下,一帧传输时间约 260 μs。若 ECU1 高速 DAQ 每 1 ms 发 4 帧,则每秒 4000 帧,占用时间约 4000×260 μs = 1.04 s,即单这一项就超过 100% 负载,显然不可行。因此需要调整:要么降低采样率,要么合并信号到更少的帧中,要么改用 CAN FD。

以 CAN FD 为例,数据段 64 字节时一帧约 500 位,在 2 Mbps 数据速率下传输时间约 250 μs,但一帧能携带 8 倍数据。若将 4 帧合并为 1 帧,每秒 1000 帧,占用约 0.25 s,负载降到 25%,就合理多了。实际评估时,把所有周期性报文(DAQ、事件)的帧数乘以单帧时间,再除以总线可用时间,得到总负载率。工程上建议控制在 50% 以下,留出余量给命令响应和突发事件。

负载评估不能只看平均帧数,还要考虑最坏情况:多个 ECU 同时发送高速 DAQ 时,仲裁和错误帧会进一步增加负载。建议在台架上用 CAN 分析仪实测总线负载率,再回头调整 ID 和采样周期。

五、配置与验证要点

在 ECU 侧配置 XCP 时,需要把上述 ID 写入 A2L 或 XCP 配置参数中,通常包括:CMD_ID、RES_ID、EV_ID、DAQ_ID 列表。每个 DAQ 列表对应一组 ID,工具端按相同配置解析。配置完成后,用标定工具连接,观察是否能正常收到响应和 DAQ 数据。若出现丢帧,优先检查 ID 是否冲突、DAQ 周期是否过短、总线负载是否过高。

下面这张图展示了多 ECU 台架中四类报文的 ID 分配与总线仲裁关系,帮助理解优先级和数据流向。

多 ECU 台架 XCP on CAN 报文 ID 分配与仲裁优先级 标定工具 CAN 接口 CAN 总线(仲裁:ID 越小优先级越高) ECU1 电机控制器 CMD 0x101 → 工具 RES 0x102 → 工具 EV 0x103 → 工具 DAQ 高速 0x110~0x11F DAQ 低速 0x120~0x12F 1ms / 10ms 分层 ECU2 电池管理 CMD 0x201 → 工具 RES 0x202 → 工具 EV 0x203 → 工具 DAQ 高速 0x210~0x21F DAQ 低速 0x220~0x22F 10ms / 100ms 分层 ECU3 整车控制器 CMD 0x301 → 工具 RES 0x302 → 工具 EV 0x303 → 工具 DAQ 高速 0x310~0x31F 10ms 周期 优先级顺序:事件 EV(0x103/0x203/0x303) > 命令 CMD > 响应 RES > 高速 DAQ > 低速 DAQ

从图中可以看出,三个 ECU 的 ID 段彼此隔离,每个 ECU 内部又按报文类型细分。事件报文 ID 最小,优先级最高,确保故障能及时上报;DAQ 报文按速率分层,高速段 ID 更小,低速段 ID 更大。实际配置时,把这张表直接映射到 A2L 的 XCP 参数和工具端的 DAQ 列表即可。验证阶段建议先用低速 DAQ 跑通,再逐步提高速率,同时用总线分析仪观察负载率,直到找到稳定且满足实时性的平衡点。