- CPU的兩種工作狀態:內核態和用戶態(或者稱管態和目態)
內核態
- 系統中既有操作系統的程序,也由普通用戶的程序。為了安全和穩定性操作系統的程序不能隨便訪問,這就是內核態
- 內核態可以使用所有的硬件資源
用戶態
- 不能直接使用系統資源,也不能改變CPU的工作狀態,并且只能訪問這個用戶程序自己的存儲空間
用戶態和內核態
特權級
- Linux使用了Ring3級別運行用戶態,Ring0標識內核態
- Ring0作為內核態,沒有使用Ring1和Ring2。
- Ring3狀態不能訪問Ring0的地址 空間,包括代碼和數據。
- Linux進程的4GB地址空間,3G-4G部分大家是共享的,是內核態的地址空間,這里存放在整個內核的代碼和所有的內核模塊, 以及內核所維護的數據。用戶運行一個程序,該程序所創建的進程開始是運行在用戶態的,如果要執行文件操作,網絡數據發送等操作,必須通過 write,send等系統調用,這些系統調用會調用內核中的代碼來完成操作,這時,必須切換到Ring0,然后進入3GB-4GB中的內核地址空間去執 行這些代碼完成操作,完成后,切換回Ring3,回到用戶態。這樣,用戶態的程序就不能隨意操作內核地址空間,具有一定的安全保護作用。
用戶態和內核態的轉換
Paste_Image.png
系統調用
- 這 是用戶態進程主動要求切換到內核態的一種方式,用戶態進程通過系統調用申請使 用操作系統提供的服務程序完成工作,比如linux中fork()實際上就是執行了一個創建新進程的系統調用。而系統調用的機制其核心還是使用了操作系統為用戶 特別開放的一個中斷來實現,例如Linux的int 80h中斷。
異常
- 當CPU在執行運行在用戶態下的程序時,發生了某些事先不可知的異常,這時會觸發由當前運行進程切換到處理此異常的內核相關程序中,也就轉到了內核態,比如缺頁異常。
外圍設備的中斷
- 當 外圍設備完成用戶請求的操作后,會向CPU發出相應的中斷信號,這時CPU會 暫停執行下一條即將要執行的指令轉而去執行與中斷信號對應的處理程序,如果先前執行的指令是用戶態下的程序,那么這個轉換的過程自然也就發生了由用戶態到 內核態的切換。比如硬盤讀寫操作完成,系統會切換到硬盤讀寫的中斷處理程序中執行后續操作等。
這3種方式是系統在運行時由用戶態轉到內核態的最主要方式,其中系統調用可以認為是用戶進程主動發起的,異常和外圍設備中斷則是被動的。
具體的切換操作
- 從 觸發方式上看,可以認為存在前述3種不同的類型,但是從最終實際完成由用戶態 到內核態的切換操作上來說,涉及的關鍵步驟是完全一致的,沒有任何區別,都相當于執行了一個中斷響應的過程,因為系統調用實際上最終是中斷機制實現的,而 異常和中斷的處理機制基本上也是一致的,關于它們的具體區別這里不再贅述。關于中斷處理機制的細節和步驟這里也不做過多分析,涉及到由用戶態切換到內核態 的步驟主要包括:
- 從當前進程的描述符中提取其內核棧的ss0及esp0信息。
- 使用ss0和esp0指向的內核棧將當前進程的cs,eip,eflags,ss,esp信息保存起來,這個過程也完成了由用戶棧到內核棧的切換過程,同時保存了被暫停執行的程序的下一條指令。
- 將先前由中斷向量檢索得到的中斷處理程序的cs,eip信息裝入相應的寄存器,開始執行中斷處理程序,這時就轉到了內核態的程序執行了。
來自于百度全科