Linux 默认调度程序替代方案

标签 linux ubuntu linux-kernel scheduler

Linux 内核将完全公平调度 (SCHED_NORMAL) 算法作为其用于调度实时进程的默认调度算法。

如何修改 linux 内核,将默认调度策略设置为 round-robin (SCHED_RR) 或任何其他调度策略?有通用的方法吗?哪些文件需要在此处完全更改?

我正在使用 Ubuntu 16.04。

最佳答案

无论如何,请告诉我这只是一个实验:)我真的看不出尝试这种异端有什么好处。

也就是说,这是我的尝试。首先,我们需要得到一个沙箱。我使用过用户模式 ​​Linux (UML)。对于内核,我随机抓取了一个 4.10.0-rc1 存储库,但任何版本都可以。对于 rootfs,UML 页面提供了其中的一堆 here (陷阱:并非所有这些都能正常工作)。

构建内核的步骤非常短:

export ARCH=um
make x86_64_defconfig
make

如果你有 Slackware rootfs,你现在可以运行:

 ./vmlinux ubda=./Slamd64-12.1-root_fs

好的,很酷。所以我们有一个安全的地方来破坏一些内核。让我们开始吧。您可能知道,init (pid=1) 是第一个进程,也是所有其他进程的父进程。 RT 调度类是继承的(除非用标志另外询问,请参阅 man 7 sched 中的 SCHED_RESET_ON_FORK)。这意味着我们可能会更改 init 进程的调度类,并让其子进程默认继承调度类。

这很容易用这样的东西来实现:

diff --git a/init/main.c b/init/main.c
index b0c9d6facef9..015f72b318ef 100644
--- a/init/main.c
+++ b/init/main.c
@@ -951,8 +951,11 @@ static inline void mark_readonly(void)

 static int __ref kernel_init(void *unused)
 {
+       struct sched_param param = { .sched_priority = MAX_RT_PRIO - 1 };
        int ret;

+       /* Sit tight and fasten your seat belt! */
+       sched_setscheduler_nocheck(current, SCHED_FIFO, &param);
        kernel_init_freeable();
        /* need to finish all async __init code before freeing the memory */
        async_synchronize_full();

而且有效!

root@darkstar:~# sleep 60 &
[1] 549
root@darkstar:~# ps -c
  PID CLS PRI TTY          TIME CMD
  536 FF  139 tty0     00:00:00 bash
  549 FF  139 tty0     00:00:00 sleep
  550 FF  139 tty0     00:00:00 ps

(顺便说一句,SCHED_DEADLINE 不能继承,如 man 7 sched 中所述)。

关于Linux 默认调度程序替代方案,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/41957088/

相关文章:

linux - 如何在 Linux 中使用 C 进行 UDP 广播?

linux - 使用自定义虚拟主机在 docker 中运行 nginx

search - 最优 Solr JVM/虚拟/物理内存配置

Git - 我是否正确使用它?

linux - 申请健康检查

linux - 删除目录(如果存在)

python - 无法使用 termios.TIOCSTI 伪造终端输入

bash - 如何在bash中将单引号替换为双引号?

linux-kernel - Linux内核如何管理小于1GB的物理内存?

linux - 编译包含非内核头文件的 linux 内核 (2.6) 模块