CAN总线故障软件排查指南
背景描述
在机械臂的运行过程中,突然弹窗can总线错误,因为硬件排查需要一定的硬件知识以及一些额外工具,这里尝试从软件以及日志层面给大家讲一下排查步骤。
软件修复历程
上位机程序迭代的过程中,已经将实际使用测试过程中的软件bug基本都解决了,包括但不限于
- 数据通信阻塞
- can与canfd的自动检查
- 传输过大字节的报错问题
问题分类
这里将can总线错误弹窗的原因分为了几个板块
- 误操作问题
- 版本不适配问题
- 硬件问题
一、误操作问题
1.升级固件包之后,弹窗报错"CAN总线错误"
原本机械臂正常运行,因为要解决其他问题(比如报误碰撞、速度跑不满等问题),然后升级的固件,升级完报错的,这种一般都是上传的版本升级包不兼容导致的,建议直接回退固件版本保证机械臂运行,再与研发沟通是否升级以及版本选择。
二、版本不适配问题
前情提要
机械臂关节主控芯片的bootloder,在从v1.0.x到v1.1.x做过改善升级,但此升级导致固件版本升级时,无法直接从v1.0.x升级到v1.1.x版本。
涉及到的关节型号有:i系列所有型号关节、C系列所有型号关节、iH系列所有型号关节。
涉及到的底座型号有:丝印为 ROBOT POWER Board V1.2 ,使⽤的固件为base_i_C_h120-*.hex的底座。
解决方法:
- 使用jlink下载包含v1.1.x版本的bootloader固件包,然后再正常在线升级。
- 重新升级v1.0.x的固件,回到v1.0.x的版本。
相关日志输出
此时固件更新失败,日志会输出如下语句 
三、硬件问题
这里列举几个常见的硬件问题在日志中的体现
现象1
在机械臂运行过程中突然报“CAN总线硬件错误”,首先检查线缆是否连接完好,若完好,则大概率是CAN硬接线出了问题(机械摩擦松动或者高温导致胶松动等),在机械臂移动过程中导致can线不稳定。


现象2

这里可以看到6个关节全部报错,且工具板、基座板、机器人全部通信断开。 这种也是典型的硬件问题。
现象3
当机械臂线缆过长时,有概率报“can总线错误”,主要是因为信号延时以及不稳定。
现象4


这里可以看上电过程报了工具板找不到的error,这个也会导致报“can bus error”。
这里贴一张can线破损的图片

PS:关于硬件问题的解决,若现场有条件的话,可以按照can错误硬件排查手册进行先期硬件排查。若无条件,则安排返厂维修。
四、日志错误码分类及其解析
/// 错误码
#define ERR_OVER_CURRENT_BIT (((uint32_t)0x01) << 0) ///< 过流
#define ERR_OVER_VOLTAGE_BIT (((uint32_t)0x01) << 1) ///< 过压
#define ERR_OVER_TEMPRATURE_BIT (((uint32_t)0x01) << 2) ///< 过温
#define ERR_COMMUNICATION (((uint32_t)0x01) << 3) ///< 通信
#define ERR_LOW_VOLTAGE (((uint32_t)0x01) << 4) ///< 欠压
#define ERR_UVW_LOGIC_INVALID (((uint32_t)0x01) << 5) ///< UVW逻辑无效
#define ERR_UVW_ABZ_FAULT (((uint32_t)0x01) << 6) ///< ABZ相错误
#define ERR_ABS_ENC_COMM_FAULT (((uint32_t)0x01) << 7) ///< 绝对编码器错误
#define ERR_ADC_ZERO_OFFSET_FAULT (((uint32_t)0x01) << 8) ///< ADC零点偏移错误
#define ERR_ENC_POLLUTE (((uint32_t)0x01) << 9) ///< 编码器污染等级错误
#define ERR_ENC_Z_LOST (((uint32_t)0x01) << 10) ///< Z相丢失
#define ERR_ENC_CALI_FAULT (((uint32_t)0x01) << 11) ///< 编码器校准错误
#define ERR_IMU_FAULT (((uint32_t)0x01) << 12) ///< 惯性测量单元故障
#define ERR_IPM_NTC_FAULT (((uint32_t)0x01) << 13) ///< NTC故障
#define ERR_ABS_ENC_LOW_VOLT (((uint32_t)0x01) << 14) ///< 绝对编码器电压低
#define ERR_SHROT_CIRCUIT_FAULT (((uint32_t)0x01) << 15) ///< 短路故障
#define ERR_POS_OVER_LIMIT (((uint32_t)0x01) << 16) ///< 位置超限
#define ERR_MOTOR_STALL (((uint32_t)0x01) << 17) ///< 电机堵转
#define ERR_ABS_MT_FAULT (((uint32_t)0x01) << 18) ///< 绝对编码器多圈故障
#define ERR_MOTOR_PHASE_LOSE (((uint32_t)0x01) << 19) ///< 电机缺相
#define ERR_BRAKE_FAULT (((uint32_t)0x01) << 20) ///< 刹车故障
#define ERR_REDUCER_OVER_TEMP (((uint32_t)0x01) << 21) ///< 减速机过温
#define ERR_REDUCER_NTC_FAULT (((uint32_t)0x01) << 22) ///< 减速机NTC故障
#define ERR_FIRMWARE_UPDATE_FAULT (((uint32_t)0x01) << 23) ///< 固件升级错误
#define ERR_FLASH_OP_FAIL (((uint32_t)0x01) << 24) ///< FLASH操作故障
#define ERR_EXT_ABS_ENC_COMMFAULT \
(((uint32_t)0x01) << 25) ///< 减速器端编码器通信故障
#define ERR_BATTERY_LOW (((uint32_t)0x01) << 26) ///< battery low power
#define ERR_PHASE_ALIGN_FAIL (((uint32_t)0x01) << 27) ///< lock magnet pole
#define ERR_CAN_BUS (((uint32_t)0x01) << 28) ///< CAN硬件错误
#define ERR_POS_CMD (((uint32_t)0x01) << 29) ///< 位置指令不连续
#define ERR_POS_INIT (((uint32_t)0x01) << 30) ///< 位置初始化失败
#define ERR_TORQUE_SENSOR (((uint32_t)0x01) << 31) ///< 力矩传感器故障错误码使用举例说明
日志报错如下

日志这里输出错误码0x10000008,这里为16进制,我们转换为二进制,再对照错误码表

可以看到二进制下,第3个bit和第28bit的值为1(从0开始),即代表
- 通信问题
- CAN硬件错误
条件允许的话,可以拆开机械臂查看对应硬件是否有问题,否则建议返厂维修。