历史上的今天
返回首页

历史上的今天

今天是:2025年08月21日(星期四)

正在发生

2018年08月21日 | STM32系统时钟 CAN UART

2018-08-21 来源:eefocus

在调试USB-CAN的适配器的过程中,采用库函数开发,在调试串口的过程中串口数据始终乱码。


思考一番,发现由于外部晶振的原因,在 Keil 中Ctrl + Shift + F 查找 HSE_VALUE:



#if !defined  HSE_VALUE

 #ifdef STM32F10X_CL   

  #define HSE_VALUE    ((uint32_t)25000000) /*!< Value of the External oscillator in Hz */

 #else 

  #define HSE_VALUE    ((uint32_t)8000000) /*!< Value of the External oscillator in Hz */

 #endif /* STM32F10X_CL */

#endif /* HSE_VALUE */

由于我采用的是12M的晶振,所以将 8000000 改为 12000000,程序测试通过;



接下来调试CAN总线,程序在自己做的 两个 USB-CAN适配器间 CAN通信测试通过,


但是接上公司买来的 USB-CAN适配器 ,数据始终不成功,双方收发一点反应都没有。




这是为什么,买来的 USB-CAN适配器 是没问题的,我自己做的 USB-CAN适配器 在两个CAN网络间也可以通信,


说明我的 USB-CAN适配器 大体是没什么问题的,由于初次调试 CAN 总线,问题出在哪里, 也没什么思路。




最后把情况反馈给  公司所买 USB-CAN适配器 的卖家,卖家人很好,他推测是CAN总线间波特率的问题。




是这个原因吗?  STM32的CAN时钟。在SystemInit()函数中的SetSysClock()



#elif defined SYSCLK_FREQ_72MHz

  SetSysClockTo72();

SetSysClockTo72() 将系统倍频到 72M ,



    /* HCLK = SYSCLK */

    RCC->CFGR |= (uint32_t)RCC_CFGR_HPRE_DIV1;

      

    /* PCLK2 = HCLK */

    RCC->CFGR |= (uint32_t)RCC_CFGR_PPRE2_DIV1;

    

    /* PCLK1 = HCLK / 2 */

    RCC->CFGR |= (uint32_t)RCC_CFGR_PPRE1_DIV2;


CAN时钟选采用的是PCLK1时钟,为SYSCLK的一半,即是36M,




但是CAN波特率配置是按照 36M的时钟来配置的,为什么还会不成功呢。



void CAN_StructInit_Init(void) 

{

CAN_InitTypeDef        CAN_InitStructure;

 

CAN_StructInit(&CAN_InitStructure);

/* CAN cell init */

CAN_InitStructure.CAN_TTCM=DISABLE;//禁止时间触发通信模式

CAN_InitStructure.CAN_ABOM=DISABLE;//DISABLE;//软件对CAN_MCR寄存器的INRQ位进行置1随后清0后,一旦硬件检测到128次11                                             位连续的隐性位,就退出离线状态。 

CAN_InitStructure.CAN_AWUM=DISABLE;//睡眠模式通过清除CAN_MCR寄存器的SLEEP位,由软件唤醒

CAN_InitStructure.CAN_NART=ENABLE;//////DISABLE;CAN报文只被发送1次,不管发送的结果如何(成功、出错或仲裁丢失) 

CAN_InitStructure.CAN_RFLM=DISABLE;//在接收溢出时FIFO未被锁定,当接收FIFO的报文未被读出,下一个收到的报文会                                       覆盖原有的报文  

CAN_InitStructure.CAN_TXFP=DISABLE;//发送FIFO优先级由报文的标识符来决定

CAN_InitStructure.CAN_Mode=CAN_Mode_Normal; //CAN硬件工作在正常模式 

 

CAN_InitStructure.CAN_SJW=CAN_SJW_1tq;//重新同步跳跃宽度1个时间单位

CAN_InitStructure.CAN_BS1=CAN_BS1_3tq;//时间段1为8个时间单位

CAN_InitStructure.CAN_BS2=CAN_BS2_2tq;//时间段2为3个时间单位

CAN_InitStructure.CAN_Prescaler=12;//(pclk1/((1+3+2)*12)) = 36Mhz/6/12 = 0.5Mbits设定了一个时间单位的长度12

CAN_Init(CAN1, &CAN_InitStructure);

}


反复思考,各种怀疑,最后发现是系统倍频至 72M的时候出了问题,


#else    

    /*  PLL configuration: PLLCLK = HSE * 9 = 72 MHz */

    RCC->CFGR &= (uint32_t)((uint32_t)~(RCC_CFGR_PLLSRC | RCC_CFGR_PLLXTPRE |

                                        RCC_CFGR_PLLMULL));

    RCC->CFGR |= (uint32_t)(RCC_CFGR_PLLSRC_HSE | RCC_CFGR_PLLMULL9); ////////////////////////////////

#endif /* STM32F10X_CL */


SetSysClockTo72() 里面的赫然是RCC_CFGR_PLLMULL9,我晕。

果断改为RCC_CFGR_PLLMULL6。


为什么库函数 SetSysClockTo72()  这么不不完善,就不能根据外部晶振参数 HSE_VALUE 来倍频吗?


这样局限只能是8M的晶振,在采用8M以外的晶振的时候,一定要注意这个问题。


也怪自己太过于相信库函数了。




一直没怀疑系统倍频 72M的原因也是因为我的串口采用的STM32的串口2,


为什么同是APB1时钟PCLK1,串口能正常工作,而CAN不可以呢...


(PCLK1用于串口2,3,4,5;PCLK2用于串口1)




  uint32_t USART_BaudRate;            /*!< This member configures the USART communication baud rate.

                                           The baud rate is computed using the following formula:

                                            - IntegerDivider = ((PCLKx) / (16 * (USART_InitStruct->USART_BaudRate)))

                                            - FractionalDivider = ((IntegerDivider - ((u32) IntegerDivider)) * 16) + 0.5 */


推荐阅读

史海拾趣

问答坊 | AI 解惑

齐纳二极管原理特性

齐纳二极管原理特性…

查看全部问答>

按下16个矩阵键盘依次在数码管上显示1-16的平方。

按下16个矩阵键盘依次在数码管上显示1-16的平方。如按下第一个显示1,第二个显示4... 我写了第3行的检测,就是说:按键按下的话 ,会显示:16   25  36   49: 但是我在实验板上运行的时候,高位的数字只会闪一下 ...…

查看全部问答>

大虾们,能推荐几个不错的嵌入式论坛吗?

如题~ 因为我要做毕业设计了,我的毕业设计是ARM9+uClinux,…

查看全部问答>

Hp2490如何打开无线网卡,连接指定SSID,最好用C#完成,谢谢

Hp2490如何打开无线网卡,连接指定SSID,最好用C#完成,例如,我们办公室有N个无线网络,我想通过程序控制连接其中指定一个网络。…

查看全部问答>

嵌入式主板介绍

嵌入式主板一般理解为嵌入在设备里面做控制、数据处理使用的CPU板,也就是设备的“大脑”。嵌入式到设备里面,当然就会对主板的体积以及功耗(嵌入式主板的散热问题)有比较严格的要求。所以一般来讲嵌入式主板会具备 尺寸小、高集成度、低功耗等特 ...…

查看全部问答>

IAR 3.41使用问题

前一阵重新装机,从网上下了个IAR 3.41 然后有个小工具生成序列号,安装过程没问题,可是在程序编译时出现下面的提示: Fatal Error[Cp001]: Copy protection check, No valid license found for this product [20] 这是什么问题呀?…

查看全部问答>

红外鼠标控制.

 红外鼠标控制. 红外鼠标控制. 红外鼠标控制.…

查看全部问答>

基于MSP430F2013的超低功耗运动检测

基于MSP430F2013的超低功耗运动检测方案…

查看全部问答>

试试传说中的低功耗

以前开发MCU都是外置电源供电,几乎没有怎么考虑过功耗问题,借此机会试试在电池供电的环境下软硬件设计。…

查看全部问答>

点阵出了点问题,图像有

今天看了下点阵的教程,自己跑去搞了下 ,结果弄是弄出来,可就是每次图像移动前都会红一团  这是电路图还有代码,大大帮忙看看#include<reg52.h>#define uchar unsigned char#define uint unsigned intsbit dula=P2^6;sbit wela=P2^7;sbi ...…

查看全部问答>