9-定时器系统

9.1 定时器系统简介

在所有的定时器中,TIM1和TIM8的功能最多。通用和基本定时器在结构上都有一定的简化。所以本章就以高级定时器为例讲解:

9.1.1 定时器概述

定时器在检测、控制领域有广泛应用,可作为应用系统运行的控制节拍,实现信号检测、控制、输入信号周期测量或电机驱动等功能。在很多的应用场合,都会用到定时器,因此定时器系统是现在微控制器中的一个不可缺少的组成部分。
定时器有很多用途,包括基本定时功能、生成输出波形(输出比较、PWM和带死区插入的互补PWM)和测量输入信号的脉冲宽度(输入捕抓)等.
STM32F429共有14个定时器,包括2个高级定时器(TIM1、TIM8),10个通用定时器(TIM2-5、TIM9~14,以及2个基本定时器分别是TIM6和TIM7)。这里面2和5是32位定时器,,其他的都是16位的。具体可看下图:
9-定时器系统_第1张图片

9.1.2 定时器结构

在这里插入图片描述
9-定时器系统_第2张图片
TIM1和TIM8结构如下图:
9-定时器系统_第3张图片
9-定时器系统_第4张图片高级定时器内部结构图如下:

9-定时器系统_第5张图片

9.1.3 时钟源

定时器计数需要计数器时钟,可由下列时钟源提供:
① 内部时钟(CK_INT)源模式。
② 外部时钟源模式1:外部输入引脚。
③ 外部时钟源模式2:外部触发输入ETR。
④ 编码器模式。
具体如下图结构:
9-定时器系统_第6张图片

定时器计数时钟源

9-定时器系统_第7张图片

1.内部时钟源模式

9-定时器系统_第8张图片

2.外部时钟源模式1

9-定时器系统_第9张图片

3.外部时钟源模式2

9-定时器系统_第10张图片

4.编码器模式

将TI1FP1和TI2FP2信号的电平状态的变化作为定时器时钟源。这一模式主要用于测量光电正交编码器输出脉冲数,以及测量电机转速和方向。

9.2 基本定时功能

9.2.1 时基单元

9-定时器系统_第11张图片

1、 定时器时基单元

9-定时器系统_第12张图片

9.2.2 计数模式

计数模式

9-定时器系统_第13张图片

1、递增计数模式

9-定时器系统_第14张图片

2、递减计数模式

9-定时器系统_第15张图片

3、中央对齐计数模式(时钟分频因子=1 ARR=6)

9-定时器系统_第16张图片

9.3 捕抓/比较功能

STM32F429微控制器的高级定时器和通用定时器中有输入捕抓通道和输出比较通道

1、输入捕抓通道:

   1 ) 、频率测量、PWM信号周期、占空比测量,以及霍尔传感器输出信号测量等。
   2 ) 、测量光电正交编码器输出信号,实现电机转速的测量。

2、输出比较通道:

实现PWM信号输出、6步PWM信号生成,用于电机控制。

9.3.1 输入捕抓/比较输出通道

1、输入捕抓通道

9-定时器系统_第17张图片

2、输出比较通道

9-定时器系统_第18张图片

9.3.2 输入捕抓模式

9-定时器系统_第19张图片
9-定时器系统_第20张图片
在使用输入捕抓通道1,当检测到TI1引脚上输入的信号出现上升沿时,将计数器的值捕抓到TIMx_CCR1中。具体操作步骤如下:

1.选择输入捕抓模式,IC1映射到TI1上
2.设定输入信号边沿检测的滤波功能(防抖动)
3.选择边沿触发方式
4.对输入预分频器进行编程
5.使能输入捕抓功能
6.设置捕抓中断和DMA请求

当连续两次捕抓同一输出信号的连续两个边沿跳变,两次得到的计数寄存器值分别为C1和C2(假设C1和C2计数期间没有溢出事件),那么这一输入信号的周期:

((C2-C1)/CK_CNT)/输入捕抓通道预分频系数。

PWM波的周期测量:

9-定时器系统_第21张图片

9.3.3 PWM输出模式

9-定时器系统_第22张图片
9-定时器系统_第23张图片

比较模式:

9-定时器系统_第24张图片

9.3.4 编码器接口模式

9-定时器系统_第25张图片
在编码器模式下,计数器会根据增量编码器的速度和方向自动进行修改,因此计数器内容始终表示编码器的位置。计数方向对应于定时器所连传感器的轴旋转方向。
不同编码器模式下的计数方式如下图:
9-定时器系统_第26张图片
9-定时器系统_第27张图片

9.4 定时器典型应用步骤及常用库函数

9.4.1 基本定时功能应用步骤

①使能定时器时钟。

RCC_APB1PeriphClockCmd();

②初始化定时器,配置ARR,PSC。

TIM_TimeBaseInit();

③开启定时器中断,选择中断请求事件并配置NVIC。

       void TIM_ITConfig(TIM_TypeDef* TIMx, uint16_t TIM_IT, FunctionalState  NewState);
   NVIC_Init();

④使能定时器。

TIM_Cmd();

⑤编写中断服务函数。

  TIMx_IRQHandler();

9.4.2 输入捕抓模式应用步骤

①使能定时器时钟和GPIO时钟
②初始化定时器输入捕抓通道引脚
③初始化定时器测量时钟
④设置输入捕抓通道
⑤选择定时器复位触发源
⑥开启定时器中断
⑦使能定时器
⑧编写中断服务函数

9.4.3 PWM输出应用步骤

①使能定时器时钟
②初始化定时器比较输出通道引脚
③定义PWM波的周期
④设置比较输出通道
⑤使能定时器
⑥开启定时器中断

9.4.4 编码器接口应用步骤

①使能定时器时钟
②初始化定时器编码器接口输入通道引脚
③定义编码器接口的计数值溢出值
④设置定时器编码器接口模式
⑤开启定时器中断
⑥使能定时器
⑦编写测量速度应用程序

9.4.5 常用库函数

9-定时器系统_第28张图片
9-定时器系统_第29张图片

9.5 应用实例

9.5.1 定时器控制实现灯闪烁

1.编程要点

9-定时器系统_第30张图片

2.主程序

9-定时器系统_第31张图片

3.定时器初始化函数

9-定时器系统_第32张图片
9-定时器系统_第33张图片

4、定时器中断服务函数

9-定时器系统_第34张图片

9.5.2 直流电机调速控制

1.编程要点

9-定时器系统_第35张图片

2.主程序

9-定时器系统_第36张图片

3.定时器输出PWM波初始化函数

9-定时器系统_第37张图片
9-定时器系统_第38张图片

4.更改占空比

9-定时器系统_第39张图片

5 代码


#include "bsp_tim_Encoder.h"



void TIM_Config_Encoder(void)
{
	GPIO_InitTypeDef 	GPIO_InitStructure;
	TIM_TimeBaseInitTypeDef  TIM_TimeBaseStructure;
	TIM_ICInitTypeDef  TIM_ICInitStructure;
	 NVIC_InitTypeDef NVIC_InitStructure; 
  /*-------------------第1步--------------------*/	
	//使能定时器时钟和相关GPIO时钟
  RCC_APB1PeriphClockCmd(RCC_APB1Periph_TIM3, ENABLE); 
	RCC_AHB1PeriphClockCmd (RCC_AHB1Periph_GPIOC, ENABLE); 
  
	/*-------------------第2步--------------------*/
	//初始化定时器编码器接口输入通道引脚
	/* 定时器复用引脚 */
	GPIO_PinAFConfig(GPIOC,GPIO_PinSource6,GPIO_AF_TIM3); 
	GPIO_PinAFConfig(GPIOC,GPIO_PinSource7,GPIO_AF_TIM3); 
	/* 配置定时器输入脚 */															   
	GPIO_InitStructure.GPIO_Pin = GPIO_Pin_6|GPIO_Pin_7;	
	GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF;    
	GPIO_InitStructure.GPIO_PuPd = GPIO_PuPd_UP;
	GPIO_Init(GPIOC, &GPIO_InitStructure);		
	/*-------------------第3步--------------------*/	
	//定义编码器旋转一圈的计数值溢出值,用于计算圈数
  TIM_TimeBaseStructure.TIM_Period = 4000-1; 	
  TIM_TimeBaseStructure.TIM_Prescaler = 0;	
  TIM_TimeBaseStructure.TIM_CounterMode=TIM_CounterMode_Up;	 // 计数方式
	TIM_TimeBaseStructure.TIM_ClockDivision=TIM_CKD_DIV1;	
	TIM_TimeBaseInit(TIM3, &TIM_TimeBaseStructure);// 初始化定时器
	
	/*-------------------第4步--------------------*/
	// 编码器模式设置          
	TIM_EncoderInterfaceConfig(TIM3,TIM_EncoderMode_TI12,TIM_ICPolarity_Falling, TIM_ICPolarity_Falling);//编码器模式3

  TIM_ICInitStructure.TIM_Channel = TIM_Channel_1;
  TIM_ICInitStructure.TIM_ICPolarity = TIM_ICPolarity_Falling;
  TIM_ICInitStructure.TIM_ICSelection = TIM_ICSelection_DirectTI;//
  TIM_ICInitStructure.TIM_ICPrescaler = TIM_ICPSC_DIV1;
	TIM_ICInitStructure.TIM_ICFilter = 6;//滤波器值,去输入信号抖动
	TIM_ICInit(TIM3, &TIM_ICInitStructure);

	/*-------------------第5步--------------------*/
	//定时器中断配置
	NVIC_PriorityGroupConfig(NVIC_PriorityGroup_0);			
	NVIC_InitStructure.NVIC_IRQChannel = TIM3_IRQn; // 设置中断来源		
	NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 0;	// 设置抢占优先级 
	NVIC_InitStructure.NVIC_IRQChannelSubPriority = 4;// 设置子优先级	
	NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE;
	NVIC_Init(&NVIC_InitStructure);
		
	TIM_ClearFlag(TIM3, TIM_FLAG_Update);  //清楚所有标志位	
  TIM_ITConfig(TIM3,TIM_IT_Update,ENABLE); //允许TIM3溢出中断
  TIM_ITConfig(TIM3,TIM_IT_CC1,ENABLE); //允许TIM3通道1比较中断

	/*-------------------第6步--------------------*/
	TIM_SetCounter(TIM3, 0);
  TIM_Cmd(TIM3, ENABLE);//使能定时器
}



/*********************************************END OF FILE**********************/


  
#include "bspl_tim_Basic.h"


void TIM_Config_Basic(void)
{
	TIM_TimeBaseInitTypeDef  TIM_TimeBaseStructure;
	NVIC_InitTypeDef NVIC_InitStructure; 
  /*-------------------第1步--------------------*/
	// 开启TIM2时钟 
  RCC_APB1PeriphClockCmd(RCC_APB1Periph_TIM2, ENABLE); 
	
  /*-------------------第2步--------------------*/	
  TIM_TimeBaseStructure.TIM_Period = 100-1;       	
  TIM_TimeBaseStructure.TIM_Prescaler = 9000-1;	
  TIM_TimeBaseStructure.TIM_ClockDivision=TIM_CKD_DIV1;
  TIM_TimeBaseStructure.TIM_CounterMode=TIM_CounterMode_Up;	
	TIM_TimeBaseInit(TIM2, &TIM_TimeBaseStructure);
	
	/*-------------------第3-1步--------------------*/
	// 开启定时器更新中断
	TIM_ITConfig(TIM2,TIM_IT_Update,ENABLE);
	// 清除定时器更新中断标志位
	TIM_ClearFlag(TIM2, TIM_FLAG_Update);	
	
	/*-------------------第3-2步--------------------*/	
	// 设置中断组为0
	NVIC_PriorityGroupConfig(NVIC_PriorityGroup_0);		
	// 设置中断来源
	NVIC_InitStructure.NVIC_IRQChannel = TIM2_IRQn; 	
	// 设置抢占优先级
	NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 0;	 
	// 设置子优先级
	NVIC_InitStructure.NVIC_IRQChannelSubPriority = 3;	
	NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE;
	NVIC_Init(&NVIC_InitStructure);	
	
	/*-------------------第4步--------------------*/	
	// 使能定时器
	TIM_Cmd(TIM2, ENABLE);	
}


/*********************************************END OF FILE**********************/

你可能感兴趣的:(STM32学习笔记,单片机,stm32,嵌入式硬件)