基礎知識
Linux將所有外部設備都看做一個文件來進行操作。因此,linux對所有外部設備的操作都可以看做是文件的操作。文件的操作當然需要有個標示描述它,這就是文件描述符(file descriptor)。
linux的IO操作如何形象理解呢?
我們說網絡socket的read()是一個IO操作命令,具體流程是這樣的:
應用程序調用read命令,通知內核需要做讀取數據操作
內核創建一個文件描述符
內核從物理層收到讀數據的命令,從網絡中獲取數據包
數據包傳遞到TCP/IP層,解析數據包的頭
內核將數據包緩存在文件描述符的讀緩存區(接受緩存區)中,注意這里的讀緩存區是在內核中的
當文件描述符讀緩存區數據字節數大於應用程序定義的低水位的時候(read的一個參數),此時文件描述符處於讀就緒的狀態
將讀緩存區中的數據復制到應用程序(用戶區)返回
這里需要說明的是
1 每個文件描述符都有自己的讀緩沖區和寫緩沖區,讀緩沖區對應的是read操作,寫緩沖區對應的就是write操作了
2 讀緩沖區和寫緩沖區都是在內核區中
IO模型
現有的linux IO模型有5種:
阻塞式IO模型,非阻塞式IO模型,IO復用模型,信號驅動式IO模型,異步IO模型
經常弄不清楚的就是阻塞,非阻塞,異步,同步
說明一下
上圖給出的同步異步標准是:數據描述符緩存是由誰來進行讀取的?由用戶程序讀取,則判斷為同步;由內核推送,判斷為異步
上圖給出的阻塞非阻塞標准是:調用的用戶進程是否是阻塞的狀態
這里關於這五種IO模型的阻塞同步狀態有很多種說法,比較有爭議的是IO復用模型和信號驅動IO模型的判斷分類上,推薦這一種判斷:
關於IO的同步、異步、阻塞、非阻塞參考文檔

本文基於署名-非商業性使用 3.0許可協議發布,歡迎轉載,演繹,但是必須保留本文的署名葉劍峰(包含鏈接http://www.cnblogs.com/yjf512/),且不得用於商業目的。如您有任何疑問或者授權方面的協商,請與我聯系。