Java NIO之基礎(chǔ)知識(shí)篇

緩沖區(qū)操作

?? ?進(jìn)程執(zhí)行I/O操作,歸結(jié)起來,也就是向操作系統(tǒng)發(fā)出請求,讓它要么把緩沖區(qū)里的數(shù)據(jù)排干(寫),要么用數(shù)據(jù)把緩沖區(qū)填滿(讀)。進(jìn)程使用這一機(jī)制處理所有數(shù)據(jù)進(jìn)出操作。

I/O緩沖區(qū)操作簡圖

進(jìn)程使用read()系統(tǒng)調(diào)用,要求其緩沖區(qū)被填滿。內(nèi)核隨即向磁盤控制硬件發(fā)出命令,要求其從磁盤讀取數(shù)據(jù)。磁盤控制器把數(shù)據(jù)直接寫入內(nèi)核內(nèi)存緩沖區(qū),這一步通過DMA完成,無需主CPU協(xié)助。一旦磁盤控制器把緩沖區(qū)裝滿,內(nèi)核即把數(shù)據(jù)從內(nèi)核空間的臨時(shí)緩沖區(qū)拷貝到進(jìn)程執(zhí)行read()調(diào)用時(shí)指定的緩沖區(qū)。

用戶空間:常規(guī)進(jìn)程所在區(qū)域。JVM就是常規(guī)進(jìn)程,駐守于用戶空間。用戶空間是非特權(quán)區(qū)域。

內(nèi)核空間:操作系統(tǒng)所在區(qū)域。內(nèi)核代碼有特別的權(quán)力:它能與設(shè)備控制器通訊,控制著用戶區(qū)域進(jìn)程的運(yùn)行狀態(tài),等等。最重要的是,所有I/O都直接或間接通過內(nèi)核空間。

當(dāng)進(jìn)程請求I/O操作的時(shí)候,它執(zhí)行一個(gè)系統(tǒng)調(diào)用將控制權(quán)交給內(nèi)核。當(dāng)內(nèi)核以這種方式被調(diào)用時(shí),它隨即采取任何必要步驟,找到進(jìn)程所需數(shù)據(jù),并把數(shù)據(jù)傳送到用戶空間的指定緩沖區(qū)。內(nèi)核試圖對數(shù)據(jù)進(jìn)行高速緩存或預(yù)讀取,因此進(jìn)程所需數(shù)據(jù)可能已經(jīng)在內(nèi)核空間里了。如果是這樣,該數(shù)據(jù)只要簡單的拷貝出來即可。如果數(shù)據(jù)不再內(nèi)存空間,則進(jìn)程被掛起,內(nèi)核著手把數(shù)據(jù)讀進(jìn)內(nèi)存。

為什么不直接讓磁盤控制器把數(shù)據(jù)送到用戶空間的緩沖區(qū)?

1.硬件通常不能直接訪問用戶空間

2.磁盤基于塊存儲(chǔ)操作的是固定大小的數(shù)據(jù)塊,而用戶進(jìn)程請求的可能是任意大小的或非對齊的數(shù)據(jù)塊。在數(shù)據(jù)往來于用戶空間與存儲(chǔ)設(shè)備的過程中,內(nèi)核負(fù)責(zé)數(shù)據(jù)的分解、再組合工作,充當(dāng)著中間人的角色。

發(fā)散/匯聚

根據(jù)發(fā)散/匯聚的概念,進(jìn)程只需一個(gè)系統(tǒng)調(diào)用,就能把一連串緩沖區(qū)地址傳遞給操作系統(tǒng)。然后內(nèi)核就可以順序填充或排干多個(gè)緩沖區(qū),讀的時(shí)候就把數(shù)據(jù)發(fā)散到多個(gè)用戶空間緩沖區(qū),寫的時(shí)候再從多個(gè)緩沖區(qū)把數(shù)據(jù)匯聚起來。

三個(gè)緩沖區(qū)的發(fā)散讀操作

這樣用戶進(jìn)程就不必多次執(zhí)行系統(tǒng)調(diào)用,內(nèi)核也可以優(yōu)化數(shù)據(jù)的處理過程,因?yàn)樗颜莆沾齻鬏敂?shù)據(jù)的全部信息。如果系統(tǒng)配有多個(gè)CPU,甚至可以同時(shí)填充或排干多個(gè)緩沖區(qū)。

虛擬內(nèi)存

? ? 使用虛擬地址取代物理內(nèi)存地址。

? ? 好處:

? ? ? ? 1.一個(gè)以上的虛擬地址可指向同一個(gè)物理內(nèi)存地址。

? ? ? ? 2.虛擬內(nèi)存空間可大于實(shí)際可用的硬件內(nèi)存。

把內(nèi)核空間地址與用戶空間的虛擬地址映射到同一物理地址,這樣,DMA硬件(只能訪問物理內(nèi)存地址)就可以填充對內(nèi)核與用戶空間進(jìn)程同時(shí)可見的緩沖區(qū)。


內(nèi)存空間多重映射

省去了內(nèi)核與用戶空間的往來拷貝。

前提條件:內(nèi)核與用戶緩沖區(qū)必須使用相同的頁對齊,緩沖區(qū)的大小還必須是磁盤控制器塊大小的倍數(shù)


內(nèi)存頁

上圖顯示了多個(gè)虛擬地址的虛擬內(nèi)存頁是如何映射到物理內(nèi)存的。

內(nèi)存頁面調(diào)度

為了支持虛擬內(nèi)存尋址空間大于物理內(nèi)存的特性,就必須進(jìn)行內(nèi)存分頁。虛擬內(nèi)存空間的頁面能夠繼續(xù)存在于外部磁盤存儲(chǔ),這樣就為物理內(nèi)存中的其它虛擬頁面騰出了空間。從本質(zhì)上來說,物理內(nèi)存充當(dāng)了分頁區(qū)的高速緩存,而所謂的分頁區(qū),即從物理內(nèi)存置換出來,轉(zhuǎn)而存儲(chǔ)于磁盤上的內(nèi)存頁面。


用于分頁區(qū)高速緩存的物理內(nèi)存

上圖顯示了分屬于四個(gè)進(jìn)程的虛擬頁面,其中每個(gè)進(jìn)程都有屬于自己的虛擬內(nèi)存空間,進(jìn)程A有五個(gè)頁面,其中兩個(gè)裝入內(nèi)存,其余存儲(chǔ)于磁盤。

現(xiàn)代CPU包含一個(gè)稱為內(nèi)存管理單元(MMU)的子系統(tǒng),該設(shè)備包含虛擬地址向物理內(nèi)存地址轉(zhuǎn)換時(shí)所需映射信息。當(dāng)CPU引用某內(nèi)存地址時(shí),MMU負(fù)責(zé)確定該地址所在頁,并將虛擬頁號轉(zhuǎn)換為物理頁號(這一步由硬件完成,速度極快)。如果當(dāng)前不存在與虛擬頁形成有效映射的物理內(nèi)存頁,MMU會(huì)向CPU提交一個(gè)頁錯(cuò)誤。然后把控制權(quán)交給內(nèi)核,由內(nèi)核主導(dǎo)從磁盤上將該頁讀入物理內(nèi)存,更新MMU。

文件I/O

文件I/O屬文件系統(tǒng)范疇,文件系統(tǒng)與磁盤迥然不同。磁盤屬于存儲(chǔ)的硬件設(shè)備,文件系統(tǒng)是更高層次的抽象,是安排、解釋磁盤數(shù)據(jù)的一種獨(dú)特方式。

文件系統(tǒng)把一連串大小一致的數(shù)據(jù)塊組織到一起。當(dāng)用戶進(jìn)程請求讀取文件數(shù)據(jù)時(shí),文件系統(tǒng)需要確定數(shù)據(jù)具體在磁盤什么位置,然后著手把相關(guān)磁盤扇區(qū)讀進(jìn)內(nèi)存。

操作系統(tǒng)還有頁的概念,其大小或者與基本內(nèi)存頁一致,或者是其倍數(shù)。典型的操作系統(tǒng)頁從2048到8192字節(jié)不等,且始終是基本內(nèi)存頁大小的倍數(shù)。

采用分頁技術(shù)的操作系統(tǒng)執(zhí)行I/O的全過程可總結(jié)為以下幾步:

1.確定請求的數(shù)據(jù)分布在文件系統(tǒng)的哪些頁。

2.在內(nèi)核空間分配足夠數(shù)量的內(nèi)存頁,以容納得到確定的文件系統(tǒng)頁。

3.在內(nèi)存頁與磁盤上的文件系統(tǒng)頁之間建立映射。

4.為每一個(gè)內(nèi)存頁產(chǎn)生錯(cuò)誤。

5.虛擬內(nèi)存系統(tǒng)俘獲頁錯(cuò)誤,安排頁面調(diào)入,從磁盤上讀取頁內(nèi)容,使頁有效。

6.一旦頁面調(diào)入操作完成,文件系統(tǒng)即對原始數(shù)據(jù)進(jìn)行解析,取得所需文件內(nèi)容或?qū)傩孕畔ⅰ?/p>

內(nèi)存映射文件

用戶內(nèi)存到文件系統(tǒng)頁的映射

內(nèi)存映射I/O使用文件系統(tǒng)建立從用戶空間直到可用文件系統(tǒng)頁的虛擬內(nèi)存映射。好處如下:

1.用戶進(jìn)程把文件數(shù)據(jù)當(dāng)成內(nèi)存,所以無需發(fā)布read()或write()系統(tǒng)調(diào)用。

2.當(dāng)用戶進(jìn)程碰觸到映射內(nèi)存空間,頁錯(cuò)誤會(huì)自動(dòng)產(chǎn)生從而將文件數(shù)據(jù)從磁盤讀進(jìn)內(nèi)存。如果用戶修改了內(nèi)存映射空間,相關(guān)頁會(huì)自動(dòng)標(biāo)記為臟隨后刷新到磁盤,文件得到更新。

3.操作系統(tǒng)的虛擬內(nèi)存子系統(tǒng)會(huì)對頁進(jìn)行智能高速緩存,自動(dòng)根據(jù)系統(tǒng)負(fù)載進(jìn)行內(nèi)存管理。

4.數(shù)據(jù)總是按頁對齊,無需執(zhí)行緩沖區(qū)拷貝。

5.大型文件使用映射,無需耗費(fèi)大量內(nèi)存即可進(jìn)行數(shù)據(jù)拷貝。

流I/O

流的傳輸一般比塊設(shè)備慢,經(jīng)常用于間歇性輸入。多數(shù)操作系統(tǒng)允許把流置于非塊模式,這樣,進(jìn)程可以查看流上是否有輸入,即便當(dāng)時(shí)沒有也不影響它干別的。這樣一種能力使得進(jìn)程可以在有輸入的時(shí)候進(jìn)行處理,輸入閑置的時(shí)候執(zhí)行其他功能。。

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時(shí)請結(jié)合常識(shí)與多方信息審慎甄別。
平臺(tái)聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點(diǎn),簡書系信息發(fā)布平臺(tái),僅提供信息存儲(chǔ)服務(wù)。

相關(guān)閱讀更多精彩內(nèi)容

友情鏈接更多精彩內(nèi)容