高中生
最后登录1970-1-1
在线时间 小时
注册时间2017-11-1
|
本帖最后由 拖延症晚期 于 2017-11-17 15:49 编辑
学习火哥的教程到RCC这一章,例程的 bsp_clkconfig.c 中分别有使用 HSE 和 HSI 配置为系统时钟的函数
第一步都是开启时钟,等待时钟稳定,稳定后进行后续的一系列配置,我对比了判断 HSE 和 HSI 稳定的过程,如下
一、HSE
- void HSE_SetSysClock(uint32_t m, uint32_t n, uint32_t p, uint32_t q)
- {
- __IO uint32_t HSEStartUpStatus = 0;
-
- // 使能HSE,开启外部晶振,秉火F407使用 HSE=25M
- RCC_HSEConfig(RCC_HSE_ON);
-
- // 等待HSE启动稳定
- HSEStartUpStatus = RCC_WaitForHSEStartUp();
- if (HSEStartUpStatus == SUCCESS)
- {......}
复制代码 判断稳定这一步调用了RCC_WaitForHSEStartUp(),查到该函数定义为
- ErrorStatus RCC_WaitForHSEStartUp(void)
- {
- __IO uint32_t startupcounter = 0;
- ErrorStatus status = ERROR;
- FlagStatus hsestatus = RESET;
- /* Wait till HSE is ready and if Time out is reached exit */
- do
- {
- hsestatus = RCC_GetFlagStatus(RCC_FLAG_HSERDY);
- startupcounter++;
- } while((startupcounter != HSE_STARTUP_TIMEOUT) && (hsestatus == RESET));
- if (RCC_GetFlagStatus(RCC_FLAG_HSERDY) != RESET)
- {
- status = SUCCESS;
- }
- else
- {
- status = ERROR;
- }
- return (status);
- }
复制代码 函数体中用了一个do{}while()循环,轮询RCC寄存器相应状态位,直到状态位指示稳定,跳出循环
可见HSE启动到稳定需要一定的时间,而HSI的函数如下
二、HSI
- void HSI_SetSysClock(uint32_t m, uint32_t n, uint32_t p, uint32_t q)
- {
- __IO uint32_t HSIStartUpStatus = 0;
-
- // 把RCC外设初始化成复位状态
- RCC_DeInit();
-
- //使能HSI, HSI=16M
- RCC_HSICmd(ENABLE);
-
- // 等待 HSI 就绪
- HSIStartUpStatus = RCC->CR & RCC_CR_HSIRDY;
-
- // 只有 HSI就绪之后则继续往下执行
- if (HSIStartUpStatus == RCC_CR_HSIRDY)
- {......}
复制代码 这里首先调用了RCC_DeInit(),这里其实已经使能了HSI,rcc初始化默认配置HSI为系统时钟,然后使能HSI,下一行注释是等待HSI就绪,然而只有一条读取 RCC_CR的HSIRDY 位的操作,并没有类似于HSE中轮询等待的步骤,相当于使能完就直接读取状态位,没有等待稳定的时间,如果这时HSI没有稳定,if 后面的语句不就不执行了吗?
这是我的一点疑惑,另外RCC_DeInit()函数中已经使能了HSI,还有一些设置默认系统时钟、分频系数的语句,难道是因为调用了RCC_DeInit()后,到读取状态位HSIStartUpStatus = RCC->CR & RCC_CR_HSIRDY这一步,这段时间已经足够HSI稳定了吗?
|
|