進程的地址空間包括可以 訪問或者引用的記憶體單元的集合。一般通過PC指標來控
制和跟蹤進程中的指令,這條指令稱為控制點,比較新的UNIX支援多個控制點,這
個控制點也就是線程,多個控制點就叫做多線程。線程存在進程之中。進程是宏觀的,線程是微觀的。
進程的地址空間往往是虛擬,往往只有部分映射到實體記憶體單元上。核心將進程
地址空間中的內容(代碼等)儲存在各種儲存物件上,包括實體記憶體,磁碟,交換分區等等。
核心的記憶體管理子系統完成進程的儲存頁面在這些對象之間的轉移。
每個進程還有一組對應於實際的CPU硬體寄存器。將當前啟動並執行進程的寄存器讀入
到硬體寄存器中,將其他進程的寄存器儲存在每個進程的資料結構中。
每個進程有唯一的進程號PID。
進程表是系統用於描述所有當前裝載的進程的一個資料結構,可以用ps來查看他們。
一般來說進程都是由其他進程(稱為父進程)啟動的,被啟動的進程成為自進程。
最早的進程稱為init,PID=1。
採用時間片輪轉的方法分配CPU在各個進程之間使用。
當一個進程需要調用一個外部命令或者一個程式的時候,需要建立一個子進程。
最簡單的方法用system函數,運行shell命令,外部程式(把外部程式的程式名寫入
到一個bash指令檔中,然後在system中運行這個指令碼,可以用&使程式在後台運
行)。
用fork建立子進程後,子進程從父進程脫離出去,按照自己的流程去執行。父進程
啟動並執行程式是代碼中if(pid)中的代碼。公用的代碼由父、子進程交替使用CPU的時
間。如果這塊公用代碼父進程執行完了,那麼父進程使用CPU時間時,繼續往下執
行。
有的時候父進程結束了,子進程還沒有結束,可以在後面的if(pid)中用wait()掛
起,等待子進程結束才開始執行wait()以及下面的代碼。
詳見p204的例子。
fork的一個基本結構:
pid=fork();
switch(pid)
{
case -1;
exit(1);
case 0: //子進程
。。。。(主要是子進程中的變數設定)
default://父進程
。。。。(主要是父進程中的變數設定)
}
。。。//公用程式碼片段,此處父子進程交替使用CPU時間。
if(pid)
{
wait();//等待子進程結束
。。//最後父進程退出
}
殭屍進程會佔用proc結構,因而會減少處於活動狀態的進程總數。子進程退出之後
,父進程清除它之前,它一直處於殭屍狀態,在這個狀態下,它所保留的唯一的資
源就是proc結構。父進程調用wait來釋放該proc結構。
如果父進程先於子進程退出,init進程會領養子進程,清除proc結構。
但是如果子進程先於父進程退出,但是父進程沒有調用wait()函數,子進程的proc
結構將不會被釋放,子進程保持殭屍狀態並佔有proc結構,直到系統重啟。