自学内容网 自学内容网

FreeRTOS——任务调度、任务状态

任务调度

        调度器就是使用相关的调度算法来决定当前需要执行哪个任务。

FreeRTOS一共支持三种任务调度方式:

抢占式调度:主要是针对优先级不同的任务,每个任务都有一个优先级,优先级高的任务可以抢占优先级低的任务。(数值大的任务优先级高)

时间片调度:主要针对优先级相同的任务,当多个任务的优先级相同时,任务调度器会在每一次系统时钟节拍到的时候切换任务。

协程式调度:当前执行任务将会一直运行,同时高优先级的任务不会抢占低优先级任务,FreeRTOS现在虽然还支持但是官方已经表示不再更新协程式调度。

 抢占式调度

运行条件:

创建三个任务:Task1、Task2、Task3,他们的优先级分别为1、2、3,在FreeRTOS中,数值越大优先级越高。

运行过程如下:

1)首先Task1在运行中,在这个时候Task2进入就绪态,在抢占式调度器的作用下,Task2会抢占Task1的运行;

2)Task运行过程中,Task3进入就绪态,在抢占调度器的作用下Task3会抢占Task2的运行;

3)Task3运行过程中,Task3阻塞了(系统延时或等待信号量等),此时就绪态中优先级最高的任务运行。

总结:

1、高优先级任务,优先执行。

2、高优先级任务不停止,低优先级任务无法执行。

3、被抢占的任务会进入就绪态。

时间片调度

同等优先级任务轮流地享有相同的CPU时间(可设置系统滴答定时器的周期)叫时间片,在FreeRTOS中,一个时间片就等于SysTick中断周期

运行条件:

创建三个任务:Task1、Task2、Task3,他们的优先级相同,均为1

运行过程如下:

1)首先Task1运行完一个时间片后,切换至Task2运行

2)Task2运行一个时间片后,切换至Task3运行

3)Task3运行过程中,如果阻塞了(系统延时或等待信号量等),只运行了0.5个时间片,此时也会让出CPU资源,让给Task1运行,Task1运行一个时间片之后切换Task2运行一个时间片,然后再切换给Task3运行一个时间片,而不是1.5个时间片。

总结:

1、同等优先级任务,轮流执行;时间片流转

2、一个时间片大小,取决为滴答定时器中断周期

3、注意没有用完的时间片不会再使用,下次任务Task3得到执行还是按照一个时间片的时钟节拍运行


任务状态

   FreeRTOS中任务共存在4种状态:

  • 运行态 

        正在执行的任务,该任务就处于运行态,注意在STM32中:同一时间仅一个任务处于运行态。

  • 就绪态

        如果该任务已经能够被执行,但当前还未被执行,那么该任务处于就绪态。

  • 阻塞态

        如果一个任务因延时或等待外部事件(信号量、互斥量等)发生,那么这个任务就处于阻塞态。

  • 挂起态

        类似暂停,调用函数 vTaskSuspend()进入挂起态,需要调用解挂函数vTaskResume()才可以进入就绪态。

四种任务状态之间的转换图:

总结:

1、仅就绪态可转变成运行态

2、其他状态的任务想运行,必须先转变成就绪态

FreeRTOS中无非就四种状态,运行态,就绪态、阻塞态、挂起态

这四种状态中,除了运行态,其他三种任务状态的任务都有其对应的任务状态列表

就绪列表

pxReadyTasksLists[x],其中x代表任务优先级数值

如果用硬件的方式构建就绪列表,x的取值范围是0~31,也就是可以存放32个任务到就绪列表中

新创建的任务是直接挂在就绪列表中的,在我们创建任务时,给任务赋优先级,此时就会把我们的任务放到就绪列表的对应位置。那我们的系统怎么知道就绪列表的哪个位置有任务呢?

  • 设置一个32位的变量,当某个位置1时,代表所对应的优先级就绪列表有任务存在。

阻塞列表

pxDelayedTaskList

挂起列表

xSuspendTaskList

假设创建3个任务分别是Task1、Task2、Task3,优先级分别是1、2、3

此时我们的任务分别放在就绪列表的pxReadyTasksLists[1]、pxReadyTasksLists[2]、pxReadyTasksLists[3]。

首先我们的Task3优先级最高,会从就绪列表中取出Task3优先执行使其转为运行态,当Task3进入阻塞态(系统延时或等待信号量)时,就会把Task3放入阻塞列表,执行就绪列表中任务优先级高的其他任务Task2,Task2进入运行态,如果将Task2用pxSuspendTaskList使其挂起,这时Task2进入挂起列表,这时运行就绪列表中的Task1,使其进入运行态,这时Task2要解挂要调用pxSuspendTaskList。

如果Task1、Task2、Task3的优先级均为1呢

相同优先级的任务会连接在同一个就绪列表上

运行过程:首先Task1运行一个时间片的时间,然后Task2运行一个时间片的时间、再Task3运行一个时间片的时间。

总结:

调度器总是在所有就绪列表的任务中,选择具有最高优先级的任务去执行


原文地址:https://blog.csdn.net/weixin_74209413/article/details/142548453

免责声明:本站文章内容转载自网络资源,如本站内容侵犯了原著者的合法权益,可联系本站删除。更多内容请关注自学内容网(zxcms.com)!