STM32学习week2

本文详细介绍了STM32F1的时钟系统,包括输入时钟源(HSI、HSE、LSI、LSE),锁相环的作用,以及SYS文件夹中的delay函数和GPIO的工作模式。特别强调了如何使用HAL库实现精确延时和GPIO的输入输出控制。

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

 本篇主要基于正点原子的stm32hal库教程的第26-50讲 

一、时钟树

如图为一个简化的 STM32F1 时钟系统。图中已经把我们主要关注几处标注出来。
A 部分表示其它电路需要的输入源时钟信号。
B 为一个特殊的振荡电路“PLL”,由几个部分构成。
C 为我们重点需要关注的 MCU 内的主时钟“SYSCLK”;AHB 预分频器将 SYSCLK 分频或不分频后分发给其它外设进行处理,包括到 F 部分的 Cortex-M 内核系统的时钟。
D、E 部分别为定 时器等外设的时钟源 APB1/APB2。
G 是 STM32 的时钟输出功能。
对于 STM32F1,输入时钟源(Input Clock)主要包括 HSI,HSE,LSI,LSE。其中,从
时钟频率来分可以分为高速时钟源和低速时钟源,其中 HSI、HSE 高速时钟,LSI 和 LSE 是低
速时钟。从来源可分为外部时钟源和内部时钟源,外部时钟源就是从外部通过接晶振的方式获
取时钟源,其中 HSE 和 LSE 是外部时钟源;其他是内部时钟源,芯片上电即可产生,不需要
借助外部电路。下面我们看看 STM32 的时钟源。
(1)2 个外部时钟源:
高速外部振荡器 HSE (High Speed External Clock signal)
 低速外部振荡器 LSE (Low Speed External Clock signal)
外接 32.768kHz 石英晶体,主要作用于 RTC 的时钟源。
(2)2 个内部时钟源:
高速内部振荡器 HSI(High Speed Internal Clock signal)
由内部 RC 振荡器产生,频率为 8MHz。
低速内部振荡器 LSI(Low Speed Internal Clock signal)
由内部 RC 振荡器产生,频率为 40kHz。
锁相环是自动控制系统中常用的一个反馈电路,在 STM32 主控中,锁相环的作用主要有
两个部分:输入时钟净化和倍频。前者是利用锁相环电路的反馈机制实现,后者我们用于使芯
片在更高且频率稳定的时钟下工作。
二、SYSTEM 文件夹介绍
1、deley 文件夹代码介绍
当需要 delay_ms 和 delay_us 支持操作系统(OS)的时候,我们需要用到 3 个宏定义和 4 个
函数,宏定义及函数代码如下:
宏定义:delay_osrunning,用于标记 OS 是否正在运行,当 OS 已经开始运行时,该宏定义
值为 1,当 OS 还未运行时,该宏定义值为 0。
宏定义:delay_ostickspersec,用于表示 OS 的时钟节拍,即 OS 每秒钟任务调度次数。
宏定义:delay_osintnesting,用于表示 OS 中断嵌套级别,即中断嵌套次数,每进入一个中
断,该值加 1,每退出一个中断,该值减 1。
函数:delay_osschedlock,用于 delay_us 延时,作用是禁止 OS 进行调度,以防打断 us 级
延时,导致延时时间不准。
函数:delay_osschedunlock,同样用于 delay_us 延时,作用是在延时结束后恢复 OS 的调度,
继续正常的 OS 任务调度。
函数:delay_ostimedly,调用 OS 自带的延时函数,实现延时。该函数的参数为时钟节拍数。
函数:SysTick_Handler,则是 systick 的中断服务函数,该函数为 OS 提供时钟节拍,同时
可以引起任务调度。

2、delay_init 函数
该函数用来初始化 2 个重要参数:g_fac_us 以及 g_fac_ms;同时把 SysTick 的时钟源选择 为外部时钟,如果需要支持操作系统(OS),只需要在 sys.h 里面,设置 SYS_SUPPORT_OS 宏 的值为 1 即可,然后,该函数会根据 delay_ostickspersec 宏的设置,来配置 SysTick 的中断时间, 并开启 SysTick 中断。
SysTick 是 MDK 定义了的一个结构体(在 core_m3.h 里面),里面包含 CTRL、LOAD、
VAL、CALIB 等 4 个寄存器。
SysTick->CTRL定义如下:
SysTick->LOAD定义如下:

SysTick->VAL定义如下:

3、delay_us 函数

该函数用来延时指定的 us,其参数 nus 为要延时的微秒数。delay_osschedlock和delay_osschedunlock 是 OS 提供的两个函数,用于调度上锁和解锁,这里为了防止 OS 在 delay_us 的时候打断延时,可能导致的延时不准,所以我们利用这两个函数来实现免打断,从而保证延时精度。
4、delay_ms 函数
该函数是用来延时指定的 ms 的,其参数 nms 为要延时的毫秒数。该函数其实就是多次调用 delay_us 函数,来实现毫秒级延时的。
5、HAL 库延时函数 HAL_Delay

HAL 库实现延时功能非常简单,首先定义了一个 32 位全局变量 uwTick,在 Systick 中断服务函数 SysTick_Handler 中通过调用 HAL_IncTick 实现 uwTick 值不断增加,也就是每隔 1ms增加uwTickFreq,而 uwTickFreq 默认是 1。而 HAL_Delay 函数在进入函数之后先记录当前uwTick 的值,然后不断在循环中读取 uwTick 当前值,进行减运算,得出的就是延时的毫秒数,
整个逻辑非常简单也非常清晰。

三、GPIO

GPIO 是控制或者采集外部器件的信息的外设,即负责输入输出。它按组分配,每组 16 个 IO 口,组数视芯片而定。STM32F103ZET6 芯片是 144 脚的芯片,具有 GPIOA、GPIOB、GPIOC、 GPIOD、GPIOE、GPIOF 和 GPIOG 七组 GPIO 口,共有 112 个 IO 口可供我们编程使用。

GPIO 有八种工作模式,分别是:
1、输入浮空
2、输入上拉
3、输入下拉
4、模拟功能
5、开漏输出
6、推挽输出
7、开漏式复用功能
8、推挽式复用功能

输入浮空模式:上拉/下拉电阻为断开状态,施密特触发器打开,输出被禁止。输入浮空模
式下,IO 口的电平完全是由外部电路决定。如果 IO 引脚没有连接其他的设备,那么检测其输
入电平是不确定的。该模式可以用于按键检测等场景。

输入上拉模式:上拉电阻导通,施密特触发器打开,输出被禁止。在需要外部上拉电阻的
时候,可以使用内部上拉电阻,这样可以节省一个外部电阻,但是内部上拉电阻的阻值较大,
所以只是“弱上拉”,不适合做电流型驱动。

输入下拉模式:下拉电阻导通,施密特触发器打开,输出被禁止。在需要外部下拉电阻
的时候,可以使用内部下拉电阻,这样可以节省一个外部电阻,但是内部下拉电阻的阻值较
大,所以不适合做电流型驱动。

模拟功能:上下拉电阻断开,施密特触发器关闭,双 MOS 管也关闭。其他外设可以通过模
拟通道输入输出。该模式下需要用到芯片内部的模拟电路单元单元,用于 ADC、DAC、MCO
这类操作模拟信号的外设。

开漏输出模式:STM32 的开漏输出模式是数字电路输出的一种,从结果上看它只能输出低
电平 Vss 或者高阻态,常用于 IIC 通讯(IIC_SDA)或其它需要进行电平转换的场景。

推挽输出模式:STM32 的推挽输出模式,从结果上看它会输出低电平 VSS 或者高电平
VDD。推挽输出跟开漏输出不同的是,推挽输出模式 P-MOS 管和 N-MOS 管都用上。

开漏式复用功能:一个 IO 口可以是通用的 IO 口功能,还可以是其他外设的特殊功能引脚, 这就是 IO 口的复用功能。一个 IO 口可以是多个外设的功能引脚,我们需要选择作为其中一个 外设的功能引脚。当选择复用功能时,引脚的状态是由对应的外设控制,而不是输出数据寄存器。除了复用功能外,其他的结构分析请参考开漏输出模式。另外在开漏式复用功能模式下,施密特触发器也是打开的,我们可以读取 IO 口的电平状态,同时外设可以读取 IO 口的信息。

推挽式复用功能:复用功能介绍请查看开漏式复用功能。
STM32F1 每组(这里是 A~D)通用 GPIO 口有 7 个 32 位寄存器控制,包括 :
2 个 32 位端口配置寄存器(CRL 和 CRH)
2 个 32 位端口数据寄存器(IDR 和 ODR)
1 个 32 位端口置位/复位寄存器 (BSRR)
1 个 16 位端口复位寄存器(BRR)
1 个 32 位端口锁定寄存器 (LCKR)

  

评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值