基于SysTick实现精准计时

       使用过HAL库的都知道,HAL_Delay()是一个ms级延时函数,并且会至少产生1ms的延时,由于系统滴答定时器的中断优先级默认为最低,在中断中不可调用,否则会导致程序阻塞。

        在STM32的编程中,不可避免的要使用到us级延时,那么怎么做到us级延时呢?笔者将在本篇文章中详细介绍。注意:本文章只做应用,SysTick原理细节不会讲述过多(懒得讲)

        SysTick介绍

        SysTick是一个24位的递减计数器,并且捆绑在NVIC中,可以称为内核外设。

        在M3内核中,SysTick工作时钟选择位复位值为0,默认使用外部时钟源

01f3f95ba0ac4c4cb22f3e1b6a8f2649.png

        在F1的时钟树中可以发现,Cortex系统时钟是主时钟AHB的8分频,SysTick的工作时钟频率就是72/8 = 9MHZ。

f5bbde43dbfe425191d012da9ea80331.png

        在M4内核中,SysTick似乎没有嵌套到NVIC中,而是作为一个独立的内核外设。

4cdfb26653b442768b78f02d20ef3b86.png

        注意M4的SysTick工作时钟的复位值不是0,而是1。

c3ebe7012c264b999d830bd493e5b4d5.png

        SysTick应用

        注:以下代码以系统工作主时钟为80MHZ为例

        Delay_Init()初始化

        TIme_Base代表系统主频,如果为80MHZ,传参传入80即可,如果是M3系列设备,需要将Time_Base/8再赋值给Count_Base

void Delay_Init(uint8_t Time_Base){  // M4:SysTick 时钟默认HCLK 计一个数的时间是 1/80 us
    Count_Base += Time_Base;
}

        Delay_us()延时函数实现

        注意:SysTick是一个24位的递减计数器,计到0后减1重装载计数值。最大计时时间:2^32/80MHZ = 53.68秒。

void Delay_us(uint32_t Time_Count){
    Time_Count  *= Count_Base;                   // 一共需要计多少us
    uint32_t Count_Old = SysTick->VAL;           // 这里需要注意的是,Systick是一个24位的递减计数器
    uint32_t Count_New = 0;
    uint32_t Count = 0;
    uint32_t Reload = SysTick -> LOAD;
    while(1){
        Count_New = SysTick->VAL;
        if(Count_New != Count_Old){
            if(Count_New < Count_Old){
                Count += Count_Old - Count_New;
            }else{
                Count += Reload - Count_New + Count_Old;
            }
            Count_Old = Count_New;
            if(Count >= Time_Count){
                break;
            }
        }
    }
}

        Delay_ms()延时函数

        HAL_Delay()可以重写,调用Delay_ms(),这样在中断中也可以使用。

void Delay_ms(uint32_t Time_Count){
    Delay_us(1000 * Time_Count);
}
void HAL_Delay(uint32_t Delay){
    Delay_ms(Delay);
}

        尾言

        本应用代码参考正点原子SysTick例程,如有描述错误之处,还请斧正,谢谢!

 

  • 3
    点赞
  • 4
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值