精華)2020年7月22日 ASP.NET Core Swagger的使用(NSwag工具版)">(精華)2020年7月22日 ASP.NET Core Swagger的使用(NSwag工具版)
840
2025-04-04
一、什么是IO?
我們都知道unix世界里、一切皆文件、而文件是什么呢?文件就是一串二進制流而已、不管socket、還是FIFO、管道、終端、對我們來說、一切都是文件、一切都是流、在信息交換的過程中、我們都是對這些流進行數(shù)據(jù)的收發(fā)操作、簡稱為I/O操作(input and output)、往流中讀出數(shù)據(jù)、系統(tǒng)調(diào)用read、寫入數(shù)據(jù)、系統(tǒng)調(diào)用write、不過話說回來了、計算機里有這么多的流、我怎么知道要操作哪個流呢?做到這個的就是文件描述符、即通常所說的fd、一個fd就是一個整數(shù)、所以對這個整數(shù)的操作、就是對這個文件(流)的操作、我們創(chuàng)建一個socket、通過系統(tǒng)調(diào)用會返回一個文件描述符、那么剩下對socket的操作就會轉(zhuǎn)化為對這個描述符的操作、不能不說這又是一種分層和抽象的思想。
二、IO交互## 標題
通常用戶進程中的一個完整IO分為兩個階段:
用戶空間<------------->內(nèi)核空間、
內(nèi)核空間<------------->設(shè)備空間、
內(nèi)核空間中存放的是內(nèi)核代碼和數(shù)據(jù)、而進程的用戶空間中存放的是用戶程序的代碼和數(shù)據(jù)、不管是內(nèi)核空間還是用戶空間、它們都處于虛擬空間中、Linux使用兩級保護機制:0級供內(nèi)核使用、3級供用戶程序使用、
操作系統(tǒng)和驅(qū)動程序運行在內(nèi)核空間、應(yīng)用程序運行在用戶空間、兩者不能簡單地使用指針傳遞數(shù)據(jù)、因為Linux使用的虛擬內(nèi)存機制、其必須通過系統(tǒng)調(diào)用請求kernel來協(xié)助完成IO動作、內(nèi)核會為每個IO設(shè)備維護一個緩沖區(qū)、用戶空間的數(shù)據(jù)可能被換出、當內(nèi)核空 間使用用戶空間指針時、對應(yīng)的數(shù)據(jù)可能不在內(nèi)存中
對于一個輸入操作來說、進程IO系統(tǒng)調(diào)用后、內(nèi)核會先看緩沖區(qū)中有沒有相應(yīng)的緩存數(shù)據(jù)、沒有的話再到設(shè)備中讀取、因為設(shè)備IO一般速度較慢、需要等待、內(nèi)核緩沖區(qū)有數(shù)據(jù)則直接復(fù)制到進程空間、
所以、對于一個網(wǎng)絡(luò)輸入操作通常包括兩個不同階段:
(1)等待網(wǎng)絡(luò)數(shù)據(jù)到達網(wǎng)卡 –> 讀取到內(nèi)核緩沖區(qū)
(2)從內(nèi)核緩沖區(qū)復(fù)制數(shù)據(jù) –> 用戶空間
IO有內(nèi)存IO、網(wǎng)絡(luò)IO和磁盤IO三種、通常我們說的IO指的是后兩者
1.阻塞IO(blocking I/O)
A拿著一支魚竿在河邊釣魚,并且一直在魚竿前等,在等的時候不做其他的事情,十分專心。只有魚上鉤的時,才結(jié)束掉等的動作,把魚釣上來。
在內(nèi)核將數(shù)據(jù)準備好之前,系統(tǒng)調(diào)用會一直等待所有的套接字,默認的是阻塞方式。
其實,我們例子中所說的魚竿就是這一個文件描述符。這個模型是我們最常見的,程序調(diào)用和我們編寫的基本程序是一致的。
程序的read必須在write之后執(zhí)行,當write阻塞住了,read就不能執(zhí)行下去,一直處于等待狀態(tài)。
2.非阻塞IO(noblocking I/O)
B也在河邊釣魚,但是B不想將自己的所有時間都花費在釣魚上,在等魚上鉤這個時間段中,B也在做其他的事情(一會看看書,一會讀讀報紙,一會又去看其他人的釣魚等),但B在做這些事情的時候,每隔一個固定的時間檢查魚是否上鉤。一旦檢查到有魚上鉤,就停下手中的事情,把魚釣上來。
其實,B在檢查魚竿是否有魚,是一個輪詢的過程。
每次客戶詢問內(nèi)核是否有數(shù)據(jù)準備好,即文件描述符緩沖區(qū)是否就緒。當有數(shù)據(jù)報準備好時,就進行拷貝數(shù)據(jù)報的操作。當沒有數(shù)據(jù)報準備好時,也不阻塞程序,內(nèi)核直接返回未準備就緒的信號,等待用戶程序的下一個輪尋。
但是,輪尋對于CPU來說是較大的浪費,一般只有在特定的場景下才使用。
3.信號驅(qū)動IO(signal blocking I/O)
C也在河邊釣魚,但與A、B不同的是,C比較聰明,他給魚竿上掛一個鈴鐺,當有魚上鉤的時候,這個鈴鐺就會被碰響,C就會將魚釣上來。
信號驅(qū)動IO模型,應(yīng)用進程告訴內(nèi)核:當數(shù)據(jù)報準備好的時候,給我發(fā)送一個信號,對SIGIO信號進行捕捉,并且調(diào)用我的信號處理函數(shù)來獲取數(shù)據(jù)報。
4.IO多路復(fù)用(I/O multiplexing)
D同樣也在河邊釣魚,但是D生活水平比較好,D拿了很多的魚竿,一次性有很多魚竿在等,D不斷的查看每個魚竿是否有魚上鉤。增加了效率,減少了等待的時間。
IO多路轉(zhuǎn)接是多了一個select函數(shù),select函數(shù)有一個參數(shù)是文件描述符集合,對這些文件描述符進行循環(huán)監(jiān)聽,當某個文件描述符就緒時,就對這個文件描述符進行處理。
其中,select只負責等,recvfrom只負責拷貝。
IO多路轉(zhuǎn)接是屬于阻塞IO,但可以對多個文件描述符進行阻塞監(jiān)聽,所以效率較阻塞IO的高。
5.異步IO(asynchronous I/O)
E也想釣魚,但E有事情,于是他雇來了F,讓F幫他等待魚上鉤,一旦有魚上鉤,F(xiàn)就打電話給E,E就會將魚釣上去。
當應(yīng)用程序調(diào)用aio_read時,內(nèi)核一方面去取數(shù)據(jù)報內(nèi)容返回,另一方面將程序控制權(quán)還給應(yīng)用進程,應(yīng)用進程繼續(xù)處理其他事情,是一種非阻塞的狀態(tài)。
當內(nèi)核中有數(shù)據(jù)報就緒時,由內(nèi)核將數(shù)據(jù)報拷貝到應(yīng)用程序中,返回aio_read中定義好的函數(shù)處理程序。
很少有Linux系統(tǒng)支持,Windows的IOCP就是該模型。
可以看出,阻塞程度:阻塞IO>非阻塞IO>多路轉(zhuǎn)接IO>信號驅(qū)動IO>異步IO,效率是由低到高的。
任務(wù)調(diào)度
版權(quán)聲明:本文內(nèi)容由網(wǎng)絡(luò)用戶投稿,版權(quán)歸原作者所有,本站不擁有其著作權(quán),亦不承擔相應(yīng)法律責任。如果您發(fā)現(xiàn)本站中有涉嫌抄襲或描述失實的內(nèi)容,請聯(lián)系我們jiasou666@gmail.com 處理,核實后本網(wǎng)站將在24小時內(nèi)刪除侵權(quán)內(nèi)容。
版權(quán)聲明:本文內(nèi)容由網(wǎng)絡(luò)用戶投稿,版權(quán)歸原作者所有,本站不擁有其著作權(quán),亦不承擔相應(yīng)法律責任。如果您發(fā)現(xiàn)本站中有涉嫌抄襲或描述失實的內(nèi)容,請聯(lián)系我們jiasou666@gmail.com 處理,核實后本網(wǎng)站將在24小時內(nèi)刪除侵權(quán)內(nèi)容。