【FreeRTOS 教程 二】任务优先级与任务控制

目录

一、任务优先级:

二、任务状态:

(1)任务状态说明:

(2)状态间的转换:

三、任务优先级函数:

(1)uxTaskPriorityGet():

(2)vTaskPrioritySet():

(3)uxTaskBasePriorityGet(): 

(4)uxTaskBasePriorityGetFromISR():

 四、任务控制函数:

(1)vTaskSuspend():

(2)vTaskResume():

(3)xTaskResumeFromISR():

(4)xTaskAbortDelay():

(5)uxTaskPriorityGetFromISR(): 

五、 任务优先级处理:

(1)获取并修改优先级:

(2)运行结果: 

(3)思考:

 六、任务挂起与解除:

(1)任务挂起与解除程序:

(2)程序现象:

七、任务退出阻塞状态:

(1)唤醒阻塞的任务:

(2)程序现象:

八、程序代码下载: 


一、任务优先级:

  • 每个任务均被分配了从 0 到 ( configMAX_PRIORITIES - 1 ) 的优先级,其中 configMAX_PRIORITIES 定义在 FreeRTOSConfig.h。
  • 如果正在使用的移植实现了使用“前导零计数”类指令的移植优化任务选择机制 (针对单一指令中的任务选择)而且 configUSE_PORT_OPTIMISED_TASK_SELECTION 在 FreeRTOSConfig.h 中设置为 1,则 configMAX_PRIORITIES 无法高于 32。在其他所有情况下, configMAX_PRIORITIES 可以取任何合理数值——但为了保证 RAM 的使用效率,应取实际需要的最小值。
  • 优先级数字小表示任务优先级低。空闲任务的优先级为零 (tskIDLE_PRIORITY)。
  • FreeRTOS 调度器可确保在就绪或运行状态下的任务始终比同样处于就绪状态下的更低优先级任务先获得处理器 (CPU) 时间。 换句话来说,处于运行状态的任务始终是能够运行的最高优先级任务。
  • 处于相同优先级的任务数量不限。如果 configUSE_TIME_SLICING 未经定义,或者如果 configUSE_TIME_SLICING 设置为 1,则具有相同优先级的若干就绪状态任务将通过时间切片轮询调度方案共享可用的处理时间。

二、任务状态:

(1)任务状态说明:

运行:

  • 当任务实际执行时,它被称为处于运行状态。任务当前正在使用处理器。 如果运行 RTOS 的处理器只有一个内核, 那么在任何给定时间内都只能有一个任务处于运行状态。

准备就绪:

  • 准备就绪任务指那些能够执行(它们不处于阻塞或挂起状态), 但目前没有执行的任务, 因为同等或更高优先级的不同任务已经处于运行状态。

阻塞:

  • 如果任务当前正在等待时间或外部事件,则该任务被认为处于阻塞状态。 例如,如果一个任务调用vTaskDelay(),它将被阻塞(被置于阻塞状态), 直到延迟结束——一个时间事件。 任务也可以通过阻塞来等待队列、信号量、事件组、通知或信号量 事件。处于阻塞状态的任务通常有一个"超时"期, 超时后任务将被超时,并被解除阻塞, 即使该任务所等待的事件没有发生。“阻塞”状态下的任务不使用任何处理时间,不能 被选择进入运行状态。

挂起:

  • 与“阻塞”状态下的任务一样, “挂起”状态下的任务不能 被选择进入运行状态,但处于挂起状态的任务 没有超时。相反,任务只有在分别通过 vTaskSuspend() 和 xTaskResume() API 调用明确命令时 才会进入或退出挂起状态。

(2)状态间的转换:

三、任务优先级函数:

(1)uxTaskPriorityGet():

函数原型:

UBaseType_t uxTaskPriorityGet( const TaskHandle_t xTask );
  • INCLUDE_uxTaskPriorityGet必须定义为 1,才可使用此函数。获取任意任务的优先级。
参数 xTask
返回 xTask的优先级

用法示例: 

void vAFunction( void )
{
    TaskHandle_t xHandle; // 定义一个任务句柄变量,用于跟踪创建的任务。

    // 创建一个任务,并将任务句柄存储在xHandle中。
    // vTaskCode是任务函数,"NAME"是任务的名称,STACK_SIZE是任务堆栈的大小,
    // NULL表示不传递参数给任务,tskIDLE_PRIORITY是任务的优先级,
    // &xHandle用于存储新创建的任务的句柄。
    xTaskCreate( vTaskCode, "NAME", STACK_SIZE, NULL, tskIDLE_PRIORITY, &xHandle );

    // ... 其他代码 ...

    // 使用任务句柄获取创建的任务的优先级。
    // 任务是以tskIDLE_PRIORITY优先级创建的,但可能已经自己改变了优先级。
    if( uxTaskPriorityGet( xHandle ) != tskIDLE_PRIORITY )
    {
        // 任务已经改变了它的优先级。
    }

    // ... 其他代码 ...

    // 我们的任务优先级是否高于创建的任务?
    // uxTaskPriorityGet(NULL)获取当前任务(即vAFunction运行的任务)的优先级。
    if( uxTaskPriorityGet( xHandle ) < uxTaskPriorityGet( NULL ) )
    {
        // 我们的优先级(使用NULL句柄获得)更高。
    }
}

(2)vTaskPrioritySet():

函数原型:

void vTaskPrioritySet( TaskHandle_t xTask,
                       UBaseType_t uxNewPriority );

INCLUDE_vTaskPrioritySet必须定义为 1,才可使用此函数。设置任何任务的优先级。如果正在设置的优先级高于当前执行任务的优先级,则函数返回之前将发生上下文切换。

参数 作用
xTask 正在设置优先级的任务的句柄。空句柄会设置调用任务的优先级。
uxNewPriority 将要设置任务的优先级。应断言优先级低于 configMAX_PRIORITIES。 如果 configASSERT未定义,则优先级默认上限为 (configMAX_PRIORITIES - 1)。

用法示例: 

void vAFunction( void )
{
    TaskHandle_t xHandle;  // 定义一个任务句柄变量,用于跟踪创建的任务。

    // 创建一个任务,并将任务句柄存储在xHandle中。
    // vTaskCode是任务函数,"NAME"是任务的名称,STACK_SIZE是任务堆栈的大小,
    // NULL表示不传递参数给任务,tskIDLE_PRIORITY是任务的优先级,
    // &xHandle用于存储新创建的任务的句柄。
    xTaskCreate( vTaskCode, "NAME", STACK_SIZE, NULL, tskIDLE_PRIORITY, &xHandle );

    // ... 其他代码 ...

    // 使用任务句柄提高创建的任务的优先级。
    // 将任务的优先级设置为比空闲任务优先级高一级。
    vTaskPrioritySet( xHandle, tskIDLE_PRIORITY + 1 );

    // ... 其他代码 ...

    // 使用NULL句柄提高当前任务(即vAFunction运行的任务)的优先级到相同的值。
    // 将当前任务的优先级设置为比空闲任务优先级高一级。
    vTaskPrioritySet( NULL, tskIDLE_PRIORITY + 1 );
}

(3)uxTaskBasePriorityGet(): 

函数原型:

UBaseType_t uxTaskBasePriorityGet( const TaskHandle_t xTask );
  • IN
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

The_xzs

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值