芯旺微KF32A156芯片CANFD过滤配置
在调试KF32A156的CANFD功能,需要使用硬过滤来降低软件负荷,在配置CANFD全局掩码和MBx_MASK(邮箱专用掩码)时配到了一些小问题,特记录下来。
先来看看KF32A156用户手册中对CANFD全局掩码和邮箱专用掩码的描述:
以上描述说明了全局掩码和邮箱专用掩码共同决定着过滤的结果,因此参照官方例程,详细配置如下:
const uint32_t CAN_ID[51] = {
0x00,0x00,0x120,0x121,0x122,0x123,0x124,0x125,0x126,0x127,
0x128,0x129,0x130,0x131,0x132,0x133,0x134,0x135,0x136,0x137,
0x138,0x139,0x4F0,0x4F1,0x4F2,0x4F3,0x4F4,0x4F5,0x4F6,0x4F7,
0x4F8,0x4F9,0x500,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00
};
/**
* @brief :Receive Mailbox init
* @param in :Can_Controller_Index
* @param out :None
* @retval :None
*/
void Receive_Mailboxinit(const uint8_t Can_Controller_Index) {
volatile uint8_t retryTimes;
Canfd_ReturnType ret;
uint8_t receviemailbox = 0x00;
for (receviemailbox = 2; receviemailbox <= 35; receviemailbox++) {
Can_Receive_Mailbox_BUFFER[0].Id = CAN_ID[receviemailbox];
Can_Receive_Mailbox_BUFFER[0].Can_id = CAN_DATA_STANDARD;
Can_Receive_Mailbox_BUFFER[0].TransceiveType = MAIL_RECEIVE;
do{
ret = Can_m_FdMailBox_Write(Can_Controller_Index, receviemailbox,&Can_Receive_Mailbox_BUFFER[0]);
} while ((CAN_OK != ret) && ((retryTimes++) < CAN_RETRY_TIMES));
}
}
#if (HARDWARE_FILTER == STD_ON)
Can_HwFilterType Can_HwFilter = {
/* Filter 0 */
0x00000000U, /* Mask code */
/* Filter 1 */
0x00000000U, /* Mask code */
/* Filter 2 */
0x00000000U, /* Mask code */
/* Filter 3 */
0x00000000U, /* Mask code */
/* Filter 4 */
0x00000000U, /* Mask code */
/* Filter 5 */
0x00000000U, /* Mask code */
/* Filter 6 */
0x00000000U, /* Mask code */
/* Filter 7 */
0x00000000U, /* Mask code */
/* Filter 8 */
0x00000000U, /* Mask code */
/* Filter 9 */
0x00000000U, /* Mask code */
/* Filter 10 */
0x00000000U, /* Mask code */
/* Filter 11 */
0x00000000U, /* Mask code */
/* Filter 12 */
0x00000000U, /* Mask code */
/* Filter 13 */
0x00000000U, /* Mask code */
/* Filter 14 */
0x00000000U, /* Mask code */
/* Filter 15 */
0x00000000U, /* Mask code */
/* Filter 16 */
0x00000000U, /* Mask code */
/* Filter 17 */
0x00000000U, /* Mask code */
/* Filter 18 */
0x00000000U, /* Mask code */
/* Filter 19 */
0x00000000U, /* Mask code */
/* Filter 20 */
0x00000000U, /* Mask code */
/* Filter 21 */
0x00000000U, /* Mask code */
/* Filter 22 */
0x00000000U, /* Mask code */
/* Filter 23 */
0x00000000U, /* Mask code */
/* Filter 24 */
0x00000000U, /* Mask code */
/* Filter 25 */
0x00000000U, /* Mask code */
/* Filter 26 */
0x00000000U, /* Mask code */
/* Filter 27 */
0x00000000U, /* Mask code */
/* Filter 28 */
0x00000000U, /* Mask code */
/* Filter 29 */
0x00000000U, /* Mask code */
/* Filter 30 */
0x00000000U, /* Mask code */
/* Filter 31 */
0x00000000U, /* Mask code */
/* Filter 32 */
0x1FFFFFF8U, /* Mask code */
/* Filter 33 */
0x00000000U, /* Mask code */
/* Filter 34 */
0x00000000U, /* Mask code */
/* Filter 35 */
0x00000000U, /* Mask code */
/* Filter 36 */
0x00000000U, /* Mask code */
/* Filter 37 */
0x00000000U, /* Mask code */
/* Filter 38 */
0x00000000U, /* Mask code */
/* Filter 39 */
0x00000000U, /* Mask code */
/* Filter 40 */
0x00000000U, /* Mask code */
/* Filter 41 */
0x00000000U, /* Mask code */
/* Filter 42 */
0x00000000U, /* Mask code */
/* Filter 43 */
0x00000000U, /* Mask code */
/* Filter 44 */
0x00000000U, /* Mask code */
/* Filter 45 */
0x00000000U, /* Mask code */
/* Filter 46 */
0x00000000U, /* Mask code */
/* Filter 47 */
0x00000000U, /* Mask code */
/* Filter 48 */
0x00000000U, /* Mask code */
/* Filter 49 */
0x00000000U, /* Mask code */
/* Filter 50 */
0x00000000U, /* Mask code */
/* Filter 0 */
CAN_FILTER_STANDARD, /* Acceptance code type */
/* Filter 1 */
CAN_FILTER_STANDARD, /* Acceptance code type */
/* Filter 2 */
CAN_FILTER_STANDARD, /* Acceptance code type */
/* Filter 3 */
CAN_FILTER_STANDARD, /* Acceptance code type */
/* Filter 4 */
CAN_FILTER_STANDARD, /* Acceptance code type */
/* Filter 5 */
CAN_FILTER_STANDARD, /* Acceptance code type */
/* Filter 6 */
CAN_FILTER_STANDARD, /* Acceptance code type */
/* Filter 7 */
CAN_FILTER_STANDARD, /* Acceptance code type */
/* Filter 8 */
CAN_FILTER_STANDARD, /* Acceptance code type */
/* Filter 9 */
CAN_FILTER_STANDARD, /* Acceptance code type */
/* Filter 10 */
CAN_FILTER_STANDARD, /* Acceptance code type */
/* Filter 11 */
CAN_FILTER_STANDARD, /* Acceptance code type */
/* Filter 12 */
CAN_FILTER_STANDARD, /* Acceptance code type */
/* Filter 13 */
CAN_FILTER_STANDARD, /* Acceptance code type */
/* Filter 14 */
CAN_FILTER_STANDARD, /* Acceptance code type */
/* Filter 15 */
CAN_FILTER_STANDARD, /* Acceptance code type */
/* Filter 16 */
CAN_FILTER_STANDARD, /* Acceptance code type */
/* Filter 17 */
CAN_FILTER_STANDARD, /* Acceptance code type */
/* Filter 18 */
CAN_FILTER_STANDARD, /* Acceptance code type */
/* Filter 19 */
CAN_FILTER_STANDARD, /* Acceptance code type */
/* Filter 20 */
CAN_FILTER_STANDARD, /* Acceptance code type */
/* Filter 21 */
CAN_FILTER_STANDARD, /* Acceptance code type */
/* Filter 22 */
CAN_FILTER_STANDARD, /* Acceptance code type */
/* Filter 23 */
CAN_FILTER_STANDARD, /* Acceptance code type */
/* Filter 24 */
CAN_FILTER_STANDARD, /* Acceptance code type */
/* Filter 25 */
CAN_FILTER_STANDARD, /* Acceptance code type */
/* Filter 26 */
CAN_FILTER_STANDARD, /* Acceptance code type */
/* Filter 27 */
CAN_FILTER_STANDARD, /* Acceptance code type */
/* Filter 28 */
CAN_FILTER_STANDARD, /* Acceptance code type */
/* Filter 29 */
CAN_FILTER_STANDARD, /* Acceptance code type */
/* Filter 30 */
CAN_FILTER_STANDARD, /* Acceptance code type */
/* Filter 31 */
CAN_FILTER_STANDARD, /* Acceptance code type */
/* Filter 32 */
CAN_FILTER_STANDARD, /* Acceptance code type */
/* Filter 33 */
CAN_FILTER_STANDARD, /* Acceptance code type */
/* Filter 34 */
CAN_FILTER_STANDARD, /* Acceptance code type */
/* Filter 35 */
CAN_FILTER_STANDARD, /* Acceptance code type */
/* Filter 36 */
CAN_FILTER_STANDARD, /* Acceptance code type */
/* Filter 37 */
CAN_FILTER_STANDARD, /* Acceptance code type */
/* Filter 38 */
CAN_FILTER_STANDARD, /* Acceptance code type */
/* Filter 39 */
CAN_FILTER_STANDARD, /* Acceptance code type */
/* Filter 40 */
CAN_FILTER_STANDARD, /* Acceptance code type */
/* Filter 41 */
CAN_FILTER_STANDARD, /* Acceptance code type */
/* Filter 42 */
CAN_FILTER_STANDARD, /* Acceptance code type */
/* Filter 43 */
CAN_FILTER_STANDARD, /* Acceptance code type */
/* Filter 44 */
CAN_FILTER_STANDARD, /* Acceptance code type */
/* Filter 45 */
CAN_FILTER_STANDARD, /* Acceptance code type */
/* Filter 46 */
CAN_FILTER_STANDARD, /* Acceptance code type */
/* Filter 47 */
CAN_FILTER_STANDARD, /* Acceptance code type */
/* Filter 48 */
CAN_FILTER_STANDARD, /* Acceptance code type */
/* Filter 49 */
CAN_FILTER_STANDARD, /* Acceptance code type */
/* Filter 50 */
CAN_FILTER_STANDARD, /* Acceptance code type */
};
#endif
Canfd_ConfigType Canfd_Controller_AllConfig[1] = {
/* Can 0 Config */
{
/* Can controller Mode set
Value Range :
CANFD_NORMAL_MODE
CANFD_LOOP_INTERNAL_MODE
CANFD_LOOP_EXTERNAL_MODE
CANFD_SILENT_MODE */
CANFD_NORMAL_MODE,
/* Can FD Mode set
Value Range :
DISABLE
ENABLE */
ENABLE,
/* Can controller clock source set
Value Range :
CAN_CLOCKSOURCE_SCLK
CAN_CLOCKSOURCE_HFCLK
CAN_CLOCKSOURCE_LFCLK */
#if (WORKSOURCE_HFCLK == STD_ON)
CAN_CLOCKSOURCE_HFCLK,
#else
CAN_CLOCKSOURCE_SCLK,
#endif
/* Can controller Arbitrate clock source set
Value Range :
CAN_CLOCKSOURCE_SCLK
CAN_CLOCKSOURCE_HFCLK
CAN_CLOCKSOURCE_LFCLK */
CAN_CLOCKSOURCE_SCLK,
/* Mailbox block size config
Value Range :
CAN_8_BYTE_DATALENGTH :
CAN_16_BYTE_DATALENGTH :
CAN_32_BYTE_DATALENGTH :
CAN_64_BYTE_DATALENGTH : */
CAN_8_BYTE_DATALENGTH,
/* Iso mode or non-iso mode config
Value Range :
CAN_FD_NON_ISOMODE :
CAN_FD_ISOMODE : */
CAN_FD_ISOMODE,
/* Global Mask Set */
#if (HARDWARE_FILTER == STD_ON)
0x00000000,
#else
0xFFFFFFFF,
#endif
/* Enable/disable mailbox full receive config
Value Range :
CAN_MBFULLRECEIVE_DISABLE
CAN_MBFULLRECEIVE_ENABLE */
CAN_MBFULLRECEIVE_DISABLE,
/* Interrupt config */
&Can_Controller_InterruptConfig[0],
#if (HARDWARE_FILTER == STD_ON)
/* Hardware Filter config */
&Can_HwFilter,
#endif
/* Arbitrate Segment Baudrate Config */
&Canfd_Controller_AllClockAndBDRConfig[0],
/* Data Segment Baudrate Config */
&Canfd_Controller_ALLFdBDRConfig[0],
},
/* end */
};
自测发现,发送0x501,无法触发CANFD接收中断,修改报文ID为0x500,可以触发CANFD接收中断,说明ID是0x501报文被过滤掉了;在线调试时发现,查看初始化的代码发现如下函数中,当MBIndex是32时,MaskValue的值是0x1ffffff8,而fdMask.SFF.MASK的是0x7F8;
查看FdMask_Type的定义如下:
/* ----------------------------------------------------------------------------
-- 增强型控制器局域网总线(CANFD)
---------------------------------------------------------------------------- */
typedef union
{
volatile uint32_t MaskCode;
union
{
struct
{
uint32_t :21;
volatile uint32_t MASK :11;
} SFF;
struct
{
uint32_t :3;
volatile uint32_t MASK :29;
} EFF;
};
} FdMask_Type;
可以看出是低11位保存到了fdMask.SFF.MASK中(大小端的问题),修改如下进行验证是不是这个问题:
/* Filter 32 */
0x1FFFFF5AU, /* Mask code */
验证如下:
确定是这个问题后,做如下修改:
/* Filter 32 */
0xFFFFF8FFU, /* Mask code */ // 接收0x5xx的报文
经验证,终于实现了功能(能正常接收0x500~0x5FF的报文)。