STM32H7 CANFD过滤问题
最近在调试STM32H7的CANFD外设,通信调试都没有问题了,但是使用CANFD滤波进行ID过滤时出现问题了,CANFD的滤波视乎没有起到作用,总线上的任何一个ID都能收到,不知道有没有人研究过这个东西。使用官方提供的例程也是相同的问题,不能过滤CAN总线上的固定ID。有弄明白的大神没有,求赐教!!!!本帖最后由 oujisang 于 2019-1-11 11:03 编辑
代码上传上来了,需要的参考看看!!!
u8 FDCAN1_Mode_Init(u16 presc,u8 ntsjw,u16 ntsg1,u8 ntsg2,u32 mode)
{
FDCAN_FilterTypeDef FDCAN1_RXFilter;
//初始化FDCAN1
HAL_FDCAN_DeInit(&FDCAN1_Handler); //先清除以前的设置
FDCAN1_Handler.Instance=FDCAN1;
FDCAN1_Handler.Init.FrameFormat=FDCAN_FRAME_CLASSIC; //传统模式
FDCAN1_Handler.Init.Mode=mode; //回环测试
FDCAN1_Handler.Init.AutoRetransmission=DISABLE; //关闭自动重传!传统模式下一定要关闭!!!
FDCAN1_Handler.Init.TransmitPause=DISABLE; //关闭传输暂停
FDCAN1_Handler.Init.ProtocolException=DISABLE; //关闭协议异常处理
FDCAN1_Handler.Init.NominalPrescaler=presc; //分频系数
FDCAN1_Handler.Init.NominalSyncJumpWidth=ntsjw; //重新同步跳跃宽度
FDCAN1_Handler.Init.NominalTimeSeg1=ntsg1; //tsg1范围:2~256
FDCAN1_Handler.Init.NominalTimeSeg2=ntsg2; //tsg2范围:2~128
FDCAN1_Handler.Init.MessageRAMOffset=0; //信息RAM偏移
FDCAN1_Handler.Init.StdFiltersNbr=16; //标准信息ID滤波器编号
FDCAN1_Handler.Init.ExtFiltersNbr=16; //扩展信息ID滤波器编号
FDCAN1_Handler.Init.RxFifo0ElmtsNbr=1; //接收FIFO0元素编号
FDCAN1_Handler.Init.RxFifo0ElmtSize=FDCAN_DATA_BYTES_8; //接收FIFO0元素大小:8字节
FDCAN1_Handler.Init.RxBuffersNbr=1; //接收缓冲编号
FDCAN1_Handler.Init.RxBufferSize = FDCAN_DATA_BYTES_64;
FDCAN1_Handler.Init.TxEventsNbr=1; //发送事件编号
FDCAN1_Handler.Init.TxBuffersNbr=1; //发送缓冲编号
FDCAN1_Handler.Init.TxFifoQueueElmtsNbr=16; //发送FIFO序列元素编号
FDCAN1_Handler.Init.TxFifoQueueMode=FDCAN_TX_FIFO_OPERATION; //发送FIFO序列模式
FDCAN1_Handler.Init.TxElmtSize=FDCAN_DATA_BYTES_8; //发送大小:8字节
if(HAL_FDCAN_Init(&FDCAN1_Handler)!=HAL_OK) return 1; //初始化FDCAN
printf("Baudrate is %d \n",(200000/presc/(ntsg1+ntsg2+1)));
//配置RX滤波器
FDCAN1_RXFilter.IdType=FDCAN_STANDARD_ID; //标准ID
FDCAN1_RXFilter.FilterIndex=0; //滤波器索引
FDCAN1_RXFilter.FilterType=FDCAN_FILTER_RANGE; //滤波器类型
FDCAN1_RXFilter.FilterConfig=FDCAN_FILTER_TO_RXFIFO0; //过滤器0关联到FIFO0
FDCAN1_RXFilter.FilterID1=0x0012; //32位ID
FDCAN1_RXFilter.FilterID2=0x0012; //如果FDCAN配置为传统模式的话,这里是32位掩码
if(HAL_FDCAN_ConfigFilter(&FDCAN1_Handler,&FDCAN1_RXFilter)!=HAL_OK) return 2;//滤波器初始化
HAL_FDCAN_ConfigGlobalFilter(&FDCAN1_Handler,FDCAN_REJECT, FDCAN_REJECT, ENABLE, ENABLE);
HAL_FDCAN_Start(&FDCAN1_Handler); //开启FDCAN
HAL_FDCAN_ActivateNotification(&FDCAN1_Handler,FDCAN_IT_RX_FIFO0_NEW_MESSAGE,0);
//HAL_FDCAN_ActivateNotification(&FDCAN1_Handler, FDCAN_IT_TX_FIFO_EMPTY, 0);
return 0;
}
//FDCAN1底层驱动,引脚配置,时钟使能
//HAL_FDCAN_Init()调用
//hsdram:FDCAN1句柄
void HAL_FDCAN_MspInit(FDCAN_HandleTypeDef* hfdcan)
{
GPIO_InitTypeDef GPIO_Initure;
RCC_PeriphCLKInitTypeDef FDCAN_PeriphClk;
__HAL_RCC_FDCAN_CLK_ENABLE(); //使能FDCAN1时钟
__HAL_RCC_GPIOA_CLK_ENABLE(); //开启GPIOA时钟
//FDCAN1时钟源配置为PLL1Q
FDCAN_PeriphClk.PeriphClockSelection=RCC_PERIPHCLK_FDCAN;
FDCAN_PeriphClk.FdcanClockSelection=RCC_FDCANCLKSOURCE_PLL;
HAL_RCCEx_PeriphCLKConfig(&FDCAN_PeriphClk);
GPIO_Initure.Pin=GPIO_PIN_11|GPIO_PIN_12; //PA11,12
GPIO_Initure.Mode=GPIO_MODE_AF_PP; //推挽复用
GPIO_Initure.Pull=GPIO_PULLUP; //上拉
GPIO_Initure.Speed=GPIO_SPEED_FREQ_MEDIUM; //超高速
GPIO_Initure.Alternate=GPIO_AF9_FDCAN1; //复用为CAN1
HAL_GPIO_Init(GPIOA,&GPIO_Initure); //初始化
#if FDCAN1_RX0_INT_ENABLE
HAL_NVIC_SetPriority(FDCAN1_IT0_IRQn,1,2);
HAL_NVIC_EnableIRQ(FDCAN1_IT0_IRQn);
#endif
}
//此函数会被HAL_FDCAN_DeInit调用
//hfdcan:fdcan句柄
void HAL_FDCAN_MspDeInit(FDCAN_HandleTypeDef* hfdcan)
{
__HAL_RCC_FDCAN_FORCE_RESET(); //复位FDCAN1
__HAL_RCC_FDCAN_RELEASE_RESET(); //停止复位
#if FDCAN1_RX0_INT_ENABLE
HAL_NVIC_DisableIRQ(FDCAN1_IT0_IRQn);
#endif
}
//can发送一组数据(固定格式:ID为0X12,标准帧,数据帧)
//len:数据长度(最大为8),可设置为FDCAN_DLC_BYTES_2~FDCAN_DLC_BYTES_8
//msg:数据指针,最大为8个字节.
//返回值:0,成功;
// 其他,失败;
u8 FDCAN1_Send_Msg(u8* msg,u32 len)
{
FDCAN1_TxHeader.Identifier=0x0012; //32位ID
FDCAN1_TxHeader.IdType=FDCAN_STANDARD_ID; //标准ID
FDCAN1_TxHeader.TxFrameType=FDCAN_DATA_FRAME; //数据帧
FDCAN1_TxHeader.DataLength=len; //数据长度
FDCAN1_TxHeader.ErrorStateIndicator=FDCAN_ESI_ACTIVE;
FDCAN1_TxHeader.BitRateSwitch=FDCAN_BRS_OFF; //关闭速率切换
FDCAN1_TxHeader.FDFormat=FDCAN_CLASSIC_CAN; //传统的CAN模式
FDCAN1_TxHeader.TxEventFifoControl=FDCAN_NO_TX_EVENTS; //无发送事件
FDCAN1_TxHeader.MessageMarker=0;
if(HAL_FDCAN_AddMessageToTxFifoQ(&FDCAN1_Handler,&FDCAN1_TxHeader,msg)!=HAL_OK)
{
printf("Send massage error!\n");
return 1;//发送
}
printf("Send massage success!\n");
return 0;
}
//can口接收数据查询
//buf:数据缓存区;
//返回值:0,无数据被收到;
// 其他,接收的数据长度;
u8 FDCAN1_Receive_Msg(u8 *buf)
{
if(HAL_FDCAN_GetRxMessage(&FDCAN1_Handler,FDCAN_RX_FIFO0,&FDCAN1_RxHeader,buf)!=HAL_OK)return 0;//接收数据
return FDCAN1_RxHeader.DataLength>>16;
}
#if FDCAN1_RX0_INT_ENABLE
//FDCAN1中断服务函数
void FDCAN1_IT0_IRQHandler(void)
{
HAL_FDCAN_IRQHandler(&FDCAN1_Handler);
}
//FIFO0回调函数
void HAL_FDCAN_RxFifo0Callback(FDCAN_HandleTypeDef *hfdcan, uint32_t RxFifo0ITs)
{
u8 i=0;
u8 rxdata;
if((RxFifo0ITs&FDCAN_IT_RX_FIFO0_NEW_MESSAGE)!=RESET) //FIFO1新数据中断
{
//提取FIFO0中接收到的数据
HAL_FDCAN_GetRxMessage(hfdcan,FDCAN_RX_FIFO0,&FDCAN1_RxHeader,rxdata);
printf("id:%#x\r\n",FDCAN1_RxHeader.Identifier);
printf("len:%d\r\n",FDCAN1_RxHeader.DataLength>>16);
for(i=0;i<8;i++)
printf("rxdata[%d]:%02x\r\n",i,rxdata);
HAL_FDCAN_ActivateNotification(hfdcan,FDCAN_IT_RX_FIFO0_NEW_MESSAGE,0);
}
}
#endif
帮我看看吧
u8 FDCAN1_Mode_Init(u8 tnsjw,u16 tseg1,u8 tseg2,u16 tnbrp,u8 mode)
{
FDCAN_ClkCalUnitTypeDef FDCAN1_ClkCalUnit;
FDCAN_FilterTypeDef FDCAN1_RXFilter;
//初始化FDCAN1
HAL_FDCAN_DeInit(&FDCAN1_Handler); //先清除以前的设置
FDCAN1_Handler.Instance = FDCAN1;
FDCAN1_Handler.Init.FrameFormat = FDCAN_FRAME_FD_BRS; //传统模式
FDCAN1_Handler.Init.Mode = mode; //模式设置
FDCAN1_Handler.Init.AutoRetransmission = ENABLE;//DISABLE; //关闭自动重传!传统模式下一定要关闭!!!
FDCAN1_Handler.Init.TransmitPause = DISABLE; //关闭传输暂停
FDCAN1_Handler.Init.ProtocolException = ENABLE;//DISABLE; //关闭协议异常处理
//FDCAN的Nominal波特率
//FDCAN_NBTP
FDCAN1_Handler.Init.NominalPrescaler = tnbrp; //分频系数 5
FDCAN1_Handler.Init.NominalSyncJumpWidth = tnsjw; //重新同步跳跃宽度范围:2~1288
FDCAN1_Handler.Init.NominalTimeSeg1 = tseg1; //tseg1范围:2~256 8
FDCAN1_Handler.Init.NominalTimeSeg2 = tseg2; //tseg2范围:2~128 11
FDCAN1_Handler.Init.MessageRAMOffset = 0; //信息RAM偏移
//FDCAN的波特率Data波特率
//FDCAN_DBTP
FDCAN1_Handler.Init.DataPrescaler = 0x1;
FDCAN1_Handler.Init.DataSyncJumpWidth = 0x4;
FDCAN1_Handler.Init.DataTimeSeg1 = 0x5; // DataTimeSeg1 = Propagation_segment + Phase_segment_1 //
FDCAN1_Handler.Init.DataTimeSeg2 = 0x4;
FDCAN1_Handler.Init.StdFiltersNbr = 1; //标准信息ID滤波器编号
FDCAN1_Handler.Init.ExtFiltersNbr = 1; //扩展信息ID滤波器编号
FDCAN1_Handler.Init.RxFifo0ElmtsNbr = 1; //接收FIFO0元素编号
FDCAN1_Handler.Init.RxFifo0ElmtSize = FDCAN_DATA_BYTES_8; //接收FIFO0元素大小:8字节
FDCAN1_Handler.Init.RxFifo1ElmtsNbr = 2;
FDCAN1_Handler.Init.RxFifo1ElmtSize = FDCAN_DATA_BYTES_8;
FDCAN1_Handler.Init.RxBuffersNbr = 1;
FDCAN1_Handler.Init.RxBufferSize = FDCAN_DATA_BYTES_8; //接收缓冲编号
FDCAN1_Handler.Init.TxEventsNbr = 2; //发送事件编号
FDCAN1_Handler.Init.TxBuffersNbr = 1; //发送缓冲编号
FDCAN1_Handler.Init.TxFifoQueueElmtsNbr = 2; //发送FIFO序列元素编号
FDCAN1_Handler.Init.TxFifoQueueMode = FDCAN_TX_FIFO_OPERATION; //发送FIFO序列模式
FDCAN1_Handler.Init.TxElmtSize = FDCAN_DATA_BYTES_8; //发送大小:8字节
HAL_FDCAN_Init(&FDCAN1_Handler);
FDCAN1_ClkCalUnit.ClockCalibration = DISABLE; //不使用时钟校准功能
//FDCAN_CLOCK_DIV10 10分频,得到20Mhz的fdca_tq_ck
//FDCAN_CLOCK_DIV4 4分频,得到50Mhz的fdca_tq_ck
FDCAN1_ClkCalUnit.ClockDivider = FDCAN_CLOCK_DIV10;
HAL_FDCAN_ConfigClockCalibration(&FDCAN1_Handler,&FDCAN1_ClkCalUnit); //设置分频
//配置RX滤波器
FDCAN1_RXFilter.IdType = FDCAN_STANDARD_ID; //标准ID
FDCAN1_RXFilter.FilterIndex = 0; //滤波器索引
//滤波器类型
//FDCAN_FILTER_RANGE Range filter from FilterID1 to FilterID2
//FDCAN_FILTER_DUAL Dual ID filter for FilterID1 or FilterID2
//FDCAN_FILTER_MASK Classic filter: FilterID1 = filter, FilterID2 = mask
//FDCAN_FILTER_RANGE_NO_EIDM Range filter from FilterID1 to FilterID2, EIDM mask not applied
FDCAN1_RXFilter.FilterType = FDCAN_FILTER_DUAL;
FDCAN1_RXFilter.FilterConfig =FDCAN_FILTER_TO_RXFIFO0;//FDCAN_FILTER_TO_RXBUFFER;////过滤器0关联到FIFO0
FDCAN1_RXFilter.FilterID1 = 0x0543; //32位ID
FDCAN1_RXFilter.FilterID2 = 0x07ff; //如果FDCAN配置为传统模式的话,这里是32位掩码
FDCAN1_RXFilter.RxBufferIndex = 0;
HAL_FDCAN_ConfigFilter(&FDCAN1_Handler,&FDCAN1_RXFilter);
HAL_FDCAN_ConfigGlobalFilter(&FDCAN1_Handler, FDCAN_ACCEPT_IN_RX_FIFO0, FDCAN_ACCEPT_IN_RX_FIFO0, ENABLE, ENABLE);
// // Configure extended ID reception filter to Rx FIFO 1
// FDCAN1_RXFilter.IdType = FDCAN_STANDARD_ID;
// FDCAN1_RXFilter.FilterIndex = 0;
// FDCAN1_RXFilter.FilterType = FDCAN_FILTER_DUAL;
// FDCAN1_RXFilter.FilterConfig = FDCAN_FILTER_TO_RXFIFO1;//FDCAN_FILTER_TO_RXBUFFER;//
// FDCAN1_RXFilter.FilterID1 = 0x0643;
// FDCAN1_RXFilter.FilterID2 = 0x07ff;
// HAL_FDCAN_ConfigFilter(&FDCAN1_Handler, &FDCAN1_RXFilter);
//
// HAL_FDCAN_ConfigGlobalFilter(&FDCAN1_Handler, FDCAN_ACCEPT_IN_RX_FIFO0, FDCAN_ACCEPT_IN_RX_FIFO0, ENABLE, ENABLE);
HAL_FDCAN_Start(&FDCAN1_Handler); //开启FDCAN
HAL_FDCAN_ActivateNotification(&FDCAN1_Handler,FDCAN_IT_RX_FIFO0_NEW_MESSAGE,0);//Enable interrupts.
return 0;
} 解决了!!官方历程里没有调用滤波全局设置,只是配置了一个滤波组设置,一直以为滤波组设置完就可以了,调用滤波全局设置一下就可以了。 您好 我的怎么没有反应 标准模式 pb12 pb13 没反应
可否给看一下 德华 发表于 2018-10-5 23:17
可否给看一下
先做一下回环自测模式,看看能完成收发不。 丢出你的代码,让大家学习一下? stm1024 发表于 2018-10-7 18:19
丢出你的代码,让大家学习一下?
好!!明天上班 我把代码传上来,让大家遇到问题提供参考! 感謝, 下載看一下
希望這個driver 可以用吧 我现在可以发送不能接收不知道什么原因求赐教 本帖最后由 oujisang 于 2018-12-7 13:50 编辑
你怎么知道你能发送不能接收?是不是你板子发送数据有问题,先用电脑的CANFD盒子接收板子发送的数据,先解决板子发送数据没有问题,你先找个能调试CANFD的盒子,检查一下看看你板子发送的东西对不对,用示波器测试波形看不出问题,然后在用CAN盒子发送数据板子接收这样一步一步调试才能知道问题在哪里。 jasoncheungb2 发表于 2018-11-29 11:39
希望這個driver 可以用吧
项目验证过的,可以用! 无法正确解压缩,文件损坏 本帖最后由 oujisang 于 2019-1-11 11:03 编辑
cxj16888 发表于 2018-12-8 20:46
无法正确解压缩,文件损坏
我重新下载解压了一下,没问题,应该是你下载过程中出问题了!