STM32F103 CAN通讯注意事项:
- stm32有3个发送邮箱 2个三级深度的接受FIFO
- 发送数据注意事项:
- 需要首先设置CanTxMsg结构体,每次最多发送8个字节数据
- 之后调用CAN_Transmit(CANx, &TxMessage);函数真正发送,同时可以根据返回值判断是否发送成功
- 接收数据注意事项
- 接收需要调用
void CAN_Receive(CAN_TypeDef* CANx, uint8_t FIFONumber, CanRxMsg* RxMessage);'
从接收FIFO中提取数据,每从FIFO中提出一个数据之后会释放一次空间,但是这里特别注意,当FIFO为空的时候,也就是说FIFO中的数据被你提出来过了,然后再去提取,还是可以提取到同样的数据,因此大家写程序的时候一定不要把CAN_Receive
丢到while(1)
里面去做循环,哪怕是循环也要加上标志位 - 接收可根据CanRxMSg结构体判断接收到的can数据包的ID等
3.过滤器配置
static void CAN_Filter_Config(void)
{
CAN_FilterInitTypeDef CAN_FilterInitStructure;
/*CAN筛选器初始化*/
CAN_FilterInitStructure.CAN_FilterNumber=0; //筛选器组0
CAN_FilterInitStructure.CAN_FilterMode=CAN_FilterMode_IdMask; //工作在掩码模式
CAN_FilterInitStructure.CAN_FilterScale=CAN_FilterScale_32bit; //筛选器位宽为单个32位。
/* 使能筛选器,按照标志的内容进行比对筛选,扩展ID不是如下的就抛弃掉,是的话,会存入FIFO0。 */
CAN_FilterInitStructure.CAN_FilterIdHigh= ((((u32)0x1314<<3)|CAN_ID_EXT|CAN_RTR_DATA)&0xFFFF0000)>>16; //要筛选的ID高位
CAN_FilterInitStructure.CAN_FilterIdLow= (((u32)0x1314<<3)|CAN_ID_EXT|CAN_RTR_DATA)&0xFFFF; //要筛选的ID低位
CAN_FilterInitStructure.CAN_FilterMaskIdHigh= 0xFFFF; //筛选器高16位每位必须匹配
CAN_FilterInitStructure.CAN_FilterMaskIdLow= 0xFFFF; //筛选器低16位每位必须匹配
CAN_FilterInitStructure.CAN_FilterFIFOAssignment=CAN_Filter_FIFO0 ; //筛选器被关联到FIFO0
CAN_FilterInitStructure.CAN_FilterActivation=ENABLE; //使能筛选器
CAN_FilterInit(&CAN_FilterInitStructure);
/*CAN通信中断使能*/
CAN_ITConfig(CANx, CAN_IT_FMP0, ENABLE);
}
重点注意:
CAN_FilterInitStructure.CAN_FilterMode=CAN_FilterMode_IdMask; //工作在掩码模式
CAN_FilterInitStructure.CAN_FilterScale=CAN_FilterScale_32bit; //筛选器位宽为单个32位。
/* 使能筛选器,按照标志的内容进行比对筛选,扩展ID不是如下的就抛弃掉,是的话,会存入FIFO0。 */
CAN_FilterInitStructure.CAN_FilterIdHigh= ((((u32)0x1314<<3)|CAN_ID_EXT|CAN_RTR_DATA)&0xFFFF0000)>>16; //要筛选的ID高位
CAN_FilterInitStructure.CAN_FilterIdLow= (((u32)0x1314<<3)|CAN_ID_EXT|CAN_RTR_DATA)&0xFFFF; //要筛选的ID低位
为什么要这么弄,看下图!!!