时间片在FreeRTOS中的含义解析

什么是时间片

时间片是一个任务被任务调度管理器强制切换出CPU之前连续运行的最长时间。

FreeRTOS 中,时间片的长度固定为 1 个 tick。

tick的时长可以通过配置文件FreeRTOSConfig.h中的宏定义configTICK_RATE_HZ修改。

每个时间片的长度 (秒) = 1 / configTICK_RATE_HZ。

复制代码
// 将Tick频率设置为1000Hz,此时1个Tick = 1ms
#define configTICK_RATE_HZ    1000

什么是时间片轮转

时间片轮转是一种任务调度算法,让多个同优先级任务轮流使用 CPU,每个任务每次运行一个固定长度的时间片,时间片用完后强制切换到下一个任务。

时间片轮转的触发机制

复制代码
void vTask1(void *pvParameters)
{
    for(;;)
    {
        printf("Task1 running\r\n");
        vTaskDelay(pdMS_TO_TICKS(1000));
    }
}

这里printf() 执行时间极短(比如 10 微秒),然后任务主动调用 vTaskDelay(),立即进入阻塞态。

任务在 printf() 刚执行完就主动让出了 CPU。时间片轮转并没有触发。

因为时间片轮转触发的前提是:任务连续运行满 1 个 tick 且没有主动让出。

任务在 1 个 tick 还没到(才运行了 10 微秒)就主动调用 vTaskDelay() 阻塞了,所以:

✅ 触发的是 vTaskDelay() 的阻塞机制。

❌ 没有触发时间片轮转机制。

复制代码
void Task_TimeSlice(void *pv) {
    while(1) {
        for(int i = 0; i < 1000000; i++);  // 耗时 > 1 tick
       vTaskDelay(1000);
    }
}

即使后面有 vTaskDelay(1000),for(int i = 0; i < 1000000; i++)超过1 tick,CPU也会强制进行任务切换。

如果不想比打断可以使用临界区:

复制代码
taskENTER_CRITICAL();
for(int i = 0; i < 1000000; i++);  // 不会被中断
taskEXIT_CRITICAL();

时间片轮转的开关

  • configUSE_TIME_SLICING = 1 (开启):系统会在每个Tick中断时,检查当前优先级下是否还有其他就绪任务。如果有,就强制切换到下一个任务,实现时间片轮转调度。
  • configUSE_TIME_SLICING = 0 (关闭):系统关闭自动轮转。此时,同优先级任务之间不会因为Tick中断而自动切换,必须通过任务主动阻塞(如调用vTaskDelay)或主动让出(如调用taskYIELD())才能发生切换。
    注意:configUSE_TIME_SLICING 只有开(1)和关(0)两种状态。
相关推荐
一支闲人7 小时前
Free RTOS:信号量实验
freertos
济61721 小时前
FreeRTOS看门狗任务设计---软件看门狗 + 硬件 IWDG 双保险实现
嵌入式·freertos
山木嵌入式3 天前
FreeRTOS任务创建全解析:动态/静态创建+实战案例+参数深度剖析
stm32·freertos
济6174 天前
FreeRTOS日志任务设计----LogTask 日志任务
单片机·嵌入式·freertos
济6174 天前
FreeRTOS教程----队列详解
嵌入式·freertos
温中志6 天前
esp_event_loop_create_default详细解释
esp32·freertos
济6177 天前
FreeRTOS 系统监控任务设计(上篇) ---MonitorTask的 基础框架
单片机·嵌入式·freertos
济6177 天前
MonitorTask 系统监控任务(下篇)---完善堆内存 、任务栈监控
单片机·嵌入式·freertos
济61710 天前
FreeRTOS传感器采集任务 ——SensorTask 传感器采集任务整体实现
stm32·单片机·嵌入式·freertos
济61710 天前
FreeRTOS 上报任务设计---UplinkTask 上行数据上报任务详解
stm32·嵌入式·freertos