//基本定时器:
//滴答定时器复习:
滴答定时器集成在CM4内核中,属于NVIC的一部分
特征:
24位递减计数器
时钟源的选择:
1.参考时钟-----21Mhz 时钟树(中文参考手册RCC部分)
2.内核时钟-----168Mhz
滴答定时器周期计算公式:
T = ARR / Fck
Mhz--------us
Khz--------ms
//基本定时器TIM6和TIM7:
包含一个16位自动重载计数器(16位递增计数),并由可编程预分频器驱动;
它不仅可以作为定时器生成时基,也可与驱动DAC;
TIM6与TIM7彼此之间相互独立,不共享任何资源;
定时器数数的范围:
0--65535
//基本定时器框图:
//基本功能:
1.延时、计数
2.触发DAC转换
//基本定时器的特征:
1.16位自动重载递增计数器
2.可编程预分频器,可以对时钟频率进行自定义
3.3可以触发DAC同步电路
4.发生更新事件会生成中断 (更新事件:时间到)
//PSC与ARR的数值范围
0----65535
//基本定时器周期计算公式:
T = ARR / (Fck / PSC(预分频数))
//定时器的频率确定:
先看时钟树对应总线的频率,若频率被分频,则分频后的结果成2为定时器的初始频率,没有经过分频,则这个频率就是定时器初始频率;
//注意:
并不是每款芯片都有基本定时器
//注意看数据手册
//预分频器的作用:
1.作为减慢数数速度,延长定时周期
2.方便周期的计算
//重装载寄存器的作用:
设置最大的计数值
//如何将设置好的重装载值加载到计数器中:
需产生更新事件(UG置一),重装载值才会被加载到计数器上 (更新事件:时间到,一个周期结束)
//影子寄存器:
用户配置的只是配置寄存器,而真正发挥作用的是影子寄存器;
//作用:
缓冲功能,保证定时器周期的完整性,避免发生未知错误,导致程序卡死;
//预分频器的影子寄存器:
自动开启,不需要手动;
//重装载寄存器的影子寄存器:
可以自己手动选择开启(ARPE);【当在定时器程序执行的过程中需要改变ARR时可以选择开启】
//定时器时基单元:
1.ARR重装载值
2.PSC预分频值
3.CNT计数值
//相关寄存器:
1.TIMx->CR1(TIMx控制寄存器):
位 7 ARPE:自动重载预装载使能 (Auto-reload preload enable)
0:TIMx_ARR 寄存器不进行缓冲。
1:TIMx_ARR 寄存器进行缓冲。
位 3 OPM:单脉冲模式 (One-pulse mode)
0:计数器在发生更新事件时不会停止计数
1:计数器在发生下一更新事件时停止计数(将 CEN 位清零)
位 2 URS:更新请求源 (Update request source)
此位由软件置 1 和清零,用以选择 UEV 事件源。
0:使能时,所有以下事件都会生成更新中断或 DMA 请求。此类事件包括:
— 计数器上溢/下溢
— 将 UG 位置 1
— 通过从模式控制器生成的更新事件
1:使能时,只有计数器上溢/下溢会生成更新中断或 DMA 请求。
位 1 UDIS:更新禁止 (Update disable)
此位由软件置 1 和清零,用以使能/禁止 UEV 事件生成。
0:使能 UEV。更新 (UEV) 事件可通过以下事件之一生成:
— 计数器上溢/下溢
— 将 UG 位置 1
— 通过从模式控制器生成的更新事件
然后更新影子寄存器的值。
1:禁止 UEV。不会生成更新事件,各影子寄存器的值(ARR 和 PSC)保持不变。但如果将
UG 位置 1,或者从从模式控制器接收到硬件复位,则会重新初始化计数器和预分频器
位 0 CEN:计数器使能 (Counter enable)
0:禁止计数器
1:使能计数器
2.TIMx->DIER(中断使能寄存器):
位 0 UIE:更新中断使能 (Update interrupt enable)
0:禁止更新中断。
1:使能更新中断。
3.TIMx->SR(状态寄存器):
位 0 UIF:更新中断标志 (Update interrupt flag)
该位在发生更新事件时通过硬件置 1。但需要通过软件清零。
0:未发生更新。
1:更新中断挂起。该位在以下情况下更新寄存器时由硬件置 1:
— 上溢或下溢并且当 TIMx_CR1 寄存器中 UDIS = 0 时。
— 当由于 TIMx_CR1 寄存器中 URS = 0 且 UDIS = 0 而通过软件使用 TIMx_EGR 寄存器中
的 UG 位重新初始化 CNT 时。
4.TIMx->EGR(事件生成寄存器):
位 0 UG:更新生成 (Update generation)
该位可通过软件置 1,并由硬件自动清零。
0:不执行任何操作。
1:重新初始化定时器计数器并生成寄存器更新事件。请注意,预分频器计数器也将清零(但
预分频比不受影响)
在初始化设置重装载值
需要将UG位置一,加载重装载值到计数器
5.TIMx->CNT(计数器):
设置初始计数值(注意:设置初始计数值只有在第一个周期有效)
6.TIMx->PSC(预分频器):
7.TIMx->ARR(自动重载寄存器):
//微秒级延时代码框架:
代码框架:
void TIM6_Delay_us(u16 nus)
{
//1、打开TIM6时钟
//2、初始化TIM6
//使能ARR寄存器影子寄存器的缓冲功能
//使能单脉冲模式
//更新请求源清零
//UDIS清零,使能更新
//3、设置定时器时基单元 TIM6频率:84Mhz 更新事件: 0->1
//设置PSC
//设置ARR
//UG位置1 --->产生更新事件 ---> UIF标志位(更新标志位)置1
//清除更新标志位
//4、定时器使能(计数器使能)
//5、等待更新标志位置1
}
//例程:
/*
函数功能:以微秒为单位延时
返回值:void
形参:u16 nus
函数说明:
*/
void TIM6_Delay_us(u16 nus)
{
//打开TIM6时钟
RCC->APB1ENR |= 1 << 4;
//初始化TIM6
TIM6->CR1 |= 1 << 7; //配置影子寄存器的缓冲功能
TIM6->CR1 |= 1 << 3; //配置单脉冲模式
TIM6->CR1 &=~ (1 << 2); //更新请求源
TIM6->CR1 &=~ (1 << 1); //关闭更新禁止
//设置时基单元
TIM6->PSC = 42 - 1;
TIM6->ARR = nus * 2 - 1;
TIM6->EGR |= 1 << 0;//产生更新事件
TIM6->SR &=~ (1 << 0);//清除更新标志位
//计数器使能
TIM6->CR1 |= 1 << 0;
//等待标志位更新标志位置一
while(!(TIM6->SR & 1 << 0));
}
//基本定时器中断初始化基本框架:
1、打开TIM7时钟
2、初始化TIM7 使能中断
3、配置TIM7 时基单元
4、配置NVIC
5、使能TIM7
6、TIM7中断服务函数
//例程:
/*
函数功能:TIM7中断初始化
返回值:void
形参:u16 nms
函数说明:
*/
void Tim7_Interrupt_Init(u16 nms)
{
u32 pri;
//打开时钟
RCC->APB1ENR |= 1 << 5;
//初始化TIM7
TIM7->CR1 |= 1 << 7;
TIM7->CR1 &=~ (1 << 3);
TIM7->CR1 &=~ (1 << 2);
TIM7->CR1 &=~ (1 << 1);
TIM7->DIER |= 1 << 0;//中断使能
//配置时基
TIM7->PSC = 8400 - 1;
TIM7->ARR = nms * 10 - 1;
TIM7->EGR |= 1 << 0;
TIM7->SR &=~ (1 << 0);
//配置NVIC
pri = NVIC_EncodePriority (5,0,0);
NVIC_SetPriority(TIM7_IRQn,pri);
NVIC_EnableIRQ(TIM7_IRQn);
//计数器使能
TIM7->CR1 |= 1 << 0;
}