如何清除STM32 定时器TIM1的状态寄存 (能解按要求决问题有赏)

如何清除STM32 定时器TIM1的状态寄存 (能解按要求决问题有赏),第1张

前期准备:

STM32CubeMX

STM32RCT6核心板

IDE Keil(MDK-ARM)

STM32CubeMX部分

1 配置时钟

选择STM32F103RCTx系列芯片,配置时钟的同时会自动配置IO口引脚

在这里插入描述

将HCLK设置为最大频率72MHz

在这里插入描述

2配置TIM

在这里插入描述

Internal Clock(内部时钟)

Prtscaler (定时器分频系数) : 71

Counter Mode(计数模式) Up(向上计数模式)

Counter Period(自动重装载值) : 999

CKD(时钟分频因子) :No Division (不分频 )

auto-reload-preload(自动重装载) : Enable (使能)

在这里插入描述

勾选update interrupt(更新中断)

1 定时器溢出时间计算公式:

在这里插入描述

Tout:中断溢出的时间

arr:自动重装载值

psc:定时器分频系数

Tclk:时钟频率

Tout = ((71+1)(999+1))/72 us

Tout = ( 72 1000 ) / 72 us

1000us = 1ms

所以这里我们的定时时间为:1ms

也就是说单片机1ms进入一次定时器中断

2 定时器计数模式:

向上计数模式:计数器从0计数到自动加载值(TIMx_ARR),然后重新从0开始计数并且产生一个计数器溢出事件。

向下计数模式:计数器从自动装入的值(TIMx_ARR)开始向下计数到0,然后从自动装入的值重新开始,并产生一个计数器向下溢出事件。

向上/向下计数模式(中央对齐模式):计数器从0开始计数到自动装入的值-1,产生一个计数器溢出事件,然后向下计数到1并且产生一个计数器溢出事件;然后再从0开始重新计数。

在这里插入描述

2 计数时钟:

内部时钟(TIMx_CLK):

外部时钟模式1:外部捕捉比较引脚(TIx)

外部时钟模式2:外部引脚输入(TIMx_ETR)

内部触发输入(ITRx):使用一个定时器作为另一个定时器的预分频器,如可以配置一个定时器Timer1而作为另一个定时器Timer2的预分频器。

3配置IO口

在这里插入描述

将PB0设置为:

低电平

Output模式

既不上拉也不下拉

响应速度低

4 工程生成

在这里插入描述

在这里插入描述

工程管理依旧是这几个选项,然后GENERATE CODE,STM32CubeMX部分完成。

MDK 5部分

HAL_TIM_IRQHandler(&htim1);//定时器中断处理函数

此函数的作用是判断中断是否正常,是哪一类定时器中断(溢出中断/捕获中断/PWM中断…),然后进入相应的中断回调函数

void HAL_TIM_PeriodElapsedCallback(TIM_HandleTypeDef htim)//定时器溢出中断回调函数

定时器中断时,每进行完一个中断,并不会立刻退出,而是会进入到中断回调函数中

点开mainc在这里插入描述

在如图位置上添加

HAL_TIM_Base_Start_IT(&htim1);//开启定时器1

1

1

然后再timc文件中,添加

/ USER CODE BEGIN 0 /

uint16_t Tim_cnt = 0; //定时器计数

/ USER CODE END 0 /

1

2

3

1

2

3

然后在timc文件中重写

void HAL_TIM_PeriodElapsedCallback(TIM_HandleTypeDef htim)函数

在这里插入描述

/ USER CODE BEGIN 1 /

void HAL_TIM_PeriodElapsedCallback(TIM_HandleTypeDef htim)

{

if (htim->Instance == htim1Instance)

{

Tim_cnt++;

if(Tim_cnt==500) //05s进行一次下列代码

{

Tim_cnt=0; //清0

HAL_GPIO_TogglePin(GPIOB, GPIO_PIN_0);

}

}

}

/ USER CODE END 1 /

1

2

3

4

5

6

7

8

9

10

11

12

13

14

1

2

3

4

5

6

7

8

9

10

11

12

13

14

设一个全局变量,每进一次中断+1,因为1ms进入一次中断,所以当Tim_cnt=500的时候(即05s)写入我们需要运行的代码(不要忘记清0)

编译下载时需要选择相对应的下载器,勾选以下

在这里插入描述

运行即可

本期工程文档——>Gitee

在这里插入描述

前面省略了

TIM_TimeBaseInit(TIM3, &TIM_TimeBaseStructure);

/ 通道1工作模式 /

TIM_OCStructInit(&TIM_OCInitStructure); //其它默认值

//110:PWM模式1- 在向上计数时,一旦TIMx_CNT<TIMx_CCR1时通道1为有效电平,否则为无效电平;

TIM_OCInitStructureTIM_OCMode = TIM_OCMode_PWM1;

TIM_OCInitStructureTIM_OCPolarity = TIM_OCPolarity_High; //TIM_OCPolarity_Low;//输出极性0:高电平有效

TIM_OCInitStructureTIM_OutputState = TIM_OutputState_Enable;//输出

TIM_OCInitStructureTIM_Pulse = 50(SYSTEM_CLOCK/1000000); //50us高电平

//1通道pwm

TIM_OC3Init(TIM3, &TIM_OCInitStructure);

TIM_OC3FastConfig(TIM3, TIM_OCFast_Enable);

TIM_OC3PreloadConfig(TIM3,TIM_OCPreload_Enable); //通道预装载使能

/ //12模拟输入捕获上升下降沿/

TIM_ICInitStructureTIM_Channel = TIM_Channel_4;

TIM_ICInitStructureTIM_ICPolarity = TIM_ICPolarity_Rising;

TIM_ICInitStructureTIM_ICSelection = TIM_ICSelection_DirectTI;//TIM_ICSelection_IndirectTI;//

TIM_ICInitStructureTIM_ICPrescaler = TIM_ICPSC_DIV1;

TIM_ICInitStructureTIM_ICFilter = 0x08;

TIM_ICInit(TIM3, &TIM_ICInitStructure); TIM_ClearFlag(TIM3,TIM_FLAG_Update|TIM_FLAG_CC1|TIM_FLAG_CC2|TIM_FLAG_CC3|TIM_FLAG_CC4);

TIM_ITConfig(TIM3,TIM_IT_Update|TIM_IT_CC4, ENABLE);

TIM_Cmd(TIM3, ENABLE);

再加中断配置,不保证一定行大概意思就是这样了

不会吧,参考手册里是这样说的:

软件可以读此位,也可以通过写’0’清除此位,写’1’对此位无影响

所以是可以写0清零的, 实在不行可以通过读相应寄存器清零,如读TIMx_CCRx可以清零CCxIF位

实现10ms定时需要使用STM32的定时器模块,并且要将系统时钟频率设置为足够高的值。以下是实现10ms定时的步骤:

设置系统时钟:使用RCC寄存器设置PLL倍频系数,将系统时钟频率设置为72 MHz。

选择合适的定时器:在STM32中有多个定时器可供选择,根据需要选取合适的定时器。假设在这里我们选用TIM2定时器。

配置定时器:使用TIM2的相关寄存器配置定时器的时钟源、分频系数和计数周期等参数。可以将定时器的时钟源设置为内部时钟,将分频系数设置为7200,则每秒钟定时器计数器会自增100次。

启动定时器:将TIM2的控制寄存器使能,并设置定时器计数器初值为0。

编写中断服务程序:在定时器溢出时会产生中断请求,在中断服务程序中可以进行相应的 *** 作。例如,可以使用GPIO输出引脚控制LED闪烁。

启用全局中断:调用__enable_irq();函数启用全局中断

在以上代码中,使用了TIM2定时器,并将计数周期设置为100,即每秒钟会产生10次溢出中断。在中断服务程序中,控制LED引脚状态的改变,从而实现了10ms的定时效果。

#include "stm32f10xh"

void TIM2_IRQHandler(void)

{

if(TIM_GetITStatus(TIM2, TIM_IT_Update) == SET)

{

//定时器中断执行的内容

GPIO_WriteBit(GPIOC, GPIO_Pin_13, (BitAction)(1 - GPIO_ReadOutputDataBit(GPIOC, GPIO_Pin_13)));

TIM_ClearITPendingBit(TIM2, TIM_IT_Update);

}

}

int main(void)

{

//开启GPIOC时钟

RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOC, ENABLE);

//配置LED引脚为推挽输出模式

GPIO_InitTypeDef GPIO_InitStructure;

GPIO_InitStructureGPIO_Pin = GPIO_Pin_13;

GPIO_InitStructureGPIO_Mode = GPIO_Mode_Out_PP;

GPIO_InitStructureGPIO_Speed = GPIO_Speed_50MHz;

GPIO_Init(GPIOC, &GPIO_InitStructure);

//开启TIM2时钟

RCC_APB1PeriphClockCmd(RCC_APB1Periph_TIM2, ENABLE);

//设置定时器参数

TIM_TimeBaseInitTypeDef TIM_TimeBaseInitStruct;

TIM_TimeBaseInitStructTIM_Prescaler = 7200-1; //预分频系数

TIM_TimeBaseInitStructTIM_Period = 100-1; //自动重载计数值

TIM_TimeBaseInitStructTIM_ClockDivision = TIM_CKD_DIV1; //时钟分割

TIM_TimeBaseInitStructTIM_CounterMode = TIM_CounterMode_Up; //向上计数

TIM_TimeBaseInit(TIM2, &TIM_TimeBaseInitStruct);

//使能TIM2中断

TIM_ITConfig(TIM2, TIM_IT_Update, ENABLE);

//启动TIM2定时器

TIM_Cmd(TIM2, ENABLE);

//注册中断服务程序

NVIC_InitTypeDef NVIC_InitStructure;

NVIC_InitStructureNVIC_IRQChannel = TIM2_IRQn;

NVIC_InitStructureNVIC_IRQChannelPreemptionPriority = 0;

NVIC_InitStructureNVIC_IRQChannelSubPriority = 0;

NVIC_InitStructureNVIC_IRQChannelCmd = ENABLE;

NVIC_Init(&NVIC_InitStructure);

//启用全局中断

__enable_irq();

while(1)

{

//主循环程序

}

}

谢谢您的指点,是不是

前者来自于

CCR3

的匹配

(或捕捉)

触发之后CNT计数就,不再向ARR上累计了,而是CNT

重新计数了?而通常是计数器溢出是指CNT计数到ARR是时候产生中断,这样理解对吗

TIM_OC4PreloadConfig(TIM1, TIM_OCPreload_Disable); //如果使能则定时器等待下一次定时器溢出才会发生变化 -- 同步

TIM_OC1PreloadConfig(TIM1, TIM_OCPreload_Disable); //不使能则会立即发生变化 -- 异步

所以不使能的话就会立刻变化,今天遇到相同的问题翻芯片手册才看到这个。

以上就是关于stm32获取定时器溢出状态但不中断全部的内容,包括:stm32获取定时器溢出状态但不中断、想用stm32的TIM3的通道3做PWM输出,通道4做捕获输入,但是不知道怎么使用,请高手指教!、如何清除STM32 定时器TIM1的状态寄存 (能解按要求决问题有赏)等相关内容解答,如果想了解更多相关内容,可以关注我们,你们的支持是我们更新的动力!

欢迎分享,转载请注明来源:内存溢出

原文地址: http://outofmemory.cn/langs/8871814.html

(0)
打赏 微信扫一扫 微信扫一扫 支付宝扫一扫 支付宝扫一扫
上一篇 2023-04-22
下一篇 2023-04-22

发表评论

登录后才能评论

评论列表(0条)

保存