结论:Hyundai CAN FD safety 的「模式」不是一个开关,而是LKA/LFA × 纵向/非纵向 × 按钮格式 × SCC 来源的组合,每一组对应不同的 RX 检查表与 TX 白名单。纵向(LONG)只在 ALLOW_DEBUG 构建下生效:无该宏的构建强制 hyundai_longitudinal=false,因此上层设置 openpilotLongitudinalControl 不会自动改变固件事实。此外,替代转向地址是条件性接口不匹配,不能靠扩充普通插件的 CAN 发送权限来规避。
车型资格与总线编号:LKA 与 LFA 是两套拓扑
资格判定在 CarInterface._get_params():根据相机指纹判定 LKA/LFA,确定按钮、SCC 来源和 safetyParam。源文档特别强调,alphaLongitudinalAvailable、实际启用和 ECU 静默成功是三个不同状态,不能混为一谈。
总线编号由 CanBus.__init__() 决定,而且两种模式恰好相反:
| 模式 | A-CAN | E-CAN | 相机 |
|---|---|---|---|
| LKA | 0 | 1 | 2 |
| LFA | 1 | 0 | 2 |
相机总线固定为 2,再叠加多设备偏移。这里要注意:表中 bus 号是单个 panda safety 实例的本地编号,多 panda 场景的偏移由上层配置处理,不能把逻辑编号硬编码成自制板引脚。
模式与总线矩阵
hyundai_canfd_init() 用 LKA/LFA、LONG、替代按钮、相机 SCC 和替代转向地址选择 RX 检查与 TX 白名单。下面这张表是整篇的核心:
| 模式 | 动力总线 / 原车 SCC RX | 关键 TX 白名单 |
|---|---|---|
| LKA 非纵向 | 1 / 1 | 0x50+0x2A4 或替代 0x110+0x362 在 bus 0;0x1CF 在 bus 1 |
| LKA 纵向 | 1 / 不检查原车 SCC | LKA 0x50+0x2A4 在 bus 0;LFA、HUD、SCC、若干 ADRV 与 0x730 在 bus 1;0x51 在 bus 0 |
| LFA 雷达 SCC 非纵向 | 0 / 0 | LFA、HUD、0x1A0 在 bus 0;0x1CF 在 bus 2 |
| LFA 相机 SCC 非纵向 | 0 / 2 | 上行相同,另有 0x160 在 bus 0 |
| LFA 雷达 SCC 纵向 | 0 / 不检查原车 SCC | LFA、HUD、SCC、0x160、0x7D0 在 bus 0;0x1CF 在 bus 2 |
| LFA 相机 SCC 纵向 | 0 / 不检查原车 SCC | LFA、HUD、SCC、0x160 在 bus 0;0x1CF 在 bus 2 |
表头里的「原车 SCC RX」指的是 safety 必需 RX 检查与巡航状态消费,不是该总线上物理帧是否存在。几个细节:LKA 两种分支的按钮 RX 固定使用 0x1CF;LFA 分支依据替代按钮标志,选择动力总线上的 0x1CF 或 0x1AA。所有配置均监视油门备选组、制动 0x175、轮速 0xA0、驾驶员扭矩 0xEA——油门三种地址是同一检查组的备选格式,不等于三种都必须到达。
构建门:LONG 参数只在 ALLOW_DEBUG 下生效
hyundai_common_init() 只在 ALLOW_DEBUG 下读取 LONG 参数;无该宏的构建强制 hyundai_longitudinal=false。这是一道编译期门,而不是运行期开关。
校验侧码分布同样要记住:hyundai_canfd_get_counter() 对 8 字节普通按钮取字节 1 高四位的计数,其余帧取字节 2;校验值取前两字节。hyundai_common_canfd_compute_checksum() 对字节 2 起的载荷与地址执行 CRC16,24/32 字节分别异或长度常数。特别之处在于:按钮 RX 明确忽略 checksum,但仍检查计数。
权限与失效边界
这些边界在源文档里逐条列出,直接决定「白名单里有这帧」和「这帧会被执行」之间的差距:
- 按钮:普通按钮 TX 0x1CF 仅允许「原车巡航已接合时 Cancel」或「
controls_allowed时 Resume」。替代按钮 RX 0x1AA 不在 TX 白名单中;但设置替代按钮并不会从全部 TX 表删除 0x1CF,不能误写成「该模式彻底禁止发送任何按钮帧」。 - 转向:非纵向 LKA 对 0x50/0x110 检查扭矩;LKA 纵向及全部 LFA 对 0x12A 检查。共享扭矩门限制最大 270、实时变化 112、每帧增加 2/减少 3,并含驾驶员反扭矩与转向请求位节拍。
- SCC:非纵向 LFA 的 0x1A0 仅允许
ACCMode=4且aReqRaw/aReqValue同时为零;该钩子未逐位审核 0x1A0 的其它信号。 - 诊断与附属帧:0x730/0x7D0 的 8 字节数据仅可为
02 3E 80 00 00 00 00 00,且仅相应模式在白名单中。0x51、0x160、0x1EA、0x200、0x345、0x1DA、HUD 和相机抑制帧没有同等级的专属载荷校验。 - 转发:Hyundai CAN FD 没有专属
fwd钩子,使用通用 0↔2 转发规则及check_relay静态阻断;bus 1 不在该通用转发对内。
第 4 条尤其重要:白名单准入不等于 ECU 接受,也不等于 AEB 不受影响。缺少逐字段校验的帧,只能保证「被允许发送」,不能保证「被接受后效果正确」。
替代 LKA 与纵向的跨层组合
CarInterface._get_params() 可从相机指纹识别 0x110 替代 LKA,并把该标志传到 safety 参数;若有 ADAS ECU 且未被其他条件禁止,纵向能力仍可能开启。此时主机侧 create_steering_messages() 继续生成 0x110 LKAS_ALT,create_suppress_lfa() 继续生成 0x362。
但 hyundai_canfd_init() 的纵向 LKA 分支固定选择普通 0x50/0x2A4 白名单,而非按替代标志切换;原测试只有普通 LKA 纵向类,没有替代 LKA 纵向类。离线探针确认:同一替代标志加 LONG 后,调试构建拒绝 0x110/0x362、接受 0x50/0x2A4;无调试宏构建则忽略 LONG,采用非纵向替代 LKA 白名单。也就是说该组合在两类构建中的失败形态不同,均不能仅凭主机 CarParams 宣称纵向或替代转向可执行。
源文档对此的定性是关键:这是条件性接口不匹配,不应通过扩充普通插件的 CAN 发送权限来规避;正确做法是先确定该车型/纵向组合是否应被允许,再联合修订主机消息选择、固件白名单、转向限制和回归测试。现有 test_hyundai_canfd.py 在测试基座默认编译 ALLOW_DEBUG;本机运行该模块共 981 项、117 项跳过,跳过项及未覆盖的替代 LKA 纵向组合不能视为验证通过。
常见问题
LKA 和 LFA 的总线编号为什么会相反?
因为 CanBus.__init__() 明确按模式分配:LKA 时 A-CAN/E-CAN 为 0/1,LFA 时为 1/0,相机固定为 2。这是逻辑编号,多 panda 场景的偏移由上层配置处理,不能直接当作物理引脚。
启用纵向控制后,固件就一定允许吗?
不一定。hyundai_common_init() 只在 ALLOW_DEBUG 下读取 LONG 参数,无该宏的构建会强制 hyundai_longitudinal=false。所以上层设置 openpilotLongitudinalControl 不会自动改变固件事实,alphaLongitudinalAvailable、实际启用和 ECU 静默成功是不同状态。
0x1A0 在白名单里就可以自由发送吗?
不可以。非纵向 LFA 的 0x1A0 仅允许 ACCMode=4 且 aReqRaw/aReqValue 同时为零;纵向则分别调用共享加速度检查。而且该钩子并未逐位审核 0x1A0 的全部其它信号。
为什么设置「替代按钮」不等于禁用 0x1CF?
因为替代按钮 RX 0x1AA 虽不在 TX 白名单,但设置替代按钮并不会从全部 TX 表删除 0x1CF。现有 test_button_sends() 构造的是替代格式 0x1AA,因此没有证明 0x1CF 被禁用。
延伸阅读
- CAN 报文解析的「健康位」在说什么:校验、计数器与总线空窗 —— 与本文的 CRC16/计数与 RX 存活语义相互印证。
- 从使能到车轮:执行链上的八道门,以及它们各自不保证什么 —— 解释白名单准入为何不等于 ECU 接受。
- 同一个「转向灯」在三家车厂是三种实现:车辆状态归一化的坑 —— 承接 LKA/LFA 指纹与状态归一化。
- Hyundai 与 Honda 两条链的对照:安全模式为什么不能互借 —— 同一品牌不同平台的模式差异视角。
- 横向限幅的四种算法:主机候选与 panda 判决为什么不是一件事 —— 承接本文转向扭矩门的实现细节。
参考资料
- 项目 02 ——
openpilot-research/HYUNDAI_CANFD_PANDA_SAFETY_DEEP_DIVE.md(取用了模式与总线矩阵、构建门、权限与失效边界、替代 LKA 与纵向跨层组合)。 - 项目 02 ——
openpilot-research/CAR_PROTOCOL_IMPLEMENTATIONS.md(仅用于确认 Hyundai CAN FD 分支与set_safety_hooks()的注册位置)。
说明:本文为对固定源码快照的静态结构分析,未运行完整测试套件、未连接硬件、未验证目标车型的真实参数组合。文中所有阈值、行号索引与配置均出自源文档,标注为未验证的结论保留其原有边界。
更新记录
首次发布 2026-10-11 最近核对:2026-10-11
发表回复