STM32学习手记2——IO、时钟部分

STM32的时钟系统

STM32与MSP430类似,有多个内部、外部时钟源,并且可以自由选择外设的时钟源。

填写图片摘要(选填) 

​​​

内部时钟源包括:HSI高速内部时钟、LSI低速内部时钟、PLL内部锁相环倍频

外部时钟源包括:​HSE外部高速晶振(8M)、LSE外部低速时钟(32768)

PLL的时钟源可选择HSI/2 HSE 或者HSE/2,通过2~16倍频,最高输出不超过72M

​USB模块的时钟源必须是PLL或PLL分频获得。

​SYSCLK是系统主时钟,来源可以使PLL、HSE或者HSI。通过AHB将SYSCLK进行分频后,可供核心存储器、总线、内存、DMA使用;再经过8分频后,送入Cortex核心作为系统时钟,也就是systick。

APB(Advanced Peripheral Bus),片上外设总线。主要用于慢速片上外设与ARM核的通讯

​AHB(Advanced High performance Bus),高性能总线。主要用于系统高性能、高时钟速率模块间通信,。​

通过AHB分频的信号,还会进入APB1和APB2分频器,分别送给低速和高速外设使用。​

​在默认情况下,系统时钟在系统初始化函数SystemInit函数中的SetSysClock()函数实现。

​在使用某个外设或者内部模块的时候,必须先使能相应的时钟。如:

 RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA|RCC_APB2Periph_GPIOD, ENABLE);   //使能GPIO模块的时钟

​ RCC_APB2PeriphClockCmd()函数的作用是使能APB2分频器下挂的某个模块时钟,其中两个参数前一个代表要使能的模块,后一个则是ENABLE或者DISABLE。

官方库中默认是使用HSE(外部高速时钟)驱动PLL输出特定的时钟。如果板上有晶振,我们只需要定义晶振频率和将要得到的频率就可以了,库函数会为我们自动初始化。

外部高速晶振的频率范围为4~16MHz,定义晶振频率在stm32f10x.h文件中第119行定义,#define HSE_VALUE    ((uint32_t)8000000)  默认为8MHz.

系统时钟频率在system_stm32f10x.c文件中第110~115行中定义,把需要的频率取消注释,不要的频率注释掉就可以了.

​以上的都是用外部晶振的情况,只需要一点点定义就可以实现了,但是用HSI内部高速时钟的话我还没有发现有更直接的方法,所以就自己用库函数做了一下Init,具体代码如下:

RCC_DeInit(); //初始化RCC各寄存器

RCC_HSICmd(ENABLE); //使能内部HSI时

while(RCC_GetFlagStatus(RCC_FLAG_HSIRDY) == RESET); //等待设置成功

RCC_PLLConfig(RCC_PLLSource_HSI_Div2,RCC_PLLMul_12); //HSI/2时钟输入,倍频16,4*12=48M

RCC_HCLKConfig(RCC_SYSCLK_Div1); //设置AHB时钟

RCC_PCLK1Config(RCC_HCLK_Div1); //设置低速AHB时钟

RCC_PCLK2Config(RCC_HCLK_Div2); //设置高速AHB时钟

RCC_PLLCmd(ENABLE); //使能PLL

while(RCC_GetFlagStatus(RCC_FLAG_PLLRDY) == RESET); //等待使能成功

RCC_SYSCLKConfig(RCC_SYSCLKSource_PLLCLK); //选择PLL输出做为系统时钟

while(RCC_GetSYSCLKSource() != 0x08); //等待设置成功

然后下面就可以为各种外设时钟(例如GPIO)使能并使用了,这里值得一提的是,PLL输入只能得到HSI时钟的2分频后的频率,也就是说如果HSI设置为8M,则PLL输入只有4M.

我试验中还发现,在使用HSI作为PLL时钟源时,输出频率不得大于56M,否则STM32不会运行...

当然,内部RC震荡精度有限,在能使用晶振的情况下还是选择外部高速时钟.

GPIO的使用

STM32的GPIO:

STM32-M3共有6组GPIO:USART1-USART4。

初始化结构体​:

​ USART_InitStructure.USART_BaudRate = bound;//波特率9600;

USART_InitStructure.USART_WordLength = USART_WordLength_8b;                       //数据长度8bit

USART_InitStructure.USART_StopBits = USART_StopBits_1;//停止位1位

USART_InitStructure.USART_Parity = USART_Parity_No;//无校验位

USART_InitStructure.USART_HardwareFlowControl = USART_HardwareFlowControl_None;//无硬件流控制

USART_InitStructure.USART_Mode = USART_Mode_Rx | USART_Mode_Tx;             //发送、接收模式

​控制结构体:
 

控制寄存器:

 

猜你喜欢

转载自blog.csdn.net/laoponline/article/details/111049729