從操作系統(tǒng)說起
計算機(jī)系統(tǒng)是由“硬件”和“軟件”兩大部分組成,計算機(jī)硬件包括一個或多個處理器(CPU)、內(nèi)存、鍵盤、顯示器、磁盤、I/O接口以及其他一些外圍設(shè)備比如打印機(jī),繪圖儀等等。
總之,計算機(jī)硬件部分是一個由多種電子和機(jī)械設(shè)備組成的硬件系統(tǒng)。
為了讓人方便正確使用這些設(shè)備,就需要編寫若干程序來管理這些設(shè)備,正是這些程序組成了計算機(jī)的軟件系統(tǒng)。軟件也可以分為兩大類:系統(tǒng)軟件和應(yīng)用軟件。人們首先直接在硬件上加載一層程序,用它來管理整個計算機(jī)硬件設(shè)備以及一些軟件信息資源,同時還為用戶提供開發(fā)應(yīng)用程序的環(huán)境,這就是操作系統(tǒng)軟件和實用軟件。應(yīng)用軟件是在操作系統(tǒng)支持下,為實現(xiàn)用戶要求而編制的各種應(yīng)用程序。

CPU、內(nèi)存和I/O接口組成的主設(shè)備通常稱為主機(jī),把沒有加載操作系統(tǒng)的主機(jī)叫做裸機(jī)。裸機(jī)與操作系統(tǒng)軟件的接口是由CPU的指令系統(tǒng)和廠商提供的系統(tǒng)BIOS組成。
由于操作系統(tǒng)向用戶隱藏了系統(tǒng)使用的硬件設(shè)備,因此操作系統(tǒng)要為它上面的應(yīng)用系統(tǒng)軟件提供一組命令或系統(tǒng)調(diào)用接口供用戶程序使用。比如我們需要使用磁盤,可以通過系統(tǒng)命名或系統(tǒng)調(diào)用來間接完成,而不需要親自手動編寫一個磁盤設(shè)備驅(qū)動程序。因此對于用戶來說,當(dāng)計算機(jī)加載操作系統(tǒng)后,用戶不直接與計算機(jī)硬件打交道,而是利用操作系統(tǒng)提供的命令和功能區(qū)使用計算機(jī)。
由于操作系統(tǒng)處于硬件和軟件的中央位置,因此很早就有人把操作系統(tǒng)成為計算機(jī)系統(tǒng)軟件的核心,簡稱核心或內(nèi)核。
內(nèi)核態(tài)和用戶態(tài)
從系統(tǒng)安全和保護(hù)的角度出發(fā),在進(jìn)行計算機(jī)體系結(jié)構(gòu)設(shè)計時,處理機(jī)的執(zhí)行模式一般設(shè)定為兩種:分別稱為內(nèi)核模式(內(nèi)核態(tài))和用戶模式(用戶態(tài))。當(dāng)處理機(jī)處于內(nèi)核模式執(zhí)行時,意味著系統(tǒng)除了可以執(zhí)行一般指令外,還可以執(zhí)行特權(quán)指令,即可以執(zhí)行訪問各種控制寄存器的指令、I/O指令以及程序狀態(tài)字。
當(dāng)處理機(jī)處于用戶模式執(zhí)行時,只能執(zhí)行一般指令,而不允許執(zhí)行特權(quán)指令。這樣做可以保護(hù)核心代碼不受用戶程序有意和無意的攻擊。
顯然,處理機(jī)在運行期間需要在內(nèi)核模式和用戶模式之前進(jìn)行切換。
零拷貝
Kafka使用零拷貝(Zero-Copy)技術(shù)來提供它的性能,所謂的零拷貝是指將數(shù)據(jù)直接從磁盤文件復(fù)制到網(wǎng)卡設(shè)備中,而不需要經(jīng)由應(yīng)用程序之手,減少了內(nèi)核和用戶模式之間的上下文切換,零拷貝技術(shù)通過DMA技術(shù)實現(xiàn)。
直接存儲器存取方式(Direct Memory Access, DMA)
DMA控制方式是以存儲器為中心,在主存和I/O設(shè)備之間建立一條直接通路,在DMA控制器的控制下進(jìn)行設(shè)備和主存之間的數(shù)據(jù)交換。這種方式只在傳輸開始和傳輸結(jié)束時才需要CPU的干預(yù)。它非常適用于高速設(shè)備與主存之間的成批數(shù)據(jù)傳輸。
我們看下下面這樣的這樣一個場景:
客戶端在游覽器中發(fā)起請求獲取內(nèi)容,到看到具體內(nèi)容經(jīng)歷了什么?

首先,該請求經(jīng)過解析后,通過系統(tǒng)調(diào)用由用戶態(tài)轉(zhuǎn)為核心態(tài)執(zhí)行,在核心態(tài)由操作系統(tǒng)中的TCP/IP協(xié)議代碼和網(wǎng)卡驅(qū)動程序控制網(wǎng)卡把請求發(fā)送到相應(yīng)的網(wǎng)絡(luò)上,
等待Web服務(wù)器相應(yīng)。當(dāng)服務(wù)器返回時,由網(wǎng)卡接受,并通過內(nèi)核傳送給客戶程序。
在服務(wù)器端,內(nèi)核通過網(wǎng)卡從網(wǎng)絡(luò)上接受Web請求,并通過系統(tǒng)調(diào)用傳遞給Web服務(wù)器。Web服務(wù)器根據(jù)此服務(wù)請求執(zhí)行相應(yīng)的服務(wù)進(jìn)程,并由內(nèi)核把結(jié)果發(fā)送到網(wǎng)絡(luò)上傳送給用戶。
從上圖中可以看到如果服務(wù)器從準(zhǔn)備數(shù)據(jù)到發(fā)送數(shù)據(jù)經(jīng)歷了下面4個過程。
- 調(diào)用read()時,將文件中的內(nèi)容復(fù)制到內(nèi)核模式下的Read Buffer中
- CPU控制將內(nèi)核模式數(shù)據(jù)復(fù)制到用戶模式下
- 調(diào)用send()時,用用戶模式下的內(nèi)容復(fù)制到內(nèi)核模式下的Socket Buffer中。
- 將內(nèi)核模式下的Socket Buffer的數(shù)據(jù)復(fù)制到網(wǎng)卡設(shè)備中發(fā)送。
從上面過程可以看出,數(shù)據(jù)是先從內(nèi)核模式-->用戶模式-->內(nèi)核模式,浪費了2次復(fù)制過程:第一次是從內(nèi)核模式復(fù)制到用戶模式;第二次是從用戶模式再復(fù)制回內(nèi)核模式,而且在上面的過程中,內(nèi)核和用戶模式的上下文切換也是4次。
如果采用了零拷貝技術(shù),那么應(yīng)用程序就可以直接請求內(nèi)核把磁盤中的數(shù)據(jù)傳輸給Socket.
零拷貝技術(shù)通過DMA技術(shù)將文件內(nèi)容復(fù)制到內(nèi)核模式下的Read Buffer中。不過沒有數(shù)據(jù)被復(fù)制到Socket Buffer,只有包含數(shù)據(jù)的位置和長度的信息的文件描述符被加到Socket Buffer中。DMA引擎直接將數(shù)據(jù)從內(nèi)核模式中傳遞到網(wǎng)卡設(shè)備。這里上下文切換變成了2次,也只經(jīng)歷了2次復(fù)制過程就從磁盤中傳送出去了。