解决STM32 CAN发送丢包问题

stm32 CAN发送丢包

多机组网的工况下stm32 CAN发送函数正常运行,数据更新,但是使用CAN抓包工具发现阶段性没数据,或者丢包等情况。

这种情况分两种;

  1. 发送太快,STM32集成的CAN控制器支持三个发送邮箱,但是一般的示例程序没有对邮箱的操作,默认使用邮箱0,发送太快导致邮箱占用过高导致丢包。

//Find an empty sending mailbox
	while (HAL_CAN_GetTxMailboxesFreeLevel(&CAN_H) == 0);	//If all three sender mailboxes are blocked, wait until one of them is free
	
	if ((CAN_H.Instance->TSR & CAN_TSR_TME0) != RESET) {
		//Check the status of sender mailbox 0. If mailbox 0 is idle, put the data to be sent into FIFO0
		TxMailbox = CAN_TX_MAILBOX0;
	} else if ((CAN_H.Instance->TSR & CAN_TSR_TME1) != RESET) {
		TxMailbox = CAN_TX_MAILBOX1;
	} else if ((CAN_H.Instance->TSR & CAN_TSR_TME2) != RESET) {
		TxMailbox = CAN_TX_MAILBOX2;
	}
	HAL_CAN_AddTxMessage(&CAN_H, &can_tx.tx_header, can_tx.data, &TxMailbox);	// Send response

用该方法来选择可用的邮箱发送。

对一些实时性要求高的情况“while (HAL_CAN_GetTxMailboxesFreeLevel(&CAN_H) == 0)”会有阻塞作用,可以选择依次按邮箱123来输入数据,大多情况也能解决丢包问题,总感觉这么操作有些不太合理,但的确没出过问题。

		static uint8_t mailbox_count = 0;

		if (mailbox_count== 0) {
			TxMailbox = CAN_TX_MAILBOX0;
		} else if (mailbox_count== 1) {
			TxMailbox = CAN_TX_MAILBOX1;
		} else if (mailbox_count== 2) {
			TxMailbox = CAN_TX_MAILBOX2;
			mailbox_count = 0;
		}
		mailbox_count++;
  1. 多主\从站组网,导致总线占用冲突,长时间会导致CAN外设丢掉老数据来发送新的数据,如果使用操作系统等发送可以在发送函数后增加一个延时一般1us就够,或者打开自动重发,根据实际情况选择其中一个方法即可。

image.png

物联沃分享整理
物联沃-IOTWORD物联网 » 解决STM32 CAN发送丢包问题

发表评论