1.写时复制
fork()会产生一个和父进程完全相同的子进程,出于效率考虑,linux中引入了“写时复制“技术,也就是只有进程空间的各段的内容要发生变化时,才会将父进程的内容复制一份给子进程。在fork之后exec之前两个进程用的是相同的物理空间(内存区),子进程的代码段、数据段、堆栈都是指向父进程的物理空间,也就是说,两者的虚拟空间不同,但其对应的物理空间是同一个。
2.fork复制的东西
fork时子进程获得父进程的PCB、数据段、堆栈的复制。如果不是因为exec,代码段继续共享父进程的物理空间(两者的代码完全相同)。而如果是因为exec,由于两者执行的代码不同,子进程的代码段也会分配单独的物理空间。
3.子进程特有的属性
子进程从父进程继承大多数的属性,子进程有自己的pid,子进程的进程组id为父进程的id
4.fork返回值
fork 函数的特点是 "调用一次,返回两次":在父进程中调用一次,在父进程和子进程中各返回一次。在父进程中返回时的返回值为子进程的 PID,而在子进程中返回时的返回值为 0,并且返回后都将执行 fork 函数调用之后的语句。如果 fork 函数调用失败,则返回值为 -1。
5.exec函数
使用 fork/vfork 创建子进程后执行的是和父进程相同的程序,子进程往往需要调用一个 exec 族函数以执行另外一个程序。程序调用 exec 的时候,该进程的用户空间代码和数据完全被新程序替换,从新程序的起始处开始执行。调用 exec 族函数并不创建新进程,所以调用 exec 族函数前后该进程的 PID 并不改变。