vfork函式建立出的父子程式

holyshit666發表於2016-08-27

vfork函式建立新程式的主要目的在於用exec函式執行另外的程式。在沒呼叫exec或exit之前子程式的執行中是與父程式共享資料段的,在vfork呼叫中,子程式先執行,父程式掛起,直到子程式呼叫exec或exit,在這之後,父子程式的執行順序不在有限制。

例:

  1 #include<stdio.h>
  2 #include<stdlib.h>
  3 #include<unistd.h>
  4 #include<sys/types.h>
  5 
  6 int main()
  7 {
  8         int g_val = 100;
  9         pid_t id = vfork();
 10         if(id == 0)
 11         {
 12                 g_val++;
 13                 printf("child,running first...%d:%p\n",g_val,&g_val);
 14                 sleep(1);
 15                 //exit(0);
 16
 17         }
 18         else
 19         {
 20                 printf("father,running second...%d:%p\n",g_val,&g_val);
 21         }
 22         return 0;
 23 }

在執行這個程式之後,會發生什麼情況呢?執行結果如下:


在列印了第一行child,running first之後,每隔一秒列印兩行father...和child...。

這是由於在子程式呼叫exec或exit之前,在父程式空間中執行,也就是說會更改父程式的資料段,棧和堆。每個程式在核心中都有一個程式控制塊(PCB)來維護程式相關的資訊。子程式在執行sleep(1)時,更改了父程式中程式控制塊的程式計數器,程式中將被執行下一條指令的地址被修改為子程式的地址,所以在父程式結束後又執行了子程式。如此迴圈往復就得到了我們看到的情況。

若在原始檔中加上exit(0),結果如何?


在列印child...之後一秒列印father...程式執行結束。由於子程式在sleep(1)後退出,那麼父程式結束後程式結束。

總結:

1:vfork保證子程式先執行,在它呼叫exec或者exit後父程式才被排程執行;

2:在子程式呼叫exec或exit之前,在父程式空間中執行,會改變父程式的pcb。


相關文章