各位佬们请教下CAN通讯发送失败卡死的问题
本帖最后由 T-Rex1000 于 2024-8-12 15:28 编辑void CAN_Transimit(uint16_t CAN_ID,uint8_t* datas,uint8_t len)
{
uint16_t CanID;
uint8 RX_Index=0,i=0;
uint8_t sr;
if(CAN_Init_finish)
{
sr=CanReadReg(SR);
if(sr&0x01)
{
CANAR=MR;
CANDR&=~0x04;
}
else
{
CanID = CAN_ID << 5;
CanWriteReg(TX_BUF0,len); //标准帧, 数据帧, bit3~bit0: 数据长度(DLC)
CanWriteReg(TX_BUF1,(uint8_t)(CanID>>8));
CanWriteReg(TX_BUF2,(uint8_t)CanID);
RX_Index = 3;
for(i=0;i<len;i++) //数据长度为DLC,最多不超过8
{
CanWriteReg((uint8_t)(TX_BUF0 + (RX_Index++&3)),datas); //写入有效数据
}
while(RX_Index&3) //判断已读数据长度是否4的整数倍
{
//写入填充数据,一帧数据占据4的整数倍缓冲区空间,不足补0
CanWriteReg((uint8_t)(TX_BUF0 + (RX_Index++&3)),0x00);
}
CanWriteReg(CMR,0x04); //发起一次帧传输
B_Can1Send = 1; //设置CAN1发送忙标志
}
}
}
本帖最后由 T-Rex1000 于 2024-8-12 15:32 编辑
想问下各位佬为什么我每次发送都有清除错误寄存器,但只要出现通讯失败就还是不能恢复通讯,而且会占用其他中断还有主线程的资源导致卡顿
void CANBUS_Interrupt(void) interrupt 28
{
uint16_t CAN_ID=0x0000;
uint8_t isr;
isr = CanReadReg(ISR);
if((isr & 0x04) == 0x04)
{
CANAR = 0x03;
CANDR = 0x04; //CLR FLAG
}
if((isr & 0x08) == 0x08)
{
CANAR = 0x03;
CANDR = 0x08; //CLR FLAG
//CAN_ID = CanReadMsg(RX_BUF); //接收 CAN 总线数据
//CAN_Transimit(CAN_ID+1,RX_BUF,8); //CANID 加 1,原样发送 CAN 总线数据
}
}
你的中断里面只处理了CAN收发完成中断标志,没有处理错误中断标志。
如果开启了CAN总线错误中断,产生错误中断后没进行处理的话,就会反复触发中断,从而占用大量系统资源。
参考STC32G实验箱例程包或者屠龙刀例程包里面的CAN总线例子,对所有已使能的中断标志进行处理。
CAN通信调试需要总线上有2个以上节点才能正常进行收发通信,如果没有另外一个节点进行应答的话发送就会产生总线错误,一旦错误次数超过255就会触发BUS-OFF,导致当前节点无法再进行收发。清除 Reset Mode,从BUS-OFF状态退出后才能恢复通信功能。
乘风飞扬 发表于 2024-8-13 09:27
你的中断里面只处理了CAN收发完成中断标志,没有处理错误中断标志。
如果开启了CAN总线错误中断,产生错误 ...
好的谢谢,我找时间试试
页:
[1]