STM32MP157C-DK2板FDCAN正常模式无法发送消息求助
STM32MP157 FDCAN正常模式发送失败(HAL_FDCAN_ERROR_FIFO_FULL)排查方案
针对你遇到的问题——外部回环模式正常,但正常模式下FDCAN发送失败并触发HAL_FDCAN_ERROR_FIFO_FULL错误,本质是消息一直滞留在发送FIFO中无法被发送出去,以下是具体排查和解决步骤:
1. 优先检查CAN总线硬件链路
回环模式不需要外部总线,所以能正常工作,但正常模式必须依赖完整的CAN总线硬件:
- 确认CAN收发器连接:STM32MP157的PA11/PA12是FDCAN1的RX/TX引脚,但这些引脚需要外接CAN收发芯片(如TJA1050)才能接入CAN总线。检查开发板上是否有对应的收发器电路,且引脚焊接/连接正确。
- 添加终端电阻:CAN总线两端必须接120Ω终端电阻,否则总线信号会发生反射,导致FDCAN控制器无法完成发送确认,消息持续滞留在FIFO中最终溢出。
- 验证收发器工作状态:检查收发器的供电引脚(如VCC)是否正常供电,待机引脚(如STBY)是否配置为工作模式(通常拉低或悬空),确保收发器未处于休眠状态。
2. 修正FDCAN波特率配置
你当前的波特率计算存在偏差,会导致总线通信不同步:
当前配置计算的波特率为:24MHz / (8*(3+20+3)) = 24MHz / 208 ≈ 115.4Kbps,和目标125Kbps不符。
修正后的配置(24MHz时钟下精确输出125Kbps):
hfdcan1.Init.NominalPrescaler = 6; hfdcan1.Init.NominalSyncJumpWidth = 3; hfdcan1.Init.NominalTimeSeg1 = 25; hfdcan1.Init.NominalTimeSeg2 = 4;
计算验证:24MHz / (6*(3+25+4)) = 24MHz / 192 = 125Kbps,完全匹配目标波特率。
3. 检查发送头TxHeader1的初始化
你未提供TxHeader1的配置代码,错误的发送头会导致消息无法被总线识别,确认以下配置:
FDCAN_TxHeaderTypeDef TxHeader1 = {0}; TxHeader1.Identifier = 0x123; // 设置合法的标准ID(按需修改) TxHeader1.IdType = FDCAN_STANDARD_ID; // 对应你配置的CLASSIC帧格式 TxHeader1.TxFrameType = FDCAN_DATA_FRAME; // 发送数据帧而非远程帧 TxHeader1.DataLength = FDCAN_DLC_BYTES_8; // 匹配你设置的TxElmtSize(8字节) TxHeader1.BitRateSwitch = FDCAN_BRS_OFF; // CLASSIC帧无需切换波特率 TxHeader1.FDFormat = FDCAN_CLASSIC_CAN; // 启用经典CAN格式
4. 增加发送状态监控与错误排查
- 发送前检查FDCAN控制器状态:
if(HAL_FDCAN_GetState(&hfdcan1) != HAL_FDCAN_STATE_READY) { // 控制器未就绪,排查初始化或硬件问题 Error_Handler(); }
- 轮询发送FIFO剩余空间,避免盲目添加消息:
if(HAL_FDCAN_GetTxFifoFreeLevel(&hfdcan1) == 0) { // FIFO已满,等待或排查发送失败原因 HAL_Delay(100); continue; }
- 获取详细错误码,定位问题根源:
uint32_t errorCode = HAL_FDCAN_GetError(&hfdcan1); if(errorCode != HAL_FDCAN_ERROR_NONE) { // 根据错误码排查:如HAL_FDCAN_ERROR_BUS(总线错误)、HAL_FDCAN_ERROR_ARBITRATION(仲裁丢失) Error_Handler(); }
5. 检查错误计数器与总线状态
如果FDCAN的发送错误计数器超过127,控制器会进入总线关闭状态,无法发送消息:
uint8_t txErrCnt = HAL_FDCAN_GetTxErrorCounter(&hfdcan1); uint8_t rxErrCnt = HAL_FDCAN_GetRxErrorCounter(&hfdcan1); if(txErrCnt >= 128 || rxErrCnt >= 128) { // 总线关闭,需要重置控制器 HAL_FDCAN_Reset(&hfdcan1); HAL_FDCAN_Start(&hfdcan1); }
内容的提问来源于stack exchange,提问作者Telmo
相关产品推荐
相关产品推荐

