UNIX網絡編程讀書筆記:I/O模型(阻塞、非阻塞、I/O復用、信號驅動、異步)


I/O模型

UNIX下可用的5種I/O模型:

(1)阻塞I/O

(2)非阻塞I/O

(3)I/O復用(select和poll)

(4)信號驅動I/O(SIGIO)

(5)異步I/O

對於一個套接口上的輸入操作,第一步通常涉及等待數據從網絡中到達。當所等待分組到達時,它被拷貝到內核中的某個緩沖區。第二步就是把數據從內核緩沖區拷貝到應用進程緩沖區。

1、阻塞I/O模型

最流行的I/O模型是阻塞I/O(blocking I/O)模型。缺省情況下,所有套接口都是阻塞的。

以數據報套接口作為例子,我們有下圖所示的情形:

image

進程調用recvfrom,其系統調用直到數據報到達且被拷貝到應用進程的緩沖區中或者發生錯誤才返回。最常見的錯誤是系統調用被信號中斷。我們說進程在從調用recvfrom開始到它返回的整段時間內是被阻塞的recvfrom成功返回后,應用進程開始處理數據。

2、非阻塞I/O模型

進程把一個套接口設置成非阻塞是在通知內核:當所請求的I/O操作非得把本進程投入睡眠才能完成時,不要把本進程投入睡眠,而是返回一個錯誤。下圖展示了非阻塞I/O模型。

image

前三次調用recvfrom時沒有數據可返回,因此內核轉而立即返回一個EWOULDBLOCK錯誤。第四次調用recvfrom時已有數據報准備好,它被拷貝到應用進程緩沖區,recvfrom於是成功返回。我們接着處理數據。

當一個應用進程像這樣對一個非阻塞描述字循環調用recvfrom時,我們稱之為輪詢(polling)。應用進程持續輪詢內核,以查看某個操作是否就緒。這么做往往耗費大量CPU時間,不過這種模型偶爾也會遇到,通常是在只專門提供某種功能的系統中才有。

3、I/O復用模型

有了I/O復用(I/O multiplexing),我們就可以調用select或poll,阻塞在這兩個系統調用中的某一個之上,而不是阻塞在真正的I/O系統調用上。下圖展示了I/O復用模型。

image

我們阻塞於select調用,等待數據報套接口變為可讀。當select返回套接口可讀這一條件時,我們調用recvfrom把所讀數據報拷貝到應用進程緩沖區。

比較I/O復用模型和阻塞I/O模型,I/O復用並沒有顯示出什么優勢,事實上由於使用select需要使用兩個而不是單個系統調用,I/O復用還稍有劣勢。使用select的優勢在於我們可以等待多個描述字就緒。

與I/O復用密切相關的另一種I/O模型是在多線程中使用阻塞I/O。這種模型與I/O復用模型極為相似,代替使用select阻塞在多個文件描述字上的是,使用多個線程(每個文件描述字一個線程),這樣每個線程都可以自由地調用諸如recvfrom之類的阻塞式I/O系統調用了。

4、信號驅動I/O模型

我們也可以用信號,讓內核在描述字就緒時發送SIGIO信號通知我們。我們稱這種模型為信號驅動I/O(signal-driven I/O),如下圖所示:

image

我們首先開啟套接口的信號驅動I/O功能,並通過sigaction系統調用安裝一個信號處理函數。該系統調用立即返回,我們的進程繼續工作,也就是說它沒有被阻塞。當數據報准備好讀取時,內核就為該進程產生一個SIGIO信號。我們隨后既可以在信號處理函數中調用recvfrom讀取數據報,並通知主循環數據已准備好待處理,也可以立即通知主循環,讓它讀取數據報。

無論如何處理SIGIO信號,這種模型的優勢在於等待數據報到達期間,進程不被阻塞。主循環可以繼續執行,只要不時等待來自信號處理函數的通知:既可以是數據已准備好被處理,也可以是數據報已准備好被讀取。

5、異步I/O模型

異步I/O(asynchronous I/O)由POSIX規范定義。一般地說,這些函數的工作機制是:告知內核啟動某個操作,並讓內核在整個操作(包括將數據從內核拷貝到我們自己的緩沖區)完成后通知我們。這種模型與信號驅動模型的主要區別在於:信號驅動I/O是由內核通知我們何時啟動一個I/O操作,而異步I/O模型是由內核通知我們I/O操作何時完成。

image

我們調用aio_read函數(POSIX異步I/O函數以aio_或lio_開頭),給內核傳遞描述字、緩沖區指針、緩沖區大小(與read相同的三個參數)、文件偏移(與lseek類似),並告訴內核當整個操作完成時如何通知我們。該系統調用立即返回,在等待I/O完成期間,我們的進程不被阻塞。

6、各種模型的比較

image

7、同步I/O和異步I/O

POSIX把這兩個術語定義如下:

  • 同步I/O操作(synchronous I/O operation)導致請求進程阻塞,直到I/O操作完成。
  • 異步I/O操作(asynchronous I/O operation)不導致請求進程阻塞。

根據上述定義,我們的前4種模型——阻塞I/O模型、非阻塞I/O模型、I/O復用模型和信號驅動I/O模型都是同步I/O模型,因為其中真正的I/O操作(recvfrom)將阻塞進程。只有異步I/O模型與POSIX定義的異步I/O相匹配。


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM