Linux程序簡述

2021-08-09 00:16:42 字數 2374 閱讀 5023

對於程序的建立,系統呼叫fork()允許乙個程序(父程序)建立乙個新程序(子程序)。新的程序幾乎就等於父程序的翻版,子程序獲得了父程序的棧,資料段,堆和執行文字段的拷貝。

對於程序的終止,則是使用exit(status)函式,此函式會將程序所占用的所有資源(記憶體,檔案描述符等)歸還核心,交給核心進行再次分配。status這個引數則表明了程序退出的狀態,父程序可以使用wait()來獲取到該狀態。

系統會呼叫wait(),其原因有二:

最後,系統呼叫execve(pathname,argv,envp)來載入乙個新的程式到當前程序的記憶體之中,注意,在子程序的記憶體中現在還存在著父程序留下的程式文字段,但是此函式執行後,會丟棄掉現存的程式文字段,並為新程式重新建立棧,資料段,以及堆,把這一系列的行為稱之為:execing。值得注意的是exec開頭的還有多個函式,但是無一例外,它們都是由execve函式為基礎的。

對以上的內容稍微做個總結可以得出如下圖的內容,下圖以乙個shell執行命令為例子:

如上所述,建立新景程主要是使用了以下函式:

#include 

pid_t fork(void)

理解這個函式需要知道如下的資訊:

就**層面上而言,是通過fork的返回值來區別兩個程序的。對於父程序,直接返回的是子程序的程序id,這很好理解,因為父程序通常都會fork出不止乙個子程序,所以知道子程序的程序號是很有必要的,相對地,子程序的返回值則是0,因為它只需要自己就可以了,因為其返回值是0,所以若是有必要的話,子程序可以使用getpid()來得到自身的pid,也可以呼叫getppid來獲取到父程序的pid。

關於fork函式呼叫完 之後的函式執行順序(即誰先被cpu排程),需要知道的就是,這個是無法確定的,這個是很好理解的,因為你無法確認cpu的指令執行進度,在這種時候,很容易出現 」競爭條件「的錯誤,這是由核心根據系統當時的負載而做出的排程決定,因而,很難進行除錯 。若是在這個時候,需要對執行順序進行控制,有以下的方法:

關於fork之後,是子程序先執行,還是父程序先執行,其實各有各的理由,若是父程序先執行,那麼父程序依舊會為子程序複製那些修改後的資料,然而子程序一旦獲得排程,執行exec,之前的複製工作就純粹是浪費。反過來,若是子程序先執行,在這時,父程序這是處於cpu活躍中的狀態,讓其掛起則是低效率的。

雖然這麼說,但是在應用程式來說,無亂哪乙個程序先執行,影響都不大。

程序的終止,主要是有以下兩種方式:

#include 

void _exit(int status);

該函式中的status值定義了終止狀態值,父程序可以呼叫wait()來獲取這個值。按照慣例,當返回值為0時,就表示success,而非0,這是失敗,具體的失敗值需要具體定義。

該函式主要是做了以下步驟的工作:

這裡需要說明下,這個註冊進去的退出程式是由程式設計師自己所定義的內容,執行程式設計師想要的**相關工作。

還需要注意的是,這個退出程式只有在正常退出情況下才會執行,而在異常情況下,則不會執行,這個就很好理解了, 這個只呼叫庫函式時才會呼叫。

有一種情況,那就是父程序需要知道子程序在何時改變了狀態,在linux主要靠以下技術來進行監控:

系統呼叫的函式宣告如下;

#include 

pid_t wait(int

*status);

這個函式的行為主要如下:

大家都知道,父程序與子程序的生命週期一般都是不同的,它們長短不一。這會有以下幾個問題:

* 誰是孤兒程序的父程序?答案是所有程序之父,程序id為1的init程序會接管孤兒程序,換言之,某一程序的父程序終止之後,對其使用getppid會得到1.這也是乙個判斷某一程序直接父程序是否還存在的方法。

* 那麼父程序在執行wait()之前,子程序就終止了,這是什麼情況?這時候系統仍然允許父程序在之後某一時刻去執行wait,以此來確定子程序是如何結束的。在這種情況下,即父程序未執行wait,核心會將程序轉化為殭屍程序,換句話說,系統會將子程序的大部分資源釋放,僅僅在核心程序表中儲存一條記錄,裡面包含了子程序id,終止狀態,資源使用數等資訊。殭屍程序之所以叫殭屍程序,原因在於它無法使用訊號來殺死,這可以確保父程序總是可以執行wait。

但是有乙個問題,若是父程序建立了子程序,然後並沒有執行wait,那麼核心程序表將會永遠為該程序保留這麼一條記錄,若是大量的殭屍程序存在,勢必會填滿核心程序表,從來阻礙新程序的建立。這時候唯一的方法就是殺死它們的父程序,然後將子程序交接給init程序,init程序會自動呼叫wait來清理這些程序

當子程序終止時,其父程序會收到sigchld的訊號,可以利用該訊號設定訊號處理程式來進行處理。

linux程序排程方法簡述

在 linux2.6 中,仍有三種排程策略 sched other sched fifo 和 sched rr。sched orher 普通程序,基於優先順序進行排程。sched fifo 實時程序,實現一種簡單的先進先出的排程演算法。sched rr 實時程序,基於時間片的sched fifo,實...

簡述Linux中的孤兒程序和殭屍程序

父程序先於子程序終止,則子程序變成孤兒程序 乙個臨時中間狀態 系統很快將孤兒程序的父程序設定為init init程序 孤兒領養程序 孤兒收養院 作用 負責作為孤兒程序的父程序,在孤兒程序終止後,程序釋放資源 孤兒程序產生 include include include intmain if pid ...

linux核心(二) 程序管理之程序排程簡述

一 簡述 排程程式負責決定將哪個程序投入執行,何時執行以及執行多長時間,進度排程可看做在可執行程序之間分配有限的處理器時間資源的核心子系統。二 排程器介紹 1 排程器概念 排程器的乙個重要目標是有效的分配cpu時間片,同時提供很好的使用者體驗。排程器的一般原理是按需分配的計算能力,向系統中每個程序提...