1.概述

简单的说,时钟是单片机的脉搏,是单片机的驱动源,使用任何一个外设都必须打开相应的时钟。这样的好处是,如果不使用一个外设的时候,就把它的时钟关掉,从而可以降低系统的功耗,达到节能,实现低功耗的效果。每个时钟tick,系统都会处理一步数据,这样才能让工作不出现紊乱。

2.原理

首先,任何外设都需要时钟,51单片机,stm32,430等等,因为寄存器是由D触发器组成的,往触发器里面写东西,前提条件是有时钟输入。
51单片机不需要配置时钟,是因为一个时钟开了之后所有的功能都可以用了,而这个时钟是默认开启的,比如有一个水库,水库有很多个门,这些门默认是开启的,所以每个门都会出水,我们需要哪个门的水的时候可以直接用,但是也存在一个问题,其他没用到的门也在出水,即也在耗能。这里水库可以认为是能源,门可以认为是每个外设的使用状态,时钟可以认为是门的开关。stm32之所以是低功耗,他将所有的门都默认设置为disable,在你需要用哪个门的时候,开哪个门就可以,也就是说用到什么外设,只要打开对应外设的时钟就可以,其他的没用到的可以还是disable,这样耗能就会减少。
在51单片机中一个时钟把所有的都包了,而stm32的时钟是有分工的,并且每类时钟的频率不一样,因为没必要所有的时钟都是最高频率,只要够用就行,好比一个门出来水流大小,我只要洗脸,但是出来的是和洪水一样涌出来的水,那就gg了,消耗能源也多,所以不同的时钟也会有频率差别,或者在配置的时候可以配置时钟分频。

拓展:为何要先配置时钟,再配置GPIO(功能模块)

所有寄存器都需要时钟才能配置,寄存器是由D触发器组成的,只有送来了时钟,触发器才能被改写值。
任何MCU的任何外设都需要有时钟,8051也是如此;STM32为了让用户更好地掌握功耗,对每个外设的时钟都设置了开关,让用户可以精确地控制,关闭不需要的设备,达到节省供电的目的。
51单片机不用配置IO时钟,只是因为默认使用同一个时钟,这样是方便,但是这样的话功耗就降低不了。
例如,某个功能不需要,但是它还是一直运行。
stm32需要配置时钟,就可以把不需要那些功能的功耗去掉。
当你想关闭某个IO的时候,关闭它相对应的时钟使能就是了,不过在51里面,在使用IO的时候是没有设置IO的时钟的,还有在STM32中,有外部和内部时钟之分,关于时钟等好好研究
ARM的芯片都是这样,外设通常都是给了时钟后,才能设置它的寄存器(即才能使用这个外设)。STM32、LPC1XXX等等都是这样。
这么做的目的是为了省电,使用了所谓时钟门控的技术。
这也属于电路里同步电路的范畴:同步电路总是需要1个时钟。

3.分类

时钟发生器用于产生时钟,并提供给CPU和外部硬件设备。

有如下三种系统时钟。

(1)主系统时钟

①通过连接一个振荡器到X1和X2,该振荡电路产生fx=1到20MHZ的时钟;

②使用内部高速振荡器产生fRH=8MHZ的时钟。

(2)副系统时钟

①通过在XT1和XT2之间连接一个fXT=32.768KHZ的振荡器;

②通过XT2引脚提供一个外部副系统时钟fexclks=32.768KHZ。

(3)内部低速振荡时钟(看门狗定时器时钟)

①内部低速振荡器,以fRL=240KHZ的时钟振荡。该时钟不能作为CPU时钟。

4.配置

一、在STM32中,有五个时钟源,为HSIHSELSILSEPLL

HSI是高速内部时钟,RC振荡器,频率为8MHz。

HSE是高速外部时钟,可接石英/陶瓷谐振器,或者接外部时钟源,频率范围为4MHz~16MHz。

LSI是低速内部时钟,RC振荡器,频率为40kHz。

LSE是低速外部时钟,接频率为32.768kHz的石英晶体。

PLL为锁相环倍频输出,其时钟输入源可选择为HSI/2、HSE或者HSE/2。倍频可选择为2~16倍,但是其输出频率最大不得超过72MHz。

二、在STM32上如果不使用外部晶振,OSC_IN和OSC_OUT的接法:如果使用内部RC振荡器而不使用外部晶振,请按照下面方法处理:

①对于100脚或144脚的产品,OSC_IN应接地,OSC_OUT应悬空。
②对于少于100脚的产品,有2种接法:第1种:OSC_IN和OSC_OUT分别通过10K电阻接地。此方法可提高EMC性能;第2种:分别重映射OSC_IN和OSC_OUT至PD0和PD1,再配置PD0和PD1为推挽输出并输出'0'。此方法可以减小功耗并(相对上面)节省2个外部电阻。

三、用HSE时钟,程序设置时钟参数流程
01、将RCC寄存器重新设置为默认值   RCC_DeInit;
02、打开外部高速时钟晶振HSE    RCC_HSEConfig(RCC_HSE_ON);
03、等待外部高速时钟晶振工作    HSEStartUpStatus = RCC_WaitForHSEStartUp();
04、设置AHB时钟         RCC_HCLKConfig;
05、设置高速AHB时钟     RCC_PCLK2Config;
06、设置低速速AHB时钟   RCC_PCLK1Config;
07、设置PLL              RCC_PLLConfig;
08、打开PLL              RCC_PLLCmd(ENABLE);
09、等待PLL工作   while(RCC_GetFlagStatus(RCC_FLAG_PLLRDY) == RESET)
10、设置系统时钟        RCC_SYSCLKConfig;
11、判断是否PLL是系统时钟     while(RCC_GetSYSCLKSource() != 0x08)
12、打开要使用的外设时钟    RCC_APB2PeriphClockCmd()/RCC_APB1PeriphClockCmd()

四、下面是STM32软件固件库的程序中对RCC的配置函数(使用外部8MHz晶振)

/*******************************************************************************

* Function Name  : RCC_Configuration

* Description    :  RCC配置(使用外部8MHz晶振)

* Input            : 无

* Output         : 无

* Return         : 无

*******************************************************************************/

void RCC_Configuration(void)

{

/*将外设RCC寄存器重设为缺省值*/

RCC_DeInit();

/*设置外部高速晶振(HSE)*/

RCC_HSEConfig(RCC_HSE_ON);   //RCC_HSE_ON——HSE晶振打开(ON)

/*等待HSE起振*/

HSEStartUpStatus = RCC_WaitForHSEStartUp();

if(HSEStartUpStatus == SUCCESS)        //SUCCESS:HSE晶振稳定且就绪

{

/*设置AHB时钟(HCLK)*/

RCC_HCLKConfig(RCC_SYSCLK_Div1);  //RCC_SYSCLK_Div1——AHB时钟= 系统时钟

/* 设置高速AHB时钟(PCLK2)*/

RCC_PCLK2Config(RCC_HCLK_Div1);   //RCC_HCLK_Div1——APB2时钟= HCLK

/*设置低速AHB时钟(PCLK1)*/

RCC_PCLK1Config(RCC_HCLK_Div2);   //RCC_HCLK_Div2——APB1时钟= HCLK / 2

/*设置FLASH存储器延时时钟周期数*/

FLASH_SetLatency(FLASH_Latency_2);    //FLASH_Latency_2  2延时周期

/*选择FLASH预取指缓存的模式*/

FLASH_PrefetchBufferCmd(FLASH_PrefetchBuffer_Enable);       // 预取指缓存使能

/*设置PLL时钟源及倍频系数*/

RCC_PLLConfig(RCC_PLLSource_HSE_Div1, RCC_PLLMul_9);

// PLL的输入时钟= HSE时钟频率;RCC_PLLMul_9——PLL输入时钟x 9

/*使能PLL */

RCC_PLLCmd(ENABLE);

/*检查指定的RCC标志位(PLL准备好标志)设置与否*/

while(RCC_GetFlagStatus(RCC_FLAG_PLLRDY) == RESET)

{

}

/*设置系统时钟(SYSCLK)*/

RCC_SYSCLKConfig(RCC_SYSCLKSource_PLLCLK);

//RCC_SYSCLKSource_PLLCLK——选择PLL作为系统时钟

/* PLL返回用作系统时钟的时钟源*/

while(RCC_GetSYSCLKSource() != 0x08)        //0x08:PLL作为系统时钟

{

}

/*使能或者失能APB2外设时钟*/

RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA | RCC_APB2Periph_GPIOB |

RCC_APB2Periph_GPIOC , ENABLE);

//RCC_APB2Periph_GPIOA    GPIOA时钟

//RCC_APB2Periph_GPIOB    GPIOB时钟

//RCC_APB2Periph_GPIOC    GPIOC时钟

//RCC_APB2Periph_GPIOD    GPIOD时钟

}

五、时钟频率

STM32F103内部8M的内部震荡,经过倍频后最高可以达到72M。目前TI的M3系列芯片最高频率可以达到80M。

在stm32固件库3.0中对时钟频率的选择进行了大大的简化,原先的一大堆操作都在后台进行。系统给出的函数为SystemInit()。但在调用前还需要进行一些宏定义的设置,具体的设置在system_stm32f10x.c文件中。

文件开头就有一个这样的定义: 
//#define SYSCLK_FREQ_HSE    HSE_Value 
//#define SYSCLK_FREQ_20MHz 20000000 
//#define SYSCLK_FREQ_36MHz 36000000 
//#define SYSCLK_FREQ_48MHz 48000000 
//#define SYSCLK_FREQ_56MHz 56000000 
#define SYSCLK_FREQ_72MHz 72000000

ST 官方推荐的外接晶振是 8M,所以库函数的设置都是假定你的硬件已经接了 8M 晶振来运算的.以上东西就是默认晶振 8M 的时候,推荐的 CPU 频率选择.在这里选择了:
#define SYSCLK_FREQ_72MHz 72000000 
也就是103系列能跑到的最大值72M

然后这个 C文件继续往下看 
#elif defined SYSCLK_FREQ_72MHz 
const uint32_t SystemFrequency         = SYSCLK_FREQ_72MHz;    
const uint32_t SystemFrequency_SysClk = SYSCLK_FREQ_72MHz;    
const uint32_t SystemFrequency_AHBClk = SYSCLK_FREQ_72MHz;    
const uint32_t SystemFrequency_APB1Clk = (SYSCLK_FREQ_72MHz/2);
const uint32_t SystemFrequency_APB2Clk = SYSCLK_FREQ_72MHz;

这就是在定义了CPU跑72M的时候,各个系统的速度了.他们分别是:硬件频率,系统时钟,AHB总线频率,APB1总线频率,APB2总线频率.再往下看,看到这个了: 
#elif defined SYSCLK_FREQ_72MHz 
static void SetSysClockTo72(void);

这就是定义 72M 的时候,设置时钟的函数.这个函数被 SetSysClock ()函数调用,而
SetSysClock ()函数则是被 SystemInit()函数调用.最后 SystemInit()函数,就是被你调用的了

所以设置系统时钟的流程就是: 
首先用户程序调用 SystemInit()函数,这是一个库函数,然后 SystemInit()函数里面,进行了一些寄存器必要的初始化后,就调用 SetSysClock()函数. SetSysClock()函数根据那个#define SYSCLK_FREQ_72MHz 72000000 的宏定义,知道了要调用SetSysClockTo72()这个函数,于是,就一堆麻烦而复杂的设置~!@#$%^然后,CPU跑起来了,而且速度是 72M. 虽然说的有点累赘,但大家只需要知道,用户要设置频率,程序中就做的就两个事情:

第一个: system_stm32f10x.c 中 #define SYSCLK_FREQ_72MHz 72000000

第二个:调用SystemInit()

对单片机中时钟的理解:相关推荐

  1. 为什么单片机需要时钟系统,时钟信号在单片机中扮演怎样的角色?

    现在想想,我自学单片机都快一年了.我自学过8051.msp430和STM32,做一些基本的小项目,参加过2018年江苏省电子设计大赛,还获得了一等奖. 我懂,也不懂单片机.不懂就要去查资料,然后弄懂, ...

  2. RTC介绍——单片机中的时钟芯片

    RTC介绍--单片机中的时钟芯片 实时时钟芯片(Real Time Clock,RTC)是一种常用于计算机.嵌入式系统等电子设备中的计时.日期芯片.在单片机应用中,RTC以其高精度.低功耗等特点而广泛 ...

  3. 单片机中存储器扩展位地址线怎么算_51单片机CPU结构各部件的原理详细分析

    一. 51单片机串行口工作原理 MCS-51系列单片机片内有一个串行I/O端口,通过引脚RXD(P3.0)和TXD(P3.1)可与外设电路进行全双工的串行异步通信. 1.串行端口的基本特点 8031单 ...

  4. 单片机电子时钟的设计(期末课程设计)

    题目:单片机电子时钟的设计 设计一个时钟,可以正常显示时分秒,也可以通过按键改变分钟和小时,且有整点提醒功能 1.能够正常计时并且能够显示小时.分钟.秒,10分. (1)正常显示秒,2分 (2)正常显 ...

  5. 52单片机设计时钟(串口控制)

    实现目标 单片机时钟正常工作,数码管显示时分秒.电脑和单片机串行通信,通过电脑串口助手,任意修改设置单片机的时钟值. 实现的流程框图 运用到的原理有 定时器/计数器 定时器/计数器由高8位和低8位两个 ...

  6. STM32为何能在众多单片机中脱颖而出?

    现在STM32资料教程如此丰富,但还是很多人学不会- 假如STM32像10年前的NXP单片机资料一样少,估计学不会的人会更多. 大家好,我是无际,一个踩坑单片机开发10年的老油条. 这些年,我用过很多 ...

  7. 单片机中的ROM,RAM和FLASH的作用

    本文部分参考自:http://blog.sina.com.cn/s/blog_98ca54fc01017y4t.html 并在此基础上进行整理,添加了关于flash的问题. 之前从较为抽象的角度介绍了 ...

  8. 51单片机中的定时器

    文章目录 1 51单片机中的定时器介绍 1.1 定时器的初步认识 1.2 定时器的寄存器 1.3 使用定时器的方法 1.4 定时时间的计算 2 定时器模式1 2.1 定时器模式1原理分析 2.2 使用 ...

  9. 蓝桥杯单片机DS1302时钟芯片驱动代码注释

    蓝桥杯单片机DS1302时钟芯片驱动代码之前的疑惑注释了下 /* DS1302 芯片包含一个 实时时钟/日历和 31 字节的静态 RAM. 与时钟/RAM 通讯只需要三根线: CE,I/O (数据线) ...

最新文章

  1. java 程序运行时注入方法_Spring入门(九):运行时值注入
  2. 【面试必备】透过源码角度一步一步带你分析 ArrayList 扩容机制
  3. gcc 5.2.0 编译安装笔记-20151110
  4. spring 数组中随机取几个_美团Java研发三面(3年经验):MySQL+Spring源码+分布式+算法+线程...
  5. 基于linux使用mysql二进制包安装mysql
  6. mac 上安装服务,查看服务,重启和关闭
  7. RH413-测试文件的a属性
  8. 蓝桥杯 - 完美的代价(贪心+模拟)
  9. Tomcat源码解析一:下载源码与导入eclipse
  10. c语言程序中注释的格式化,格式化C语言命令indent
  11. iphone照片删掉又出现_30条让人相见恨晚的iPhone使用技巧。
  12. python 传参数 传引用_Python 函数参数 传引用还是传值
  13. HUAWEI HiAI 3.0 分布式,瑜伽、开车还能这么玩......
  14. git——远程仓库基本操作与冲突解决
  15. Kylo 浏览器 值得一玩
  16. PHP文件处理--打开文件
  17. 集团类企业信息化原则与思路
  18. 使用 Tenderly 为区块链交易设置警报通知
  19. Linux·内核源码简单分析
  20. JAVA进行图片压缩

热门文章

  1. jQuery实现后台异步加载数据的省、市二级联动
  2. 042-遍地开花的 json
  3. 【B2B】酒店客房影音解决方案
  4. leetcode: 322.零钱兑换
  5. uniapp生成海报,保存相册 / 分享微信好友和朋友圈
  6. 【Redis】聊一下缓存雪崩、击穿、穿透、预热
  7. ios 10 新系统功能
  8. rssi室内定位算法原理_一种基于RSSI测距的室内定位方法与流程
  9. 计算机复制文件的功能,禁止U盘复制电脑文件、禁止电脑文件复制到U盘、禁止复制计算机文件到U盘的方法...
  10. 《数字图像处理》学习总结及感悟:第二章数字图像基础(2)电磁波、传感器及辐射成像原理