跳转到主要内容

STM32之时钟

judy 提交于

<strong>一、RCC是什么?</strong>

RCC: Reset Clock Control,时钟和复位控制器

<strong>二、RCC的主要作用</strong>

1、设置系统时钟SYSCLK

2、设置AHB分频因子(决定HCLK等于多少)

3、设置APB2分频因子(决定PCLK2等于多少)

4、设置APB1分频因子(决定PCLK1等于多少)

5、设置各个外设的分频因子

6、控制AHB、APB2和APB1三条总线时钟的开启、控制每个外设时钟的开启。

注意:STM32库函数中时钟的标准配置为PCLK2=HCLK=SYSCLK=PLLCLK=72M,PCLK1=HCLK/2=36M

<strong>三、系统时钟库函数</strong>

对于系统时钟的配置,在固件库文件system_stm32f10x.c中。如下所示:
<pre style="overflow-x:auto; background-color:#e9e9e9;">static void SetSysClockTo72(void)
{
__IO uint32_t StartUpCounter = 0, HSEStatus = 0;

/* SYSCLK, HCLK, PCLK2 and PCLK1 configuration ---------------------------*/
/* Enable HSE */
RCC-&gt;CR |= ((uint32_t)RCC_CR_HSEON);

/* Wait till HSE is ready and if Time out is reached exit */
do
{
HSEStatus = RCC-&gt;CR & RCC_CR_HSERDY;
StartUpCounter++;
} while((HSEStatus == 0) && (StartUpCounter != HSE_STARTUP_TIMEOUT));

if ((RCC-&gt;CR & RCC_CR_HSERDY) != RESET)
{
HSEStatus = (uint32_t)0x01;
}
else
{
HSEStatus = (uint32_t)0x00;
}

if (HSEStatus == (uint32_t)0x01)
{
/* Enable Prefetch Buffer */
FLASH-&gt;ACR |= FLASH_ACR_PRFTBE;

/* Flash 2 wait state */
FLASH-&gt;ACR &= (uint32_t)((uint32_t)~FLASH_ACR_LATENCY);
FLASH-&gt;ACR |= (uint32_t)FLASH_ACR_LATENCY_2;

/* HCLK = SYSCLK */
RCC-&gt;CFGR |= (uint32_t)RCC_CFGR_HPRE_DIV1;

/* PCLK2 = HCLK */
RCC-&gt;CFGR |= (uint32_t)RCC_CFGR_PPRE2_DIV1;

/* PCLK1 = HCLK */
RCC-&gt;CFGR |= (uint32_t)RCC_CFGR_PPRE1_DIV2;

#ifdef STM32F10X_CL
/* Configure PLLs ------------------------------------------------------*/
/* PLL2 configuration: PLL2CLK = (HSE / 5) * 8 = 40 MHz */
/* PREDIV1 configuration: PREDIV1CLK = PLL2 / 5 = 8 MHz */

RCC-&gt;CFGR2 &= (uint32_t)~(RCC_CFGR2_PREDIV2 | RCC_CFGR2_PLL2MUL |
RCC_CFGR2_PREDIV1 | RCC_CFGR2_PREDIV1SRC);
RCC-&gt;CFGR2 |= (uint32_t)(RCC_CFGR2_PREDIV2_DIV5 | RCC_CFGR2_PLL2MUL8 |
RCC_CFGR2_PREDIV1SRC_PLL2 | RCC_CFGR2_PREDIV1_DIV5);

/* Enable PLL2 */
RCC-&gt;CR |= RCC_CR_PLL2ON;
/* Wait till PLL2 is ready */
while((RCC-&gt;CR & RCC_CR_PLL2RDY) == 0)
{
}

/* PLL configuration: PLLCLK = PREDIV1 * 9 = 72 MHz */
RCC-&gt;CFGR &= (uint32_t)~(RCC_CFGR_PLLXTPRE | RCC_CFGR_PLLSRC | RCC_CFGR_PLLMULL);
RCC-&gt;CFGR |= (uint32_t)(RCC_CFGR_PLLXTPRE_PREDIV1 | RCC_CFGR_PLLSRC_PREDIV1 |
RCC_CFGR_PLLMULL9);
#else
/* PLL configuration: PLLCLK = HSE * 9 = 72 MHz */
RCC-&gt;CFGR &= (uint32_t)((uint32_t)~(RCC_CFGR_PLLSRC | RCC_CFGR_PLLXTPRE |
RCC_CFGR_PLLMULL));
RCC-&gt;CFGR |= (uint32_t)(RCC_CFGR_PLLSRC_HSE | RCC_CFGR_PLLMULL6); //12*6=72M
#endif /* STM32F10X_CL */

/* Enable PLL */
RCC-&gt;CR |= RCC_CR_PLLON;

/* Wait till PLL is ready */
while((RCC-&gt;CR & RCC_CR_PLLRDY) == 0)
{
}

/* Select PLL as system clock source */
RCC-&gt;CFGR &= (uint32_t)((uint32_t)~(RCC_CFGR_SW));
RCC-&gt;CFGR |= (uint32_t)RCC_CFGR_SW_PLL;

/* Wait till PLL is used as system clock source */
while ((RCC-&gt;CFGR & (uint32_t)RCC_CFGR_SWS) != (uint32_t)0x08)
{
}
}
else
{ /* If HSE fails to start-up, the application will have wrong clock
configuration. User can add here some code to deal with this error */
}
}</pre>

<strong>四、STM32的HSE时钟</strong>

HSE是高速的外部时钟信号,可以由有源晶振或者无源晶振提供。频率为4-16MHz。

HSE最常用的是8M的无源晶振。当外部晶振为8M时,不需要对固件库中的系统时钟配置函数进行修改,但是,如果我们选择的外部晶振不是8M的,则需要对固件库中的系统时钟的配置做一修改。如我们所使用的外部晶振为12M,则需要做如下修改。

1、修改stm32f10x.h文件

打开stm32f10x.h文件,修改如下代码(119行)

#define HSE_VALUE ((uint32_t)8000000) //修改之前

#define HSE_VALUE ((uint32_t)12000000) //修改之后

2、修改system_stm32f10x.c中的系统时钟配置函数

打开system_stm32f10x.c文件,修改如下代码(1056行)

RCC-&gt;CFGR |= (uint32_t)(RCC_CFGR_PLLSRC_HSE | RCC_CFGR_PLLMULL9); //修改之前,HSE=8M,9倍频之后为8*9=72M

RCC-&gt;CFGR |= (uint32_t)(RCC_CFGR_PLLSRC_HSE | RCC_CFGR_PLLMULL6); //修改之后,HSE=12M,6倍频之后为12*6=72M

转自:<a href="http://www.cnblogs.com/Tangledice/p/7020598.html">Tangledice</a&gt;