linux - linux中系统调用机制的疑惑

标签 linux x86 system-calls

我们使用“int”或新的“syscall/sysenter”指令从 ring3 过渡到 ring0。这是否意味着需要为内核修改的页表和其他内容由“int”指令自动完成,或者“int 0x80”的中断处理程序将执行所需的内容并跳转到相应的系统调用。

此外,当从系统调用返回时,我们再次需要转到用户空间。为此我们需要知道用户空间中的指令地址以继续用户应用程序。该地址存储在哪里。 “ret”指令是否会自动将环从 ring3 更改为 ring0,或者这种环更改机制发生在何处/如何发生?

然后,我了解到从 ring3 更改为 ring0 的成本不如从 ring0 更改为 ring3 的成本高。为什么会这样??

谢谢, 巴拉

最佳答案

当切换到内核模式时,页表没有改变——虚拟地址空间的内核部分被简单地标记为只能在 ring0 中访问,所以它只是变得可访问。内核在更改当前进程时更改页表。

int 0x80 指令由陷阱门提供服务,它为处理器提供地址以作为 CS:EIP 对跳转到。新的 CS(代码段选择器)包括一个 CPL(当前特权级别)0,这会影响到 ring0 的转换。

由于从 ring3 到 ring0 的转换,处理器还从 TSS(任务段选择器)中获取 SS:ESP 的新值,并将旧值保存在 TSS 中。这从用户模式堆栈切换到内核堆栈。

然后将先前的 CS:EIP 压入内核堆栈(这是用户空间中的返回地址)。由于 int 0x80 指令本身,所有这些都是由处理器完成的。

IRET 指令可用于返回到用户空间 - 它从内核堆栈中弹出 CS:EIP。由于 CS 包含一个 CPL 3,处理器正在切换回 ring3,这导致它也切换回 ring3 堆栈。

关于linux - linux中系统调用机制的疑惑,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/2807526/

相关文章:

linux - Linux 目标的相关调试数据

assembly - 何时使用 ADOX 代替 ADCX?

linux - 到达ubuntu上linux内核源码的根目录?

assembly - NASM程序集将输入转换为整数?

performance - 英特尔内在函数中的延迟与吞吐量

c - xv6 中 open() 定义的位置

c++ - 在 C++ 中使用 ioprio_set

Python 2.7 - 类

c++ - 在 Linux 上编写 OpenGL 4.X 应用程序的常用库有哪些?

php - 在没有数据库的情况下运行 Drupal 7 网站