1. 程式人生 > >Linux系統呼叫

Linux系統呼叫

一、系統呼叫概述

  系統呼叫,顧名思義,說的是作業系統提供給使用者程式呼叫的一組“特殊”介面。使用者程式可以通過這組“特殊”介面來獲得作業系統核心提供的服務,比如使用者可以通過檔案系統相關的呼叫請求系統開啟檔案、關閉檔案或讀寫檔案,可以通過時鐘相關的系統呼叫獲得系統時間或設定定時器等。

  從邏輯上來說,系統呼叫可被看成是一個核心與使用者空間程式互動的介面——它好比一箇中間人,把使用者程序的請求傳達給核心,待核心把請求處理完畢後再將處理結果送回給使用者空間。 在這裡插入圖片描述   系統服務之所以需要通過系統呼叫來提供給使用者空間的根本原因是為了對系統進行“保護”,因為我們知道 Linux 的執行空間分為核心空間與使用者空間

,它們各自執行在不同的級別中,邏輯上相互隔離。所以使用者程序在通常情況下不允許訪問核心資料,也無法使用核心函式,它們只能在使用者空間操作使用者資料,呼叫使用者空間函式。比如我們熟悉的“hello world”程式(執行時)就是標準的使用者空間程序,它使用的列印函式 printf 就屬於使用者空間函式,列印的字元“hello word”字串也屬於使用者空間資料。

  但是很多情況下,使用者程序需要獲得系統服務(呼叫系統程式),這時就必須利用系統提供給使用者的“特殊介面”——系統呼叫了,它的特殊性主要在於規定了使用者程序進入核心的具體位置;換句話說,使用者訪問核心的路徑是事先規定好的,只能從規定位置進入核心,而不准許肆意跳入核心。有了這樣的陷入核心的統一訪問路徑限制才能保證核心安全無誤。

二、系統呼叫的實現

  系統呼叫是屬於作業系統核心的一部分的,必須以某種方式提供給程序讓它們去呼叫。CPU 可以在不同的特權級別下執行,而相應的作業系統也有不同的執行級別,使用者態和核心態。執行在核心態的程序可以毫無限制的訪問各種資源,而在使用者態下的使用者程序的各種操作都有著限制,比如不能隨意的訪問記憶體、不能開閉中斷以及切換執行的特權級別。顯然,屬於核心的系統呼叫一定是執行在核心態下,但是如何切換到核心態呢?答案是軟體中斷。軟體中斷和我們常說的中斷(硬體中斷)不同之處在於,它是通過軟體指令觸發而並非外設引發的中斷,也就是說,又是程式設計人員開發出的一種異常(該異常為正常的異常)。作業系統一般是通過軟體中斷從使用者態切換到核心態。

  中斷有兩個重要的屬性:中斷號和中斷處理程式。中斷號用來標識不同的中斷,不同的中斷具有不同的中斷處理程式。在作業系統核心中維護著一個中斷向量表(Interrupt Vector Table),這個陣列儲存了所有中斷處理程式的地址,而中斷號就是相應中斷在中斷向量表中的偏移量。

三、系統呼叫和庫函式的區別

  Linux 下對檔案操作有兩種方式:系統呼叫(system call)和庫函式呼叫(Library functions)。

庫函式由兩類函式組成:

(1)不需要呼叫系統呼叫

  不需要切換到核心空間即可完成函式全部功能,並且將結果反饋給應用程式,如strcpy、bzero 等字串操作函式。

(2)需要呼叫系統呼叫

  需要切換到核心空間,這類函式通過封裝系統呼叫去實現相應功能,如 printf、fread等。 在這裡插入圖片描述   系統呼叫是需要時間的,程式中頻繁的使用系統呼叫會降低程式的執行效率。當執行核心程式碼時,CPU工作在核心態,在系統呼叫發生前需要儲存使用者態的棧和記憶體環境,然後轉入核心態工作。系統呼叫結束後,又要切換回使用者態。這種環境的切換會消耗掉許多時間庫函式訪問檔案的時候根據需要,設定不同型別的緩衝區,從而減少了直接呼叫 IO 系統呼叫的次數,提高了訪問效率。