首页 文章

sched_setaffinity()如何工作?

提问于
浏览
12

我试图了解linux系统调用sched_setaffinity()的工作原理 . 这是我的问题here的后续内容 .

我有this guide,它解释了如何使用系统调用并且有一个非常整洁(工作!)的例子 .

所以我下载了Linux 2.6.27.19 kernel sources .

我对包含该系统调用的行进行了'grep',得到了91个结果 . 没有前途 .

最后,我试图了解内核如何为特定内核(或处理器)设置指令指针 .

我熟悉单核单线程程序的工作原理 . 有人可能发出'jmp foo'指令,这基本上将IP设置为'foo'标签的内存地址 . 但是当一个有多个内核时,必须说“在内存地址foo处获取下一条指令,并设置内核编号2的指令指针以便在那里开始执行 . ”

在汇编代码中,我们指定哪个核心执行该操作?

回到内核代码:这里重要的是什么?文件'kernel/sched.c'有一个名为sched_setaffinity()的函数,但返回类型"long" - 这与manual page不一致 . 那么重要的是什么?这些模块中的哪一个显示了组装说明?什么模块正在读'task_struct',查看'cpus_allowed'成员,然后将其转换为指令? (我还翻阅了glibc源代码 - 但我认为它只是调用内核代码来完成这项任务 . )

4 回答

  • 9

    sched_setaffinity() 只是告诉调度程序哪些CPU是允许运行的进程/线程,然后调用重新调度 .

    调度程序实际上在每个CPU上运行,因此它有机会决定在该特定CPU上执行的任务 .

    如果您对如何在其他CPU上实际调用某些代码感兴趣,我建议您查看 smp_call_function_single() . 如果我们想在另一个CPU上调用某些东西,则调用 generic_exec_single() . 后者只是将函数添加到目标CPU的调用队列中,并通过一些IPI内容强制重新调度(如果队列为空) .

    底线是: _jmp_ 指令没有实际的SMP变体 . 相反,在其他CPU上运行的代码协作以完成任务 .

  • 0

    我认为您不理解的是内核在所有CPU内核上运行 . 在每个定时器中断(每秒约1000个)时,调度程序在每个CPU上运行并选择要运行的进程 . 没有一个CPU以某种方式告诉其他人开始运行进程 . sched_setaffinity() 只需在进程上设置标志即可 . 调度程序读取这些标志,如果未设置,则不会在其CPU上运行该进程 .

  • 1

    在汇编代码中,我们指定哪个核心执行该操作?

    这里没有涉及组装 . 每个任务(线程)一次分配给单个CPU(或您的术语中的核心) . 要停止在给定CPU上运行并在另一个CPU上继续运行,任务必须为“migrate”(也是this) . 当任务从一个CPU迁移到另一个CPU时,调度程序 sched_setaffinity()sched_setaffinity() 允许的CPU中更加空闲的CPU .

    没有发布魔法汇编指令 . 内核具有更低级别的硬件视图,每个CPU都是一个单独的对象,与用户空间进程的外观非常不同(在用户空间中,CPU几乎不可见) .

  • 4

相关问题