st32 标准库 非阻塞型延时函数
时间: 2023-07-31 12:12:30 浏览: 144
st32标准库提供的延时函数有两种,一种是阻塞型延时函数,另一种是非阻塞型延时函数。
阻塞型延时函数是指在延时期间,程序会一直停留在该函数中,直到延时结束才会返回。这种方式会浪费CPU资源,不利于多任务操作。
而非阻塞型延时函数则是通过定时器来实现,可以在延时期间执行其他任务,不会浪费CPU资源。其实现方式如下:
1. 初始化定时器,设置计数器的初始值和计数器的重载值。
2. 启动定时器,并设置中断函数。
3. 在中断函数中,判断计数器是否达到重载值,如果是则清零计数器并执行回调函数。
4. 在需要延时的地方,调用该非阻塞型延时函数,并将回调函数作为参数传入。
5. 在回调函数中,将延时完成的标志置位。
6. 在主函数中,轮询延时完成的标志,当标志被置位后退出该函数。
具体实现代码如下:
```c
#include "stm32f10x.h"
volatile uint8_t delay_flag;
void TIM2_IRQHandler(void)
{
if (TIM_GetITStatus(TIM2, TIM_IT_Update) != RESET)
{
TIM_ClearITPendingBit(TIM2, TIM_IT_Update);
delay_flag = 1;
}
}
void delay_ms(uint16_t ms, void (*callback)(void))
{
TIM_TimeBaseInitTypeDef TIM_InitStruct;
NVIC_InitTypeDef NVIC_InitStruct;
RCC_APB1PeriphClockCmd(RCC_APB1Periph_TIM2, ENABLE);
TIM_InitStruct.TIM_Prescaler = SystemCoreClock / 1000 - 1;
TIM_InitStruct.TIM_CounterMode = TIM_CounterMode_Up;
TIM_InitStruct.TIM_Period = ms;
TIM_InitStruct.TIM_ClockDivision = TIM_CKD_DIV1;
TIM_TimeBaseInit(TIM2, &TIM_InitStruct);
TIM_ITConfig(TIM2, TIM_IT_Update, ENABLE);
NVIC_InitStruct.NVIC_IRQChannel = TIM2_IRQn;
NVIC_InitStruct.NVIC_IRQChannelPreemptionPriority = 0;
NVIC_InitStruct.NVIC_IRQChannelSubPriority = 0;
NVIC_InitStruct.NVIC_IRQChannelCmd = ENABLE;
NVIC_Init(&NVIC_InitStruct);
delay_flag = 0;
TIM_Cmd(TIM2, ENABLE);
while (!delay_flag)
{
if (callback != NULL)
{
callback();
}
}
TIM_Cmd(TIM2, DISABLE);
RCC_APB1PeriphClockCmd(RCC_APB1Periph_TIM2, DISABLE);
}
```
其中,delay_ms函数的参数ms表示延时的毫秒数,callback表示回调函数指针,用于在延时期间执行其他任务。在该函数中,首先初始化定时器,并启动定时器和中断函数。在中断函数中,判断计数器是否达到重载值,如果是则清零计数器并执行回调函数。在需要延时的地方,调用该延时函数,并将回调函数作为参数传入。在回调函数中,将延时完成的标志置位。在主函数中,轮询延时完成的标志,当标志被置位后退出该函数。
阅读全文