开发平台
野火F429开发板
标准库
配置系统时钟首先要学会看时钟树,f429主频为180MHZ
时钟树
查看手册 时钟树如下图
现在我需要用到的时钟总线主要是:AHB、APB1、APB2 其他的以后用到的时候再看吧
1.HSE外部高速时钟信号
HSE由晶振提供,晶振又分有源晶振和无源晶振,无源晶振需要提供时钟电路才可产生振荡。
由图中可以看到 OSC_OUT和OSC_IN,采用无源晶振时,时钟从OSC_OUT和OSC_IN进入;
采用有源晶振从OSC_IN进入,OSC_OUT悬空。这里使用无源晶振25MHZ
2.PLL锁相环
HSE经过PLL 输入分频因子M(查手册得 2~63),成为时钟输入VCO时钟(1-2M),然后再经过倍频因子N。成为VCO时钟输出 ,VCO时钟必须在(192-423)之间(要想系统时钟超频,改变倍频因子N),VCO时钟输出后由三个倍频因子P(PLLCLOCK分频因子)、Q(USB等时钟分频因子)、R(F429没有不做解释)
3.系统时钟
PLLCLOCK作为系统时钟,若HSE出现故障,PLL也会关闭,系统时钟会切换成HSI知道HSE恢复
4.AHB时钟总线HCLK
HCLK=SYSCLK,所以AHBPRESC不分频
5.APB1时钟总线PCLK1
APB1为低速时钟总线一般 HCLK/4.四分频
6.APB2时钟总线PCLK2
APB2为高速时钟总线一般 HCLK/2.二分频
需要用到的分析完了,接下来就要写程序
使用HSE/HSI配置系统时钟
1.开启HSE,等待HSE稳定(HSI首先要把RCC外设初始化成复位状态)
RCC_HSEConfig(uint8_t RCC_HSE); RCC_WaitForHSEStartUp(void);
2.使能电源接口时钟、设置调压器输出电压级别,通常为1,以便器件在最大频率实现性能和功耗平衡(这里没有函数可用要直接操作寄存器,查看手册APB1ENR寄存器、CR寄存器)
3.配置AHB APB1 APB2的分频因子
RCC_HCLKConfig(uint32_t RCC_SYSCLK);
RCC_PCLK1Config(uint32_t RCC_HCLK);
RCC_PCLK2Config(uint32_t RCC_HCLK);
4.设置PLL时钟来源(HSE/HSI)、分频因子M(2-63)、倍频因子N、PLLCKL分频因子P、USB等分频因子Q
RCC_PLLConfig(uint32_t RCC_PLLSource, uint32_t PLLM, uint32_t PLLN, uint32_t PLLP, uint32_t PLLQ);
5.使能PLL,并等待稳定
RCC_PLLCmd(FunctionalState NewState);
6.开启 OVER-RIDE模式,以能达到更高频率(这里也要直接操作寄存器CR 寄存器ODEN位)等待设置成功(CSR寄存器ODRDY)
7.切换到切换驱动模式(直接操作寄存器CR寄存器ODSWEN位)等待设置成功(CSR寄存器ODSWRDY)
8.配置FLASH预取指、指令缓存、数据缓存、和等待状态(5个等待周期)(寄存器ACR)
9.把PLLCLK设置为SYSCK
RCC_SYSCLKConfig(uint32_t RCC_SYSCLKSource);
10.读取时钟状态位,确保PLLCLK作为系统时钟(作为系统时钟数值为0X80)
RCC_GetSYSCLKSource(void);
代码如下:
void SYSCLOCK_HSE_Config(uint32_t PLLM,uint32_t PLLN,uint32_t PLLP,uint32_t PLLQ)
{
uint32_t HSE_starupstatus=0;
/*启动HSE*/
RCC_HSEConfig(RCC_HSE_ON);
/*等待HSE启动*/
HSE_starupstatus=RCC_WaitForHSEStartUp();
if(HSE_starupstatus==SUCCESS)
{
/*使能电源接口时钟*/
RCC->APB1ENR=RCC_APB1ENR_PWREN;
/*设置调压器输出级别,设置为级别1*/
PWR->CR=PWR_CR_VOS;
/*设置AHB APB1 APB2的预分频因子*/
/*AHB 180M*/
RCC_HCLKConfig(RCC_SYSCLK_Div1);
/*APB1 45M*/
RCC_PCLK1Config(RCC_HCLK_Div4);
/*APB2 90M*/
RCC_PCLK2Config(RCC_HCLK_Div2);
/*设置PLL锁相环的 M 分频 P Q 倍频因子*/
RCC_PLLConfig(RCC_PLLSource_HSE,PLLM,PLLN,PLLP,PLLQ);
/*使能PLL*/
RCC_PLLCmd( ENABLE);
/*等待PLL稳定*/
while(RCC_GetFlagStatus(RCC_FLAG_PLLRDY)==RESET)
{
;
}
/*开启 OVER-RIDE模式,以能达到更高频率*/
PWR->CR=PWR_CR_ODEN;
while(PWR->CSR & PWR_CSR_ODRDY==0)
{
;
}
/*用于切换驱动模式*/
PWR->CR=PWR_CR_ODSWEN;
while(PWR->CSR & PWR_CSR_ODSWRDY==0)
{
;
}
/*设置FLASH 预取指 指令缓存 数据缓存 等待状态为5个周期*/
FLASH->ACR=FLASH_ACR_PRFTEN|
FLASH_ACR_DCEN|
FLASH_ACR_ICEN|
FLASH_ACR_LATENCY_5WS;
/*把PLLCLOCK设置为SYSCLOCK*/
RCC_SYSCLKConfig(RCC_SYSCLKSource_PLLCLK);
/*读取时钟状态位*/
while(RCC_GetSYSCLKSource()!=0x08)
{
;
}
}
/*HSE 启动失败*/
else
{
while(1);
}
}