首页 文章

系统调用没有上下文切换?

提问于
浏览
6

当我遇到这个时,我只是在阅读我的操作系统中的linux如何工作 .

[...]内核创建为单个单一二进制文件 . 主要原因是提高性能 . 由于所有内核代码和数据结构都保存在单个地址空间中,因此当进程调用操作系统函数或传递硬件中断时,不需要上下文切换 .

这听起来对我来说非常了不起,当然它必须存储进程的上下文才能运行到内核模式来处理中断..但好吧,我现在就买它 . 在描述进程的调度上下文时,有几页,它说:

进程执行时发生的系统调用和中断都将使用此堆栈 .

“这个堆栈”是内核存储进程寄存器等的地方 .

这不是第一次引用的直接矛盾吗?我不知道以某种方式解释它吗?

3 回答

  • 3

    我认为第一个引用是指单片内核和microkernel之间的差异 .

    Linux是单片的,其所有内核组件(设备驱动程序,调度程序,VM管理器)都在ring 0运行 . 因此,在执行系统调用和处理中断时不需要上下文切换 .

    对比微内核,其中设备驱动程序和IPC提供程序等组件在环0之外的user space中运行 . 因此,此体系结构在执行系统调用时需要额外的上下文切换(因为执行模块可能驻留在用户空间中)并处理中断(以中继中断设备驱动程序) .

  • 5

    “上下文切换”可能意味着两个相关的事情之一:(1)从用户切换到内核模式以处理系统调用,或者无意识切换到内核模式以处理针对中断堆栈的中断,或者(2)切换到在用户空间中运行另一个用户进程,跳转到两者之间的内核空间 .

    从用户空间到内核空间的任何移动意味着保存足够的用户空间以可靠地返回它 . 如果内核空间代码决定 - 当你不再运行该进程的用户代码时 - 是时候让另一个用户进程运行了,它就进入了 .

    所以至少,你要说2-3个堆栈或地方来存储“上下文”:硬件中断需要内核级堆栈来说明要返回的内容;用户方法/子例程调用使用标准堆栈来完成 . 等等 .

    最初的Unix内核 - 现在这个部分的模型并没有那么不同 - 运行系统调用就像一个短序厨师处理早餐订单:在炉子上移动它,为刚刚到达的培根的订单腾出空间,启动培根,回到第一个订单 . 全部在内核切换上下文中 . 不是一个巨大的监控应用程序,这可能驱使IBM和DEC软件的人疯了 .

  • 1

    在Linux中进行系统调用时,从用户空间到内核空间(ring3到ring0)进行上下文切换 . 每个进程都有一个关联的内核模式堆栈,由系统调用使用 . 在执行系统调用之前,进程的CPU寄存器存储在其用户模式堆栈中,该堆栈与内核模式堆栈不同,并且是进程用于用户空间执行的堆栈 .

    当进程处于内核模式(或用户模式)时,调用相同模式的函数将不需要上下文切换 . 这是第一个引用所引用的内容 .

    第二个引用是指内核模式堆栈,而不是用户模式堆栈 .

    话虽如此,我必须提到Linux优化,其中内核空间不需要转换来执行系统调用,即与系统调用相关的所有处理都在用户空间本身完成(因此 no context switch ) . vsyscallVDSO 就是这样的技术 . 他们背后的想法非常简单 . 它是向用户空间发送执行相应系统调用所需的数据 . 更多信息可以在this LWN article找到 .

    除此之外,还有一些研究项目,其中所有的执行都发生在同一个环中 . 用户空间程序和操作系统代码都位于 same ring 中 . 想法是摆脱环形开关的开销 . Microsoft's [singularity][2] OS就是这样一个项目 .

相关问题