• RTOS相对延时和绝对延时的区别


    关注+星标公众,不错过精彩内容

    5618e9ce69dc3b9c643a97d197c5f1f9.gif

    作者 | strongerHuang

    微信公众号 | strongerHuang

    嵌入式软件代码中延时是很常见的,只是延时种类有很多,看你用什么延时。

    一个延时的问题

    问题:周期性(固定一个时间)去处理某一件事情。你会通过什么方式去实现?

    比如:间隔10ms去采集传感器的数据,然后通过一种算法计算出一个结果,最后通过串口发送出去。

    可能对于很多习惯裸机编程的读者,首先想到的是:利用定时器,定时10ms中断,在中断里面处理。

    中断函数适合处理简单数据,不适合算法、通信等需要长时间占用CPU的处理。

    对计时精度要求比较高的地方适合定时器,像本章节说的周期性采集传感器数据,要求不适合很高,那么就引入本文说的绝对延时。

    在实时操作系统FreeRTOS任务中,利用vTaskDelayUntil绝对延时即可完美解决这个问题。

    相对延时和绝对延时的含义

    本文拿FreeRTOS中相对延时函数vTaskDelay,绝对延时函数vTaskDelayUntil来说明。

    相对延时:指每次延时都是从执行函数vTaskDelay()开始,直到延时指定的时间(参数:滴答值)结束。

    绝对延时:指每隔指定的时间(参数:滴答值),执行一次调用vTaskDelayUntil()函数的任务。

    文字描述可能不够直观理解,下面章节结合代码例子、延时值(IO高低变化波形)、任务执行图来详细讲述一下他们的区别。

    相对延时和绝对延时区别

    以实际代码为例说明:一个任务中,添加一个10ms系统延时,然后,在执行任务(耗时1ms左右,例子以延时代替)。

    相对延时代码:

    107000704d36fc379f0786f3cf5ed25b.jpeg

    绝对延时代码:

    b84a46bd5b1da0060bc8c6cccfdcf460.jpeg

    说明:

    1.TestDelay这个延时函数仅仅用于测试(延时1ms),用于代替采集、算法、发送等耗时时间。

    2.两个代码唯一区别在于系统延时不同,一个vTaskDelay(10);,一个vTaskDelayUntil(&xLastWakeTime, 10);

    3.系统时钟频率为1000,也就是上面系统延时10个滴答,即10ms。

    看到代码,你想到了他们输出结果的差异吗?

    来看下结果的差异:用PA0这个引脚输出的高低电平,得出延时时间。

    相对延时结果:

    ca7aa6e30ced9c76f4ade9d5c544b9b5.png

    绝对延时结果:

    54a72211c3b92a11a282fa86040e95dc.png

    结果为:相对延时的周期为系统延时10ms + 执行任务1ms的时间,总共11ms时间。绝对延时的周期即为10ms时间.

    换一种方式看区别

    如果上面的区别还没明白,再来讲一个更容易理解的区别,通过文字 + 任务执行图来说明。

    1.相对延时

    先看任务执行图,按照上面代码的方式呈现:

    9fc54b81a03d4055837bbf75e0bda62d.jpeg

    这里会牵涉到操作系统任务切换、高优先级任务抢占等一些原理,若不了解,请转移直到了解再回来。

    上电,TEST任务进入延时(阻塞)状态,此时系统执行其他就绪任务。FreeRTOS内核会周期性的检查TEST任务的阻塞是否达到,如果阻塞时间达到,则将TEST任务设置为就绪状态,如果就绪任务中TEST任务的优先级最高,则会抢占CPU,再次执行任务主体代码,不断循环。

    TEST任务每次系统延时都是从调用延时函数vTaskDelay()开始算起的,所以叫相对延时。

    从上图可以看出:

    如果执行TEST任务的过程中发生中断,或者具有更高优先级的任务抢占了,那么TEST任务执行的周期就会变长,所以使用相对延时函数vTaskDelay(),不能周期性的执行TEST任务。

    2.绝对延时

    cf4b762897d670cc1c97b1dc25405709.jpeg

    代码中定义的变量xLastWakeTime,其实是用来保存上一次的系统计数器值(方便检测下一个延时时间是否到来)。

    和上面相对延时程序执行图比较,可以看出,系统延时的时间包含了程序执行的时间。即时中途有中断,或更高优先级任务打断,不会影响下一次执行的时间(也就是这个周期不会变,当然,打断时间不能超过系统延时值)。

    提示:图片中添加了一段话:一般来说,程序执行时间要小于总间隔时间(10ms)。

    如果打断时间太长,回来之后延时都超过了,则会立马执行程序,不会再延时(任务不会再阻塞延时)。

    ------------ END ------------

    2a112a6e3ce5eda124334bf2eab27b53.gif

    ●专栏《嵌入式工具

    ●专栏《嵌入式开发》

    ●专栏《Keil教程》

    ●嵌入式专栏精选教程

    关注公众号回复“加群”按规则加入技术交流群,回复“1024”查看更多内容。

    55a15ac2b23a3b0047a0a9f502845c01.jpeg

    02dfddcdc25c3b60a82690c47a630a4f.png

    点击“阅读原文”查看更多分享。

  • 相关阅读:
    OpenCV之cv::undistort
    FPGA实现Avalon-MM接口通信
    高可用架构的设计方法
    LLaMA Factory单机微调的实战教程
    MySQL索引、事务与存储引擎
    uniapp数据点击的时候将数据存入同一个本地存储中并且最大限度5个
    【Java基础篇】运算符
    java ssm在线读书与分享论坛系统
    【已解决】vue项目之爆红红红红······
    GreenPlum的gpfdist使用与原理流程分析
  • 原文地址:https://blog.csdn.net/ybhuangfugui/article/details/126313737