stm32学习总结:定时器(1)基本定时器

一、 基本概念

定时器是一种计时的工具,它具有延时、频率测量、PWM输出、电机控制及编码接口等功能。
STM32F103微控制器内部集成了多个可编程定时器,可以分为基本定时器(TIM6和TIM7)、通用定时器(TIM2~TIM5)和高级定时器(TIM1、TIM8)3种类型。从功能上看,基本定时器的功能是通用定时器的子集,而通用定时器的功能又是高级定时器的一个子集。

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

在STM32F103中,基本定时器TIM6、TIM7各自都包含一个16位自动装载计数器,能够通过各自的可编程预分频器驱动,这两个定时器相互独立,不共享任何资源。

二、 时基单元

在这里插入图片描述

上图为基本定时器的结构图,其中红色框线内为时基单元,主要由预分频器、计数器和自动重装载寄存器构成。该模块的时钟源为系统内部时钟CK_INT(72MHz),直接作为预分频器(PSC)的时钟源(CK_PSC),经过预分频后输入至计数器(CNT)对预分频后的时钟进行计数,计时时钟每来一个上升沿,计数器+1,直到达到最大计数值,即65535。最大值后再增加则会回到0,从头开始计数。自动重装寄存器存储了CNT计数器需要计数的值,当计数器计数值等于自动重装值,则会产生中断信号,并重置计数器。
更新中断即为所产生的中断信号UI。更新中断之后就会通往NMIC,再配置好NMIC的定时器通道,更新中断就可得到CPU相应的终端服务程序。更新事件为该模块产生的事件信号U,触发内部其他电路工作。

三、 工作流程

内部时钟CK_INT为唯一时钟源,当TIMx_CR1寄存器的CEN位被置为1时CK_INT为预分频器提供时钟,否则无时钟产生。预分频器的值(PSC)+1为分频数,CK_CNT =CK_PSC/(PSC+1)。预分频可以以系数介于1至65536之间的任意数值对计数器时钟分频。它是通过一个16位寄存器(TIMx_PSC)的计数实现分频。因为TIMx_PSC控制寄存器具有缓冲,可以在运行过程中改变它的数值,新的预分频数值将在下一个更新事件时起作用。
在这里插入图片描述

上图为PSC由0变到1的内部时序变化,红线左侧PSC=0,即不分频,右侧PSC=1,即2分频。当CNT_EN为高电平时,CK_CNT开始产生,计数器寄存器开始计数,每次增加1,达到计数设定值时会产生一个更新事件,即计数器清零重新计数。由于预分频器缓冲器(也叫影子寄存器)的存在,虽然在箭头处更改了分频系数,但并没有立即生效,而是在产生更新事件时生效,这样可以保护一个周期自动重装值(ARR+1)数据的完整性,也可以说明实际传输数据就是影子寄存器。

四、 相关寄存器

  1. TIM6和TIM7控制寄存器1(TIMx_CR1)
    在这里插入图片描述

CEN:计数器使能
UDIS:禁止更新
URS:更新请求源
OPM:单脉冲模式
ARPE:自动重装载预装载使能
2. TIM6和TIM7控制寄存器2(TIMx_CR2)
在这里插入图片描述

MMS:主模式选择
3. TIM6和TIM7 DMA/中断使能寄存器(TIMx_DIER)
在这里插入图片描述

UIE:更新中断使能
UDE:更新DMA请求使能
4. TIM6和TIM7状态寄存器(TIMx_SR)
在这里插入图片描述

UIF:更新中断标志
5. TIM6和TIM7事件产生寄存器(TIMx_EGR)
在这里插入图片描述

UG:产生更新事件
6. TIM6和TIM7计数器(TIMx_CNT)
在这里插入图片描述

CNT[15:0]:计数器数值
7. TIM6和TIM7预分频器(TIMx_PSC)
在这里插入图片描述

PSC[15:0]:预分频器数值
8. TIM6和TIM7自动重装载寄存器(TIMx_ARR)
在这里插入图片描述

ARR[15:0]:自动重装载数值

五、 代码分析

  1. Timer.c
#include "stm32f10x.h"                  // Device header
void Tim6_init(void)
{
    RCC_APB1PeriphClockCmd(RCC_APB1Periph_TIM6, ENABLE);//使能外设时钟

    TIM_TimeBaseInitTypeDef TIM_TimeBaseInitStructure;
    TIM_TimeBaseInitStructure.TIM_ClockDivision = 72 - 1;//分频数:72
    TIM_TimeBaseInitStructure.TIM_Period = 1000 - 1;//计数值:1000
    
    TIM_TimeBaseInit(TIM6,&TIM_TimeBaseInitStructure);//初始化时基单元
    TIM_Cmd(TIM6,ENABLE);//启动定时器
    
    TIM_ITConfig(TIM6,TIM_IT_Update,ENABLE);//TIM6中断使能

    NVIC_InitTypeDef NVIC_InitStruct; 
    NVIC_InitStruct.NVIC_IRQChannel=TIM6_IRQn;
    NVIC_InitStruct.NVIC_IRQChannelCmd=ENABLE;
    NVIC_InitStruct.NVIC_IRQChannelPreemptionPriority=0;
    NVIC_InitStruct.NVIC_IRQChannelSubPriority=3;//NVIC参数设定

    NVIC_Init(&NVIC_InitStruct);
}
  1. 中断函数(包含在main.c中)
void  TIM6_IRQHandler(void)//TIM6中断函数
{
    if ( TIM_GetITStatus(TIM6, TIM_IT_Update) != RESET ) //检测是否到达定时数
    {   
        Num ++;
        TIM_ClearITPendingBit(TIM6 , TIM_FLAG_Update);//切记要手动清除标志位!!!
    }           

}
  1. main.c
#include "stm32f10x.h"                  // Device header
#include "Delay.h"
#include "OLED.h"
#include "Timer.h"

uint16_t Num;//计次数

int main(void)
{
    OLED_Init();
    Tim6_init();//TIM6初始化
    
    OLED_ShowString(1, 1, "Num:");//固定显示部分
    
    while (1)
    {
        OLED_ShowNum(1, 5, Num, 5);//显示次数
    }
}

六、 总结

本文是TIM模块的第一部分,围绕基本定时器进行介绍,介绍了该单元的时钟源、工作原理及相关寄存器,并结合例程分析了基本定时器的使用方法。

参考链接

  1. STM32——TIM简介与TIM中断_stm32 tim-CSDN博客
  2. STM32-定时器系列(一)基本定时器_stm32基本定时器-CSDN博客
  3. STM32—定时器(TIM)_基本定时_stm32 tim复位-CSDN博客
  4. 关于STM32定时器中的影子寄存器见解_stm32影子寄存器-CSDN博客
  5. stm32 基本定时器的使用-CSDN博客
  • 9
    点赞
  • 26
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值