裝了4天的作業系統 。。。呵呵收穫頗多。
緬懷Stevens大師。
最好的參考資料:
1.師從互連網。
2.Linux man 命令:man 7 signal,man 7 socket。
3.UNP v1第25章 。
第一條:概述
訊號驅動IO,不是非同步IO。
訊號驅動IO是指:進程預先告知核心,使得 當某個socketfd有events(事件)發生時,核心使用訊號通知相關進程。
非同步IO(Asynchronous IO)是指:進程執行IO系統調用(read / write)告知核心啟動某個IO操作,核心啟動IO操作後立即返回到進程。IO操作即核心當中的服務常式。Posix 通過 aio_XXX函數提供真正的非同步IO(參見 man 7 aio).
linux 2.6.35中定義的相關訊號:
#defineSIGPOLLSIGIO/* Pollable event occurred (System V). */
#defineSIGIO29/* I/O now possible (4.2 BSD). */
第二條: System 訊號驅動IO。
System V Asynchronous I/O
APUE的描述:In System V, asynchronous I/O is part of the STREAMS
system and works only with STREAMS devices and STREAMS pipes. The System
V asynchronous I/O signal is SIGPOLL.To enable asynchronous I/O for a STREAMS device, we have to call ioctl with a second argument (request) of I_SETSIG.
在System V當中,非同步IO是STREAMS機制的一部分,並且她只能工作在流裝置和流管道上。System V 非同步IO訊號是SIGPOLL。我們可以用I_SETSIG為第二個參數調用ioctl,來在一個裝置上開啟非同步IO功能。由於linux拋棄了 STREAMS機制,就不再討論了。呵呵。
第三條:BSD訊號驅動IO。
BSD Asynchronous I/O
APUE的描述:Asynchronous I/O in BSD-derived systems is a combination of two signals: SIGIO and SIGURG.
The former is the general asynchronous I/O signal, and the latter is
used only to notify the process that out-of-band data has arrived on a
network connection.
基於BSD系統的非同步IO機制是通過SIGIO和SIGURG訊號組合實現的。SIGIO用於一般的非同步IO,SIGURG(urgent)僅用於提醒(notify)進程網路連接上有帶外資料到達,什麼是帶外資料,就是一個位元組的緊急資料,用於告訴對端,我們的機器上有某種緊急事件發生了,比方說要宕機。
(0)在描述符上開啟SIGIO訊號驅動IO功能,只需3步,僅需3步喲,就可以不用輪詢機制來耗費CPU接收資料:
1調用signal或sigaction,為訊號SIGIO建立訊號處理函數。
2設定套介面的屬主。通過調用fcntl得F_SETOWN命令,在套介面設定接收SIGIO訊號的進程或進程組。
3開啟套介面上的訊號驅動IO,通過fcntl的F_SETFL命令,在套介面上設定O_ASYNC。
(0.1)注:
1。ioctl的FIOASYNX功能也可實現第3步這個功能。
2。fctl和ioctl所引用的
描述符只能是終端和網路socket。
例子:
signal(SIGIO, &input_handler);
fcntl(STDIN_FILENO, F_SETOWN, getpid());
oflags = fcntl(STDIN_FILENO, F_GETFL);
fcntl(STDIN_FILENO, F_SETFL, oflags | FASYNC);
(1)在描述符上開啟SIGURG訊號驅動IO功能,只需2步。
1調用signal或sigaction,為訊號SIGURG建立訊號處理函數。
2設定套介面的屬主。通過調用fcntl得F_SETOWN命令,在套介面設定接收SIGURG訊號的進程或進程組。
(1.1)註:所引用的描述符只能是:支援帶外資料的網路連接的socket描述符。
第四條:Linux訊號驅動IO
Linux支援BSD的訊號驅動IO。
(0)UDP套介面上SIGIO訊號。
SIGIO在UDP使用是最合適的,UDP套介面上的SIGIO只在以下2種事件種產生:
1。套介面上有資料到達。
2。UDP套介面已經串連的前提下,套介面發生非同步錯誤。
(1)TCP套介面上SIGIO訊號。
SIGIO在TCP上幾乎無用原於產生這種訊號的事件,實在是太多了。Stevens 指出:我們應該考慮只對“監聽(形容詞)TCPsocket”(描述符)使用SIGIO,因為對於“監聽TCPsocket”產生SIGIO的唯一條件是新串連完成。