《Unix Linux系統程式設計》第六章學習筆記

2022-09-10 03:06:07 字數 3023 閱讀 1143

本章講述了訊號和訊號處理;介紹了訊號和中斷的統一處理,有助於從正確的角度看待訊號;將訊號視為程序中斷, 將程序從正常執行轉移到訊號處理;解釋了訊號的**,包括來自硬體、異常和其他程序的訊號;然後舉例說明了訊號在unix/linux 中的常見用法;詳細解釋了 unix/linux 中的訊號處理,包括訊號型別、訊號向景位、訊號掩碼位、程序 proc 結構體中的訊號處理程式以及訊號處理步驟。

訊號和中斷

"中斷」 是從 i/o 裝置或協處理器傳送到 cpu 的外部請求,它將 cpu 從正常執行轉移到中斷處理。與傳送給 cpu 的中斷請求一樣,「訊號」 是傳送給程序的請求,將程序從正常執行轉移到中斷處理。

unix/linux 訊號示例

按 "ctrl+c" 組合鍵通常會導致當前執行的程序終止。 原因如下。 "ctrl+c" 組合鍵會生成乙個鍵盤硬體中斷。 鍵盤中斷處理程式將 "ctrl+c'' 組合鍵轉換為 sigint (2)信 號, 傳送給終端上的所有程序, 並喚醒等待鍵盤輸人的程序。 在核心模式f. 每個程序都要檢查和處理未完成的訊號3 程序對大多數訊號的預設操作是凋用核心的 kexit(exitvalue) 函式來終止亡 在 linux 中, exitvalue 的低位位元組是導致程序終止的訊號編號。

unix/linux 中的訊號處理

unix/linux 支待31種不同的訊號, 每種訊號在 signal.h 檔案中都有定義。

#define sighup 

#define sigint

#define sigquit #define sigill

#define sigtrap #define sigabrt #define sigiot

#define sigbus

#define sigfpe

#define sigkill

#define sigusrl

#define sigse**

#define sigusr2

#define sigpipe

#define sigalrm

#define sigterm

#define sigstkflt

#define sigchld

#define sigcont

#define sigstop

#define sigtstp

#define sigttin

#define sigttou

#define sigurg

#define sigxcpu

#define sigxfsz

#define si**talrm

#define sigprof

#define sigwinch

#define sigpoll

#define sigpwr

#define sigsys

訊號的**

來自硬體中斷的訊號:在程序執行過程中, 一些硬體中斷被轉換為訊號傳送給程序。

來自異常的訊號: 當使用者模式下的程序遇到異常時, 會陷入核心模式, 生成乙個訊號, 並傳送給自己。 常見的陷阱訊號有sigfpe (8), 表示浮點異常(除以 0), 最常 見也是最可怕的是sigse** (11), 表示段錯誤, 等等。

來自其他程序的訊號:程序可使用kill(pid, sig)系統呼叫向pid標識的目標程序傳送訊號。

程序proc 結構體中的訊號

每個程序proc 都有乙個32位向量,用來記錄傳送給程序的訊號。在位向量中,每一

位 (0 位除外)代表乙個訊號編號。此外它還有乙個訊號mask位向盤,用來遮蔽相應的訊號。

訊號處理函式

每個程序proc都有乙個訊號處理陣列intsig[32]o sig[32]陣列的每個條目都指定了如何處理相應的訊號,其中0表示default(預設),1表示ignore(忽略),其他非零值表示使用者模式下預先安裝的訊號捕捉(處理)函式。

安裝訊號捕捉函式

在執行已安裝的訊號捕捉函式之前,通常將訊號處理函式重置為default。為捕捉下次出現的相同訊號,必須重新安裝捕捉函式。這可能會導致下乙個訊號和訊號處理函式重新安裝之間出現競態條件。相反,sigaction()在執行當前捕捉函式時會自動阻塞下-個訊號,因此不會出現競態條件。

signal()不能阻塞其他訊號。必要時,使用者必須使用sigprocmask()顯式地阻塞或解鎖其他訊號。相反,sigaction()可以指定要阻塞的其他訊號。

signal()只能向捕捉函式傳送乙個訊號編號。sigaction()可以傳輸關於訊號的其他資訊。

signal() 可能不適用於多執行緒程式中的執行緒。 sigaction() 適用於執行緒。

不同 unix 版本的 signal() 可能會有所不同。 sigaction() 採用的是 poisx 標準, 可移植性更好。

訊號處理步驟

當某程序處於核心模式時,會檢查訊號並處理未完成的訊號。如果某訊號有使用者安裝的捕捉函式,該程序會先清除訊號,獲取捕捉函式位址,對於大多數陷阱訊號則將已安裝的捕捉函式重置為default。然後,它會在使用者摸式下返回,以執行捕捉函式,以這種方式篡改返回路徑。當捕捉函式結束時.它會返回到最初的中斷點,即它最後進入核心模式的地方。因此,該程序會先迂迴執行捕捉函式,然後再恢復正常執行。

重置使用者安裝的訊號捕捉函式:使用者安裝的陷阱相關訊號捕捉函式用於處理使用者**中的陷阱錯誤。由於捕捉函式也在使用者模式下執行,因此可能會再次出現同樣的錯誤。如果是這樣,該程序最終會陷入無限迴圈,一直在使用者模式和核心模式之間跳躍。為了防止這種情況,unix核心通常會在允許程序執行捕捉函式之前先將處理函式重置為default。這意味著使用者安裝的捕捉函式只對首次出現的訊號有效。若要捕捉再次出現的同一訊號,則必須重新安裝捕捉函式。但是,使用者安裝的訊號捕捉函式的處埋方法並不都一樣,在不同unix 版本中會有所不同。

訊號和喚醒:在unix/linux核心中有兩種sleep程序;深度休眠程序和淺度休眠程序。前-種程序不可中斷,而後一種程序可由訊號中斷。如果某程序處於不可中斷的 sleep狀態,到達的訊號(必須來自硬體中斷或其他程序)不會喚醒程序。如果它處於可中斷的sleep狀態,到達的訊號將會喚醒它。

訊號與異常

unix訊號最初設計用於以下用途。

Unix Linux 程式設計實踐教程第六章習題

tips 這一章習題倒是少,練習題多到頭皮發麻。程式設計練習 6.3 中的毫秒應該是寫錯了,是百毫秒 6.1tr命令用於轉換或刪除檔案中的字元,詳細的用法可以參考 linux tr命令,至於不接受命令行指定檔案,我想是因為標準輸入輸出可以被重定向到任何型別的鏈結上,包括檔案,所以沒有必要接受命令行指...

《Unix Linux系統程式設計》第十三章學習筆記

本章論述了tcp ip 和網路程式設計,分為兩個部分。第一部分論述了tcp ip協議及其應用,具體包括 tcp ip 棧 ip位址 主機名 dns ip資料報和路由器 介紹了tcp ip 網路中的udp和 tcp 協議 埠號和資料流 闡述了伺服器 客戶機計算模型和套接字程式設計介面 通過使用udp和...

《Unix Linux系統程式設計》第十二章學習筆記

本章討論了塊裝置 i o 和緩衝區管理 解釋了塊裝置 i o 的原理和 i o 緩衝的優點 論述了 unix 的緩衝區管理演算法。塊裝置i o緩衝區 i o 緩衝的基本原理非常簡單。檔案系統使用一系列 i o 緩衝區作為塊裝置的快取記憶體。當程序試圖讀取 dev,blk 標識的磁碟塊時,它首先在緩衝...