当前位置:   article > 正文

Linux的优先级说明

Linux的优先级说明

一、背景

在工作中,不少同学对nice,priority,schedue策略,实时优先级,普通进程优先级的概念混淆,导致最后的代码可能引入bug,本文将统一进行说明,部分内容参考网络大佬的文章 ,文末标记引用来源。

二、优先级的设定 API及关键结构体

设置调度策略,在linux上,FIFO和RR都是RT 调度策略

  1. #include <pthread.h>
  2. int pthread_attr_setschedpolicy(pthread_attr_t *attr, int policy);
  3. int pthread_attr_getschedpolicy(const pthread_attr_t *attr, int *policy);
  4. //policy: SCHED_FIFO, SCHED_RR, and SCHED_OTHER

设置线程优先级相关API

  1. #include <pthread.h>
  2. int pthread_attr_setschedparam(pthread_attr_t *attr, const struct sched_param *param);
  3. int pthread_attr_getschedparam(const pthread_attr_t *attr, struct sched_param *param);
  4. struct sched_param {
  5. int sched_priority; /* Scheduling priority */
  6. };

一个进程结构体中,优先级相关字段

  1. struct task_struct {
  2. ...
  3. int prio;
  4. int static_prio;
  5. int normal_prio;
  6. unsigned int rt_priority;
  7. ...
  8. unsigned int policy;
  9. ...
  10. };

这些优先级值的关系可以参考后面说明

三、Linux 优先级调度策略及优先级值的含义

不同调度策略的说明:

  1. SCHED_OTHER 分时调度策略 (normal thread
  2. SCHED_FIFO 实时调度策略:先到先得,一旦占用cpu则一直运行,直到有更高优先级任务到达或自己放弃 (RT thread
  3. SCHED_RR 实时调度策略:时间片轮转。当进程的时间片用完,系统将重新分配时间片,并置于就绪队列尾。放在队列尾保证了所有具有相同优先级的RR任务的调度公平(RT thread

不同优先级关系的说明

动图封面

详细描述可以参考文末《Linux调度器:进程优先级》

简单的说,先要区分RT 优先级和normal 优先级:

用户空间下

RT 优先级:1~99 (值越大,优先级越高)

normal 优先级: nice 值从 -20(优先级最高) ~ 19(优先级最低) ,nice值是越小优先级越高,默认为0

内核空间中(会对normal和rt 线程优先级 nice值做归一化,对内核来讲都是一个个的task_struct,归一化有利于后面调度策略的计算和选择)

从用户空间的rt优先级值和normal线程的nice值看到,它们的定义似乎是相反的,一个越大代表优先级越高,一个越小优先级越高,怎么归一化呢,实际上内核中是用99 - rt 值进行了反转

normal_priority RT线程优先级:0~99 (注意这里的0~99 和用户空间真实设定的值是相反的关系,用户空间设置rt优先级99,这里就是0)

normal_priority normal线程优先级:100~139 (nice值为 -20,代表这里的100)

nice值priority内核空间归一化的优先级
普通线程-20~190100~139
RT线程/1~9998~0 (图实际有点小错误,99 不可到达)

四、工具显示的优先级差异

常见的查看优先级方法:

top

ps -el

atop -s

实验一、一个普通进程下不同工具的显示结果

利用工具chrt来设置调度策略及优先级,如:sudo chrt -r 50 ./hello ---- 设置 SCHED_RR,优先级为50

top

ps -el

  1. F S UID PID PPID C PRI NI ADDR SZ WCHAN TTY TIME CMD
  2. 4 R 0 5352 5351 95 9 - - 660 - pts/2 00:18:38 hello

atop -s

实验二、一个RT进程不同工具的显示结果

利用nice来调整,如:sudo nice -n 5 ./hello ---设置普通进程 nice值为5

top

ps -el

  1. F S UID PID PPID C PRI NI ADDR SZ WCHAN TTY TIME CMD
  2. 4 R 0 6917 6916 99 85 5 - 660 - pts/2 00:00:07 hello

atop -s

这些工具显示同一个进程的优先级数值却大不相同,这些值怎么和API 设置的值对应起来?这些值只是工具计算的方式不同导致的,其中和当前内核/userspace设置比较匹配的是atop;

top 在普通进程default PR值是20, 根据nice值做调整,PR取值范围在0~39, 但是在表示rt thread时,全部都是负值, 为-1-rt, 从 -2 ~ -99(这里你会有疑问,rt的值是1~99,还有一个-100怎么没有?实际当rt=99时,这里的PR会显示rt)

ps -el 它的PRI 值取值范围是 -40 ~99 (和内核归一化的值0~139 有-40的差值), 它的值实际和内核归一化的含义一致,只是有-40 的差值;

atop -s 的取值 PRI就是内核归一化的值, RTPR 在线程为rt线程时,显示为用户api设置的值,当为normal线程时为0;

五、总结

linux 下不同工具显示的优先级数值,不同的展示方式给开发者带来了困扰,再叠加用户空间设置优先级值,调度策略,以及内核侧又重新进行了归一化操作,部分工具显示的内核归一化的值,导致这些概念数值困扰了开发者,这里将工具的差异做了一个总结:

工具PRNIPRINICERTPRPOLI
RT线程top-1 - rt0无意义////
normaltop20 + nice值nice值////
RT线程ps -el/无意义99 - rt - 40///
normalps -el/nice值120 + nice -40///
RT线程atop -s//99-rtrtrr/fifo
normalatop -s//120+nicenice值0normal

上面表中的rt值和nice值均为用户空间设置的值

参考资源:

Linux调度器:进程优先级

articles/20230802-linux-sched-api.md · aosp-riscv/working-group - Gitee.com

https://mp.weixin.qq.com/s/44Gamu17Vkl77OGV2KkRmQ

声明:本文内容由网友自发贡献,不代表【wpsshop博客】立场,版权归原作者所有,本站不承担相应法律责任。如您发现有侵权的内容,请联系我们。转载请注明出处:https://www.wpsshop.cn/article/detail/53525
推荐阅读
相关标签
  

闽ICP备14008679号