本帖最后由 艾那的小强 于 2025-9-17 12:10 编辑
硬汉哥,我使用咱们的例程,想要配置1M+5M的CANFD通讯波特率,但是始终无法成功。
你的例程是500K+2M的,测试确实可以,然后我修改为1M+2M也是可以的。但是无论是1M+4M,还是1M+5M,都没有测试成功。对于1M+5M,
测试方法是将CAN接到CAN分析仪上,CAN分析仪配置1M+5M,采样点分别为80%和75%。
在代码中,我尝试了如下几种配置,均没有成功。能指点我一下吗?
第一种:can_ker_clk配置为80MHz。CAN1和CAN2的时钟配置都修改了,修改为80MHz
[C] 纯文本查看 复制代码 //时钟配置部分,can_ker_clk 80MHz
PeriphClkInitStruct.PeriphClockSelection = RCC_PERIPHCLK_FDCAN;
PeriphClkInitStruct.PLL2.PLL2M = 5;
PeriphClkInitStruct.PLL2.PLL2N = 80;
PeriphClkInitStruct.PLL2.PLL2P = 2;
PeriphClkInitStruct.PLL2.PLL2Q = 5;
PeriphClkInitStruct.PLL2.PLL2R = 2;
PeriphClkInitStruct.PLL2.PLL2RGE = RCC_PLL2VCIRANGE_2;
PeriphClkInitStruct.PLL2.PLL2VCOSEL = RCC_PLL2VCOWIDE;
PeriphClkInitStruct.PLL2.PLL2FRACN = 0;
PeriphClkInitStruct.FdcanClockSelection = RCC_FDCANCLKSOURCE_PLL2;
//波特率设置部分
/*
配置仲裁阶段波特率
CAN时钟80MHz时,仲裁阶段的波特率就是
CAN FD Freq / (Sync_Seg + Pro_Seg + Phase_Seg1 + Phase_Seg2) = 80MHz / (1+63 + 16) = 1Mbps
其中Sync_Seg是固定值 = 1 , Pro_Seg + Phase_Seg1 = NominalTimeSeg1, Phase_Seg2 = NominalTimeSeg2
*/
hfdcan1.Init.NominalPrescaler = 0x01; /* CAN时钟分配设置,一般设置为1即可,全部由PLL配置好,tq = NominalPrescaler x (1/ fdcan_ker_ck), 范围1-512 */
hfdcan1.Init.NominalSyncJumpWidth = 0x10; /* 用于动态调节 Phase_Seg1和 Phase_Seg1,所以不可以比Phase_Seg1和 Phase_Seg1大,范围1-128 */
hfdcan1.Init.NominalTimeSeg1 = 0x3F; /* 特别注意这里的Seg1,这里是两个参数之和,对应位时间特性图的 Pro_Seg + Phase_Seg1,范围2-256 */
hfdcan1.Init.NominalTimeSeg2 = 0x10; /* 对应位时间特性图的 Phase_Seg2,范围2- 128 */
/*
配置数据阶段波特率
CAN时钟80MHz时,数据阶段的波特率就是
CAN FD Freq / (Sync_Seg + Pro_Seg + Phase_Seg1 + Phase_Seg2) = 80MHz / (1+11+ 4) = 5Mbps
其中Sync_Seg是固定值 = 1 , Pro_Seg + Phase_Seg1 = DataTimeSeg1, Phase_Seg2 = DataTimeSeg2
*/
hfdcan1.Init.DataPrescaler = 0x01; /* CAN时钟分配设置,一般设置为1即可,全部由PLL配置好,tq = NominalPrescaler x (1/ fdcan_ker_ck),范围1-32 */
hfdcan1.Init.DataSyncJumpWidth = 0x04; /* 用于动态调节 Phase_Seg1和 Phase_Seg1,所以不可以比Phase_Seg1和 Phase_Seg1大,范围1-16 */
hfdcan1.Init.DataTimeSeg1 = 0x0B; /* 特别注意这里的Seg1,这里是两个参数之和,对应位时间特性图的 Pro_Seg + Phase_Seg1,范围 */
hfdcan1.Init.DataTimeSeg2 = 0x04; /* 对应位时间特性图的 Phase_Seg2 */
第2种方案是can_ker_clk=20MHz,CAN1和CAN2的时钟配置都修改了,修改为20MHz
[C] 纯文本查看 复制代码 //时钟配置部分,can_ker_clk 20MHz
PeriphClkInitStruct.PeriphClockSelection = RCC_PERIPHCLK_FDCAN;
PeriphClkInitStruct.PLL2.PLL2M = 5;
PeriphClkInitStruct.PLL2.PLL2N = 80;
PeriphClkInitStruct.PLL2.PLL2P = 2;
PeriphClkInitStruct.PLL2.PLL2Q = 20;
PeriphClkInitStruct.PLL2.PLL2R = 2;
PeriphClkInitStruct.PLL2.PLL2RGE = RCC_PLL2VCIRANGE_2;
PeriphClkInitStruct.PLL2.PLL2VCOSEL = RCC_PLL2VCOWIDE;
PeriphClkInitStruct.PLL2.PLL2FRACN = 0;
PeriphClkInitStruct.FdcanClockSelection = RCC_FDCANCLKSOURCE_PLL2;
//波特率设置部分
/*
配置仲裁阶段波特率
CAN时钟20MHz时,仲裁阶段的波特率就是
CAN FD Freq / (Sync_Seg + Pro_Seg + Phase_Seg1 + Phase_Seg2) = 20MHz / (1+15 + 4) = 1Mbps
其中Sync_Seg是固定值 = 1 , Pro_Seg + Phase_Seg1 = NominalTimeSeg1, Phase_Seg2 = NominalTimeSeg2
*/
hfdcan1.Init.NominalPrescaler = 0x01; /* CAN时钟分配设置,一般设置为1即可,全部由PLL配置好,tq = NominalPrescaler x (1/ fdcan_ker_ck), 范围1-512 */
hfdcan1.Init.NominalSyncJumpWidth = 0x04; /* 用于动态调节 Phase_Seg1和 Phase_Seg1,所以不可以比Phase_Seg1和 Phase_Seg1大,范围1-128 */
hfdcan1.Init.NominalTimeSeg1 = 0x0F; /* 特别注意这里的Seg1,这里是两个参数之和,对应位时间特性图的 Pro_Seg + Phase_Seg1,范围2-256 */
hfdcan1.Init.NominalTimeSeg2 = 0x04; /* 对应位时间特性图的 Phase_Seg2,范围2- 128 */
/*
配置数据阶段波特率
CAN时钟20MHz时,数据阶段的波特率就是
CAN FD Freq / (Sync_Seg + Pro_Seg + Phase_Seg1 + Phase_Seg2) = 20MHz / (1+2+ 1) = 5Mbps
其中Sync_Seg是固定值 = 1 , Pro_Seg + Phase_Seg1 = DataTimeSeg1, Phase_Seg2 = DataTimeSeg2
*/
hfdcan1.Init.DataPrescaler = 0x01; /* CAN时钟分配设置,一般设置为1即可,全部由PLL配置好,tq = NominalPrescaler x (1/ fdcan_ker_ck),范围1-32 */
hfdcan1.Init.DataSyncJumpWidth = 0x01; /* 用于动态调节 Phase_Seg1和 Phase_Seg1,所以不可以比Phase_Seg1和 Phase_Seg1大,范围1-16 */
hfdcan1.Init.DataTimeSeg1 = 0x02; /* 特别注意这里的Seg1,这里是两个参数之和,对应位时间特性图的 Pro_Seg + Phase_Seg1,范围 */
hfdcan1.Init.DataTimeSeg2 = 0x01; /* 对应位时间特性图的 Phase_Seg2 */ |