大数跨境
0
0

STM32F407基础教程9——定时器基本概念与库函数

STM32F407基础教程9——定时器基本概念与库函数 Easy单片机
2025-06-11
2
导读:STM32F407通用定时器结构与库函数

一、STM32F407定时器简介

STM32F407系列最多包含14个定时器(TIM1~TIM14)。分为高级控制定时器、通用定时器和基本定时器。

  • 基本定时器(TIM6、TIM7)功能最为简单,主要用于通用计时、驱动数模转换器。

  • 通用定时器(TIM2~TIM5,TIM9~TIM14)功能最为丰富,数量众多,可用于定时,测量外部信号的脉冲宽度、频率或周期,产生单脉冲、高精度脉宽调制信号等;支持编码器接口,用于电机位置和速度检测。

  • 高级控制定时器(TIM1、TIM8)在通用定时器功能的基础上,增加了专为电机控制、数字电源转换等高级特性。

本文及后续的定时器内容皆以通用定时器为例说明。

二、通用定时器结构(TIM2~TIM5,TIM9~TIM14)

虽然通用定时器的功能众多,但都可归为三大功能:定时、输入捕获、比较输出。这三大功能也是由定时器结构决定的,通用定时器的结构框图可分为三大部分:时基单元、输入捕获、输出比较。具体见下图。

本文先介绍时基单元,时基单元见下图。请结合图来阅读以下内容。

1、时基单元

时基单元包括计数器CNT预分频器PSC自动重装载寄存器ARR

(1)计数器CNT是一个16位或32位(TIM2和TIM5)的寄存器,此寄存器可采用递增方式计数,也可采用递减方式计数,每来一个时钟信号CK_CNT,计数器的值+1或-1。

(2)计数器CNT的时钟信号CK_CNT来自于预分频器PSC的输出。预分频器PSC是一个16位的寄存器,可对预分频器时钟CK_PSC进行分频,分频系数介于1~65536。

(3)预分频器时钟CK_PSC由内部时钟CK_INT提供。内部时钟CK_INT来自于RCC的定时器时钟TIMx_CLK(84MHz)。

(4)自动重装载寄存器ARR是一个16位的寄存器,可设置为1~65536之间任何一个数。

2、计数模式

  • 递增(向上)计数模式:计数器从0开始计数到自动装载值(自动重装载寄存器ARR里的值),然后又重新从0开始计数并且产生一个计数器溢出事件和更新中断。

  • 递减(向下)计数模式:计数器从自动装载值(自动重装载寄存器ARR里的值)开始向下计数到0,然后从自动装载值重新开始,并产生一个计数器向下溢出事件和更新中断。

  • 中心对齐模式(递增/递减计数):计数器从0开始计数到自动重载值-1,产生一个计数器溢出事件,然后从自动重载值开始向下计数到1并且产生一个计数器溢出事件;然后再从0开始重新计数。

3、定时器时钟源TIMx_CLK

时钟源TIMx_CLK84MHz。具体设置可见system_stm32f4xx.c文件。除了高级定时器,其他定时器都挂载在APB1总线上。

4、定时时间计算

计数器时钟信号CK_CNT的频率为:

那么1/CK_CNT即为计一个数的时间。则定时时间为:

举例:TIMx_CLK为84MHz,若分频器PSC取值8399,则CK_CNT为10KHz。那么计数器计一个数的时间为0.1ms。若定时器时间为1s,则计数器应计10000个数,注意计数器从0开始计数,那么ARR应取值9999。

三、定时器库函数

1、时基初始化库函数

void TIM_TimeBaseInit(TIM_TypeDef*TIMx, TIM_TimeBaseInitTypeDef* TIM_TimeBaseInitStruct);

参数1:TIMx,x=1~14,选择定时器

参数2:结构体指针,用于初始化定时器相关参数

typedef struct 

uint16_t TIM_Prescaler; //PSC预分频值,1~65536

uint16_t TIM_CounterMode; //计数模式,向上计数/向下计数

uint16_t TIM_Period; //自动重装载值,1~65536

uint16_t TIM_ClockDivision; //用来设置时钟分频因子

uint8_t TIM_RepetitionCounter; //该参数只用于 TIM1和TIM8

} TIM_TimeBaseInitTypeDef;

库函数使用示例:以定时器TIM2为例,定时1s

TIM_TimeBsaeInitTypeDef  TIM_TimeBsaeStructure;//定义结构体

TIM_TimeBsaeStructure.TIM_Period = 10000-1;//设置自动重装载值

TIM_TimeBsaeStructure.TIM_Prescaler = 8400-1;//设置预分频值

TIM_TimeBaseStructure.TIM_ClockDivision=TIM_CKD_DIV1;//1分频即可

TIM_TimeBsaeStructure.TIM_Mode = TIM_CounterMode_Up;//向上计数,Up换成Down为向下计数

TIM_TimeBaseInit(TIM2, & TIM_TimeBsaeStructure);//完成初始化

2、使能定时器库函数

void TIM_Cmd(TIM_TypeDef * TIMx, FunctionalState NewState)

参数1:TIMx,x=1~14,选择定时器

参数2:ENABLE使能定时器;DISABLE关闭定时器

使用方法:TIM_Cmd(TIM2, ENABLE); //使能TIM2

3、使能定时器中断库函数

void TIM_ITConfig(TIM_TypeDef *TIMx, u16 TIM_IT, FunctionalState NewState)

参数1:TIMx,x=1~14,选择定时器

参数3:ENABLE使能定时器中断;DISABLE关闭定时器中断

参数2:TIM_IT中断类型,TIM_IT取值如下:

TIM_IT_Updata; //更新中断

TIM_IT_CC1; //捕获、比较中断

TIM_IT_Trigger; //触发中断

使用方法:使能TIM2更新中断

TIM_ITConfig(TIM3,TIM_IT_Update,ENABLE );

4、获取中断标志位库函数

ITStatus TIM_GetITStatus(TIM_TypeDef* TIMx, uint16_t TIM_IT)

参数1:TIMx,x=1~14,选择定时器

参数2:TIM_IT中断类型,取值同上。

返回值:SET,表示对应的中断已触发;RESET,表示对应的中断未触发。

使用方法:获取TIM2的捕获比较中断

if(TIM_GetITStatus(TIM2,TIM_IT_CC1) == SET);

5、清除中断标志位库函数

void TIM_ClearITPendingBit(TIM_TypeDef* TIMx, u16 TIM_IT)

参数见上。

使用方法:清除TIM2的捕获比较中断标志位

TIM_ClearITPendingBit(TIM2,TIM_IT_CC1);

【声明】内容源于网络
0
0
Easy单片机
本公众号专注于单片机技术开发领域。用于记录和分享单片机开发相关技术知识,学习笔记,设计示例和基础教程。包括C/C++、51单片机、STM32单片机、PCB设计等。
内容 62
粉丝 0
Easy单片机 本公众号专注于单片机技术开发领域。用于记录和分享单片机开发相关技术知识,学习笔记,设计示例和基础教程。包括C/C++、51单片机、STM32单片机、PCB设计等。
总阅读3
粉丝0
内容62