STM32 TIM定时中断

总体介绍

TIM(Timer)定时器是STM32中功能最强大,结构最复杂的一个外设,以下对其做一下简介(以stm32为例):

  • TIM可以对输入的时钟进行计数,并在数值达到设定值时触发中断。
  • 在STM32中定时器的基准时钟一般都是主频72MHz,并且以16位计数器,预分频器,自动重装寄存器为时基单元,在72MHz计数时钟下可以实现最大59.65s的定时。同时STM32定时器支持级联模式,可实现更长时间的定时。(当两个定时器级联时就可产生8千年多的定时)
  • TIM不仅具备基本的定时中断功能,而且还包括内外时钟源选择,输入捕获,输出比较,编码器接口,主从触发模式等多种功能。
  • STM32的定时器,根据复杂程度好应用场景分为了高级定时器,通用定时器,基本定时器三种类型。

定时器类型

类型编号总线功能
高级定时器TIM1,TIM8APB2通用功能,重复计数器,互补输出,刹车输入,死区生成等
通用定时器TIM2~TIM5APB1基本定时器功能,时钟源选择,输入捕获,输出比较,编码器接口,主从触发模式等
基本定时器TIM6,TIM7APB1定时中断,主从模式触发DAC

当然也存在TIM9,TIM10等只是一般情况下用不到,同时也不是所有的STM32单片机都有所有的TIM外设,如STM32F103C8T6只有TIM1~TIM4这4个定时器。

定时中断

定时中断的基本结构

在这里插入图片描述

定时中断的代码

官方的TIM函数

要想自己配置TIM就需要了解官方封装好的库函数,下面介绍部分函数的功能(了解即可)

函数名称功能
TIM_DeInit恢复缺省配置
TIM_TimeBaseInit时基单元初始化
TIM_TimeBaseStructInit赋给结构体变量一个默认值
TIM_Cmd使能计数器
TIM_ITConfig使能中断输出信号
TIM_InternalClockConfig选择内部时钟
TIM_ITRxExternalClockConfig选择ITRx其他定时器的时钟
TIM_TIxExternalClockConfig选择TIx捕获通道的时钟
TIM_ETRClockMode1Config选择ETR通过外部时钟1输入的时钟
TIM_ETRClockMode2Config选择ETR通过外部时钟2输入的时钟
TIM_ETRConfig单独配置ETR引脚的预分频器,极性,滤波器
TIM_PrescalerConfig单独配置预分频值
TIM_CounterModeConfig改变计数器的计数模式
TIM_ARRPreloadConfig自动重装器预装功能配置
TIM_SetCounter给计数器写入一个值
TIM_SetAutoreload给自动重装器写入一个值
TIM_GetCounter获取当前计数器的值
TIM_GetPrescaler获取当前预分频器的值

配置中断函数

这里以配置TIM2(通用定时器为例),首先我们需要在keil软件中编写Timer的.c和.h文件。将基本结构中的每一步打通即可完成Timer的函数配置。

  1. 开启RCC时钟
  2. 选择时基单元的时钟源(对于定时中断选择内部时钟源即可)
  3. 配置时基单元(ARR,PSC,CNT模式等,用结构体即可配置)
  4. 配置输入中断控制,允许更新中断输出到NVIC
  5. 配置NVIC,在NVIC中打开定时器的中断通道,并配置一个优先级
  6. 运行控制
  7. 上面配置完成之后,还需要使能计数器,否则计数器无法运行,最后写一个中断函数,这样每个一段时间中断函数就可自动运行了(计数器有使能和失能两个状态,使能是开启的意思,失能则是关闭)
.c文件:
#include "stm32f10x.h"                  // Device header

void Timer_Init(void)
{
	RCC_APB1PeriphClockCmd(RCC_APB1Periph_TIM2, ENABLE);//开启时钟
	
	TIM_InternalClockConfig(TIM2);
	
	TIM_TimeBaseInitTypeDef TIM_TimeBaseInitStructure;     //TIM结构体
	TIM_TimeBaseInitStructure.TIM_ClockDivision = TIM_CKD_DIV1;
	TIM_TimeBaseInitStructure.TIM_CounterMode = TIM_CounterMode_Up;
	TIM_TimeBaseInitStructure.TIM_Period = 10000 - 1;     
	TIM_TimeBaseInitStructure.TIM_Prescaler = 7200 - 1;   //这个值和上一行的值可以自己改变玩玩,体会一下不同
	TIM_TimeBaseInitStructure.TIM_RepetitionCounter = 0;
	TIM_TimeBaseInit(TIM2, &TIM_TimeBaseInitStructure);
	
	TIM_ClearFlag(TIM2, TIM_FLAG_Update);// 清除更新时的中断标志位,防止更新时程序直接进入中断
	TIM_ITConfig(TIM2, TIM_IT_Update, ENABLE);
	
	NVIC_PriorityGroupConfig(NVIC_PriorityGroup_2);
	
	NVIC_InitTypeDef NVIC_InitStructure;                //NVIC结构体
	NVIC_InitStructure.NVIC_IRQChannel = TIM2_IRQn;
	NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE;
	NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 2;//优先级
	NVIC_InitStructure.NVIC_IRQChannelSubPriority = 1;//相应优先级
	NVIC_Init(&NVIC_InitStructure);
	
	TIM_Cmd(TIM2, ENABLE);
}


void TIM2_IRQHandler(void)    //TIM2的中断函数名称,不能更改,不需要声明,同时这个函数也可放到main.c中
{
	if (TIM_GetITStatus(TIM2, TIM_IT_Update) == SET)  //检查中断标志位
	{ //括号里添加自己所需要的中断代码
		

		TIM_ClearITPendingBit(TIM2, TIM_IT_Update);//清除标志位
	}
}


.h文件
#ifndef __TIMER_H
#define __TIMER_H

void Timer_Init(void);

#endif

编写并添加好Timer.c和Timer.h文件后,在编写主函数时需要在int mian(void)函数中加上Timer_Init();初始化中断。

  • 18
    点赞
  • 96
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值