STM32使用内部高速振荡器(HSI)通过锁相环PLL倍频到64MHZ之库函数实现方式

本文详细介绍了如何在STM32上将HSI通过PLL倍频至64MHz,包括系统时钟配置、时钟频率打印及系统初始化过程。通过具体代码实现,展示了STM32系统时钟的精确控制。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

获取STM32系统各时钟频率

一、配置系统时钟

/***************************************************************
*函数名: vSystem_Clock_Config
*描  述: 配置系统时钟
*说  明: 将HSI通过PLL倍频到64MHZ
*注  意: HSI通过PLL倍频最大只能倍频到64MHZ
***************************************************************/
void vSystem_Clock_Config(void)
{
	u32 startUpCount = 0, status = 0;


	RCC_DeInit();//Resets RCC default state
	RCC_HSICmd(ENABLE);//Enables HSI
	do
	{
		status = RCC_GetFlagStatus(RCC_FLAG_HSIRDY);//HSI ready or not
		startUpCount++;
	}
	while((status == RESET) || (startUpCount < HSE_STARTUP_TIMEOUT));
	
	if(status == SET)
	{
		FLASH_PrefetchBufferCmd(FLASH_PrefetchBuffer_Enable);//Enable Prefetch Buffer
		FLASH_SetLatency(FLASH_Latency_2);//Set code latency value Two Latency cycles
		
		RCC_HCLKConfig(RCC_SYSCLK_Div1);//HCLK=SYSCLK
		RCC_PCLK1Config(RCC_HCLK_Div1);//PCLK1/APB1=HCLK
		RCC_PCLK2Config(RCC_HCLK_Div1);//PCLK2/APB2=HCLK
		RCC_PLLConfig(RCC_PLLSource_HSI_Div2, RCC_PLLMul_16);//PLL clock=4M
		RCC_PLLCmd(ENABLE);//Enables PLL
		while(RCC_GetFlagStatus(RCC_FLAG_PLLRDY) == RESET);
		
		RCC_SYSCLKConfig(RCC_SYSCLKSource_PLLCLK);//System clock is PLLCLK
		while ((RCC->CFGR & (uint32_t)RCC_CFGR_SWS) != (uint32_t)0x08);
	}
	else
	{

	}
}

注意:
1.STM32系列HSI通过PLL倍频最大只能倍频到64MHZ。
2. 所用到的库有:
#include "stm32f10x_flash.h"
#include "stm32f10x_gpio.h"
#include "stm32f10x_rcc.h"
#include "stm32f10x_tim.h"
#include "misc.h"

二、打印输出系统各时钟频率

RCC_ClocksTypeDef RCC_CLK;

int main(void)
{	
	vSystem_Init();
	
	RCC_GetClocksFreq(&RCC_CLK);//Get chip frequencies
	#if ( USE_SEGGER_RTT_ENABLE > 0 )//Use segger rtt enable
	SEGGER_RTT_printf(0, "System Clock Source : %d\r\n", RCC_GetSYSCLKSource());
	SEGGER_RTT_printf(0, "APB1/PCLK1 : %dHZ\r\n", RCC_CLK.PCLK1_Frequency);
	SEGGER_RTT_printf(0, "APB2/PCLK2 : %dHZ\r\n", RCC_CLK.PCLK2_Frequency);
	SEGGER_RTT_printf(0, "SYSCLK     : %dHZ\r\n", RCC_CLK.SYSCLK_Frequency);
	SEGGER_RTT_printf(0, "HCLK       : %dHZ\r\n", RCC_CLK.HCLK_Frequency);
	#endif

	
	while(1)
	{
		vKeyBoard_Service_Handle();
		PAout(6) = 0;
		vDelay_ms(100);
		PAout(6) = 1;
		vDelay_ms(1000);
	}
}

三、系统初始化vSystem_Init()

static void vSystem_Init(void)
{
	SystemInit();
	vSystem_Clock_Config();
	vSysTick_Init();
	NVIC_PriorityGroupConfig(NVIC_PriorityGroup_4);
	vTIM_Init();
	vLCD1602_Init();
	LED_Init();
	vKEY_GPIO_Config();
	
		
	#if ( USE_SEGGER_RTT_ENABLE > 0 )//Use segger rtt enable
	SEGGER_RTT_Init();
	SEGGER_RTT_printf(0, "Build Times: %s  %s\r\n", __DATE__, __TIME__);
	SEGGER_RTT_printf(0, "STM32F103xx Start Running......\r\n\r\n");
	#endif
	
	#if ( USE_KEIL_MACRO_INFO_ENBALE > 0 )//Use Keil macro information enable 
	vKeil_Macro_Information();
	#endif	
}

四、运行结果

00> Build Times: Mar 14 2020  10:11:21
00> STM32F103xx Start Running......
00> 
00> System Clock Source : 8
00> APB1/PCLK1 : 64000000HZ
00> APB2/PCLK2 : 64000000HZ
00> SYSCLK     : 64000000HZ
00> HCLK       : 64000000HZ

在这里插入图片描述
在这里插入图片描述

### STM32 PLL倍频配置及工作原理 #### 配置PLL输入源 STM32锁相环(PLL)可以接收多种不同的时钟源作为其输入信号,这些时钟源包括内部高速振荡器(HSI),外部高速晶体/陶瓷谐振器(HSE)[^1]。 对于基于 HSI 进行倍频的情况,在默认状态下,HSI 提供大约 16 MHz 的频率给 PLL 输入端。为了使能并设置此路径,需调用特定的 HAL 库函数或直接操作寄存器来指定 PLL 源为 HSI 并开启它[^2]。 ```c RCC_OscInitTypeDef RCC_OscInitStruct = {0}; // ... RCC_OscInitStruct.OscillatorType = RCC_OSCILLATORTYPE_HSI; RCC_OscInitStruct.HSIState = RCC_HSI_ON; HAL_RCC_OscConfig(&RCC_OscInitStruct); ``` #### 设置PLL参数 PLL 内部有一个乘法因子 (MUL), 它决定了输出相对于输入被放大的程度;还有一个除法因子(DIV),用来调整进入 VCO 前的预分频值。当目标是将 HSI 调整至 64MHz 输出时,则需要计算合适的 M 和 N 参数组合使得最终得到期望的结果。 具体来说, 如果采用 HSI 作为基础频率(即 16 MHz),那么为了让 PLL 输出达到 64 MHz,可以选择适当的 M 和 N 来满足下面的关系: \[ \text{PLL Output Frequency} = (\frac{\text{Input Frequency}}{\text{DIV Value}})\times\text{(MUL Value)} \] 假设 DIV=16 及 MUL=4 就能满足上述条件: \[ 64\,\mathrm{MHz}=({\frac{{16}\,{\rm MHz}}{{16}}})×4 \] 实际编程中可以通过修改 `RCC_PLLMul` 和 `RCC_PLLDiv` 字段完成这一过程: ```c RCC_ClkInitStruct.PLL.PLLSource = RCC_PLLSOURCE_HSI; RCC_ClkInitStruct.PLL.PLLMUL = RCC_PLL_MUL4; RCC_ClkInitStruct.PLL.PLLDIV = RCC_PLL_DIV16; ``` #### 启动PLL并与系统时钟同步 一旦完成了前面提到的所有步骤之后,下一步就是激活PLL,并将其输出连接到系统的主时钟线上去替换原来的较低速度的时钟源。这一步同样涉及到对某些控制位的操作以及等待状态标志的变化以确认切换成功。 ```c if (HAL_RCC_OscConfig(&RCC_OscInitStruct) != HAL_OK){ Error_Handler(); } /* Activate the OverDrive to reach the 216 Mhz Frequency */ if (HAL_PWREx_EnableOverDrive() != HAL_OK){ Error_Handler(); } /* Switch System clock frequency and configure bus prescalers */ if (HAL_RCC_ClockConfig(&RCC_ClkInitStruct, FLASH_LATENCY_5) != HAL_OK){ Error_Handler(); } ``` 通过以上几个阶段的工作就可以实现从原始较慢的速度提升到了更高的处理能力水平上去了。值得注意的是在整个过程中还需要考虑到其他因素比如电源管理单元(PMU)的状态变化等可能影响到最后效果的因素。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值