我知道fork()在更高级别上做了什么。我想知道的是这个 -
只要有一个fork调用,就会跟随一个trap指令并控制跳转来执行fork“handler”。现在,通过创建另一个地址空间和进程控制块来复制父进程,创建子进程的处理程序如何返回2个值,每个进程一个?
执行什么时候fork会返回2个值?
简而言之,有人可以解释拨打电话后在较低级别发生的分步事件吗?
答案 0 :(得分:1)
这不是那么难 - fork()系统调用的内核一半可以通过您提到的过程控制块来区分这两个进程,但您甚至不需要这样做。所以伪代码看起来像:
int fork()
{
int orig_pid = getpid();
int new_pid = kernel_do_fork(); // Now there's two processes
// Remember, orig_pid is the same in both procs
if (orig_pid == getpid()) {
return new_pid;
}
// Must be the child
return 0;
}
修改强> 朴素版本就像您描述的那样 - 它创建一个新的流程上下文,复制所有相关的线程上下文,复制所有页面和文件映射,然后将新流程放入“准备运行”列表中。
我认为你感到困惑的部分是,当这些进程恢复时(即当父进程从kernel_do_fork返回,并且第一次调度子进程)时,它将从中间开始函数的em>(即首先执行'if')。这是一个精确副本 - 两个进程都将执行该函数的后半部分。
答案 1 :(得分:1)
返回到每个进程的值是不同的。父/原始线程得到子进程的PID,子进程得到0。
Linux内核通过在父进程中将eax寄存器中的值更改为copies the current thread来在x86上实现此目的。