深度剖析STM32时钟系统

发布者:PositiveVibes最新更新时间:2024-07-23 来源: elecfans关键字:STM32  时钟系统  时钟树 手机看文章 扫描二维码
随时随地手机看文章

下图是STM32的时钟树。从树上我们可以看到,STM32的时钟有两个来源——内部时钟和外部时钟。按时钟频率来分,又分为高速时钟和低速时钟。所以STM32的时钟有四个来源——高速外部时钟信号(HSE)、低速外部时钟信号(LSE)、高速内部时钟信号(HSI)和低速内部时钟信号(LSI),图中分别用蓝色的①~④标注。
深度剖析STM32时钟系统

①HSE高速外部时钟:由外部4~16MHz的晶体或有源晶振提供,通常采用8MHz,ST三合一板上的也是8MHz。

②LSI低速外部时钟:外部晶体提供,主要是给实时时钟(RTC),一般为32.768kHz。

③HSI高速内部时钟:由内部RC振荡器产生的8MHz时钟,但不够稳定。

④LSI低速内部时钟:内部RC振荡器产生的供给RTC的时钟,频率在30kHz~60kHz之间,通常约40kHz。

时钟在STM32内部最终是供给四大块,图中用红色椭圆圈出——USB的48MHz时钟、系统时钟SYSCLK、实时时钟模块RTC、独立看门狗的时钟IWDGCLK。其中最主要的,也是最大头是系统时钟SYSCLK,它可以是内部或外部高速时钟直接接过来,也可以内、外部高速时钟是PLL倍频后提供的,系统时钟再分别供给Cortex内核、SDIO、AHB总线、DMA、APB1、APB2等。

我们通常是采用外部8MHz高速时钟(HSE),所以着重说HSE。我们以前面的GPIO上的时钟为例,由ST的Datasheet可知,GPIO是在APB2高速外设总线上的,图中绿色的线就是时钟的流程,我们一步步地来看。

8MHz外部晶体(或晶振)输入后,先经过一个开关PLLXTPRE(HSE divider for PLL entry),此开关决定对HSE进行2分频再输入到PLL或直接到PLL。我们选择不分频。

这样时钟又到了第二个开关PLLSRC(PLL entry clock source),此开关决定PLL的时钟来源,是内部高速时钟二分频的时钟还是PLLXTPRE的输出。我们选择后者,这时的时钟在进入PLL前还是8MHz,因为在PLLXTPRE我们没有分频。

到了PLL倍频器,由PLLMUL决定倍频系统数,可以选择2~16倍频输出,但记住,PLL输出频率最高72MHz,所以我们选择9倍频,这样PLL输出就是最高72MHz的PLLCLK时钟了。这时的PLLCLK为USB提供时钟。

开关SW来决定SYSCLK的时钟来源,前面已经提到,这里我们由PLLCLK做为SYSCLK的来源,这样系统时钟SYSCLK就是72MHz了。

在供给外设前,先经过AHB预分频,我们选择不分频;在供给GPIO前,还要再经过APB2预分频,因为APB2为高速外设,所以我们选择不分频,这样GPIO的时钟就是72MHz了。注意,低速外设APB1最高频率为36MHz,所以在使用APB1的外设时,要注意设置好分频系统。还要注意,要使用外设,先要对外设时钟进行使能,见图中黄色云形框。这是因为STM32采用了低功耗的设计,对不使用的外设,其时钟不使能,以达到降低功耗的效果。

时钟的设置在程序中是怎么来实现的呢?这里我们以前面GPIO的程序来一步步分析。当然,前面的程序是基于ST库的,其实也就是分析ST的官方库了。

我们看到main()函数中的第一行代码是调用了一个函数:

SystemInit();

这个函数是在system_stm32f10x.c中:

void SystemInit (void)

{

/* Reset the RCC clock configuration to the default reset state(for debug purpose) */

/* Set HSION bit */

RCC->CR |= (uint32_t)0x00000001;

/* Reset SW, HPRE, PPRE1, PPRE2, ADCPRE and MCO bits */

#ifndef STM32F10X_CL

RCC->CFGR &= (uint32_t)0xF8FF0000;

#else

RCC->CFGR &= (uint32_t)0xF0FF0000;

#endif /* STM32F10X_CL */

/* Reset HSEON, CSSON and PLLON bits */

RCC->CR &= (uint32_t)0xFEF6FFFF;

/* Reset HSEBYP bit */

RCC->CR &= (uint32_t)0xFFFBFFFF;

/* Reset PLLSRC, PLLXTPRE, PLLMUL and USBPRE/OTGFSPRE bits */

RCC->CFGR &= (uint32_t)0xFF80FFFF;

#ifdef STM32F10X_CL

/* Reset PLL2ON and PLL3ON bits */

RCC->CR &= (uint32_t)0xEBFFFFFF;

/* Disable all interrupts and clear pending bits */

RCC->CIR = 0x00FF0000;

/* Reset CFGR2 register */

RCC->CFGR2 = 0x00000000;

#elif defined (STM32F10X_LD_VL) || defined (STM32F10X_MD_VL) || (defined STM32F10X_HD_VL)

/* Disable all interrupts and clear pending bits */

RCC->CIR = 0x009F0000;

/* Reset CFGR2 register */

RCC->CFGR2 = 0x00000000;

#else

/* Disable all interrupts and clear pending bits */

RCC->CIR = 0x009F0000;

#endif /* STM32F10X_CL */

#if defined (STM32F10X_HD) || (defined STM32F10X_XL) || (defined STM32F10X_HD_VL)

#ifdef DATA_IN_ExtSRAM

SystemInit_ExtMemCtl();

#endif /* DATA_IN_ExtSRAM */

#endif

/* Configure the System clock frequency, HCLK, PCLK2 and PCLK1 prescalers */

/* Configure the Flash Latency cycles and enable prefetch buffer */

SetSysClock();

#ifdef VECT_TAB_SRAM

SCB->VTOR = SRAM_BASE | VECT_TAB_OFFSET; /* Vector Table Relocation in Internal SRAM. */

#else

SCB->VTOR = FLASH_BASE | VECT_TAB_OFFSET; /* Vector Table Relocation in Internal FLASH. */

#endif

}

我们可以看到,程序前面一系统Reset或Disable,最后调用了(红色标记出来)

SetSysClock();

SetSysClock()函数也位于system_stm32f10x.c源文件中:

static void SetSysClock(void)

{

#ifdef SYSCLK_FREQ_HSE

SetSysClockToHSE();

#elif defined SYSCLK_FREQ_24MHz

SetSysClockTo24();

#elif defined SYSCLK_FREQ_36MHz

SetSysClockTo36();

#elif defined SYSCLK_FREQ_48MHz

SetSysClockTo48();

#elif defined SYSCLK_FREQ_56MHz

SetSysClockTo56();

#elif defined SYSCLK_FREQ_72MHz

SetSysClockTo72();

#endif

/* If none of the define above is enabled, the HSI is used as System clock

source (default after reset) */

}

因为我们使用的是72MHz时钟,那肯定我们定义了宏SYSCLK_FREQ_72MHz,所以才调用的函数SetSysClockTo72()。我们继续跟踪,会发现在源文件开头,我们的确定义了:

#define SYSCLK_FREQ_72MHz 72000000

在SetSysClockTo72()函数中详细地对72MHz进行设置,这里就不一步步分析。

前面已经提到,在使用外设时,要使能相应的外设时钟,例如,在使用GPIOB进行流水灯实验时,程序中调用了下面的库函数,对外设时钟进行设置:

RCC_APB2PeriphClockCmd( RCC_APB2Periph_GPIOB, ENABLE);

另外,STM32还可以把时钟输出,如图左下角的咖啡色方框里面,可以由MCO决定,PLL时钟二分频或HIS或HSE或系统时钟作为主时钟输出。


关键字:STM32  时钟系统  时钟树 引用地址:深度剖析STM32时钟系统

上一篇:详解STM32低功耗模式
下一篇:创建STM32工程模板

推荐阅读最新更新时间:2026-03-19 11:06

单片机stm32时钟以及修改系统时钟频率
  前言:在学51的时候我们知道单片机想要工作必须要有时钟,在stm32中,外部时钟源不是必须的,因为内部就有时钟源,因此我们需要了解stm32的时钟树以方便以后我们设置自己所需要的时钟频率   时钟树   解读   1.首先我们找到最重要的系统时钟:   他的最高频率为168MHZ,他可以由三个提供,一个是HSI(内部高速时钟源,h=high,i=internal),可以在主图中找到这个HSI RC,还有一个是HSE(外部高速时钟源,e=external),最后一个是PLLCLK(pll为锁相环提供,也可以在主图中找到)。。但系统时钟主要还是由PLLCLK提供   注意:   是指这个东西可以由三个其中之
[单片机]
单片机<font color='red'>stm32</font>之<font color='red'>时钟</font><font color='red'>树</font>以及修改<font color='red'>系统</font><font color='red'>时钟</font>频率
stm32时钟以及修改系统时钟频率
前言:在学51的时候我们知道单片机想要工作必须要有时钟,在stm32中,外部时钟源不是必须的,因为内部就有时钟源,因此我们需要了解stm32的时钟树以方便以后我们设置自己所需要的时钟频率 时钟树 解读 1.首先我们找到最重要的系统时钟: 他的最高频率为168MHZ,他可以由三个提供,一个是HSI(内部高速时钟源,h=high,i=internal),可以在主图中找到这个HSI RC,还有一个是HSE(外部高速时钟源,e=external),最后一个是PLLCLK(pll为锁相环提供,也可以在主图中找到)。。但系统时钟主要还是由PLLCLK提供 注意: 是指这个东西可以由三个其中之一提供,而不是由三个组成。
[单片机]
<font color='red'>stm32</font><font color='red'>时钟</font><font color='red'>树</font>以及修改<font color='red'>系统</font><font color='red'>时钟</font>频率
stm32专题五:时钟(二)系统配置时钟函数分析
分析stm32的系统时钟函数,对于我们实现自定义时钟配置非常重要,以下是标准库函数中的时钟配置函数。 static void SetSysClockTo72(void) { __IO uint32_t StartUpCounter = 0, HSEStatus = 0; /* SYSCLK, HCLK, PCLK2 and PCLK1 configuration ---------------------------*/ /* Enable HSE */ // 使能HSE RCC- CR |= ((uint32_t)RCC_CR_HSEON); /* Wait till HSE is ready
[单片机]
STM32学习笔记3——stm32系统时钟
①HSI 是内部高速时钟, RC 振荡器, 频率为 8MHz。 可作为系统时钟或 PLL 锁相环的输入。 ②HSE 是外部高速时钟。 可通过外接一个频率范围是 4-16MHz 的时钟或者晶振。 HSE 可以作为系统时钟和 PLL 锁相环输入, 还可以经过 128 分频后输入给 RTC。 ③LSI 是内部低速时钟, RC 振荡器, 频率大约为 40K, 可供独立看门狗和 RTC 使用, 并且独立看门狗只能使用 LSI 时钟。 ④LSE 是外部低速时钟,芯片上有相应的外部低速时钟管脚。 通常在此管脚上外接一个 32.768KHz 的晶振, 供 RTC使用。 ⑤PLL 是锁相环, 用于倍频输出。
[单片机]
<font color='red'>STM32</font>学习笔记3——<font color='red'>stm32</font><font color='red'>系统</font><font color='red'>时钟</font><font color='red'>树</font>
STM32时钟(结合系统时钟函数理解)
时钟树的概念: 我们可以把MCU的运行比作人体的运行一样,人最重要的是什么?是心跳! 心脏的周期性收缩将血液泵向身体各处。心脏对于人体好比时钟对于MCU,微控制器(MCU)的运行要靠周期性的时钟脉冲来驱动,而这个脉冲的始源往往是由外部晶体振荡器提供时钟输入,最终转换为多个外部设备的周期性运作。这种时钟“能量”的传递路径犹如大树的养分由主干流向个分支,因此称为时钟树。 STM32时钟: 在STM32中每个外设都有其单独的时钟,在使用某个外设之前必须打开该外设的时钟 ,为什么要这么麻烦来设置每一个外设的时钟而不是将所有外设的时钟统一打开?因为STM32的外设繁多,外设的运作所需要的最佳时钟各不相同,如果所有时钟同时运行会给MCU带
[单片机]
<font color='red'>STM32</font>—<font color='red'>时钟</font><font color='red'>树</font>(结合<font color='red'>系统</font><font color='red'>时钟</font>函数理解)
STM32系统时钟配置及时钟
参考资料:《 STM32F4xx 中文参考手册》 RCC 章节。 STM32时钟可大致分为系统时钟和其它时钟两大类,总共包含5个时钟源 HSI(High Speed Internal Clock)、HSE(High Speed External Clock)、LSI(low Speed Internal Clock)、LSE(Low Speed External Clock )、PLL(Phase Locked Loop Clock)。 下图即为STM32时钟树,黄色标识部分即为系统时钟部分,橙色即为其它时钟部分。 一、系统时钟 ①HSE(High Speed External Clock)高速外部时钟信号
[单片机]
<font color='red'>STM32</font><font color='red'>系统</font><font color='red'>时钟</font>配置及<font color='red'>时钟</font><font color='red'>树</font>
STM32之旅3——时钟
STM32F1是M3内核,它的时钟数很庞大,让一个初学者去看,估计会很吃力,和我们入门的8051单片机的时钟不同,这里又倍频、又分频,而且还分成好多个时钟,不同的外设时钟不一样。 总感觉不都明了,后来在STM32CubeMX中看到了时钟配置,这个看起来就明了多了
[单片机]
<font color='red'>STM32</font>之旅3——<font color='red'>时钟</font><font color='red'>树</font>
STM32】7—通用定时器 & 时钟学习
0 实验预期效果 让LED闪烁(每秒钟内:亮0.5s,再暗0.5s)。 1 相关原理图 2 定时器TIM2与时钟树 2.1 TIM2 简介与特性 关于通用定时器TIM2,查STM32F407中文手册392页可知: ① TIM2 到 TIM5 简介: 通用定时器包含一个16 位或 32 位自动重载计数器,该计数器由可编程预分频器驱动。 它们可用于多种用途,包括测量输入信号的脉冲宽度(输入捕获)或生成输出波形(输出比较和 PWM)。 使用定时器预分频器和 RCC 时钟控制器预分频器,可将脉冲宽度和波形周期从几微秒调制到几毫秒。 这些定时器彼此完全独立,不共享任何资源
[单片机]
【<font color='red'>STM32</font>】7—通用定时器 & <font color='red'>时钟</font><font color='red'>树</font>学习
小广播
最新单片机文章
何立民专栏 单片机及嵌入式宝典

北京航空航天大学教授,20余年来致力于单片机与嵌入式系统推广工作。

厂商技术中心

 
EEWorld订阅号

 
EEWorld服务号

 
汽车开发圈

 
机器人开发圈

电子工程世界版权所有 京ICP证060456号 京ICP备10001474号-1 电信业务审批[2006]字第258号函 京公网安备 11010802033920号 Copyright © 2005-2026 EEWORLD.com.cn, Inc. All rights reserved