在讀Leetcode OS篇有一問題問到
what happens in the background from the time you press the Power button until the Linux login prompt appears?
簡單的說,就是從按下開機鍵到Login 畫面出現時,中間做了哪些事?
我們以Linux OS為例解析其中複雜的過程:
下面這張圖可以清楚標示開機的每一步驟
當按下開機鍵後,電腦硬體會主動的讀取 [註1]BIOS 或 UEFI BIOS 來載入硬體資訊(包含啟動螢幕、DRAM、以及鍵盤滑鼠等)及進行硬體系統的自我測試,這步驟稱為POST (Power On Self Test) ,若在硬體檢測中出現錯誤的話,則會卡在開機畫面,並在畫面中顯示哪項硬體驗證錯誤資訊,稱為beep codes。
之後[註2]BIOS將電腦控制權轉交給作業系統,作業系統將會主動的去硬碟中讀取可開機的磁區(Master Boot Record, MBR),MBR通常存在於硬碟的第一個磁區中,約為512Bytes大小。MBR的結構如下圖所示
MBR 是整個硬碟的第一個 sector 內的一個區塊,充其量整個大小也才 512 bytes 而已。即使是 採用[註3]GPT也沒有很大的磁區來儲存 loader 的資料。bootloader 功能這麼強,光是程式碼與設定資料不可能只佔這麼一點點的容量吧?那如何安裝?
為了解決這個問題,所以 Linux 將 bootloader 的程式碼執行與設定值載入分成兩個階段 (two-stage) 來執行:
- Stage 1:執行 boot loader 主程式:
第一階段為執行 bootloader 的主程式,這個主程式必須要被安裝在開機區,亦即是 MBR 或者是 boot sector 。但如前所述,因為 MBR 實在太小了,所以,MBR 或 boot sector 通常僅安裝 bootloader 的最小主程式, 並沒有安裝 bootloader 的相關設定檔; - Stage 2:主程式載入設定檔:
第二階段為透過 bootloader 載入所有設定檔與相關的環境參數檔案 (包括檔案系統定義與主要設定檔 grub.cfg), 一般來說,設定檔都在 /boot 底下。
MBR將開機管理程式(bootloader)載入記憶體中,[註4]開機管理程式可以讓使用者選擇要啟動哪一個作業系統,並會負責將使用者選擇的作業系統kernel與initial RAM disk載入記憶體中,最後將電腦控制權轉交給kernel。
bootloader 可以載入 kernel 與 initramfs ,然後在記憶體中讓 initramfs 解壓縮成為根目錄, kernel 就能夠藉此載入適當的驅動程式,最終釋放虛擬檔案系統,並掛載實際的根目錄檔案系統,就能夠開始後續的正常開機流程。
kernel在載入記憶體前都是被壓縮過(compressed)的,bootloader會負責解壓縮kernel後再載入進RAM中,接著kernel會檢查所有系統硬體,並啟動所有built-in在kernel中的device driver。
Linux 被載入記憶體後會以自己的功能重新偵測一次硬體,而不一定會使用 BIOS 偵測到的硬體資訊!也就是說,kernel此時才真正的開始工作。
initramfs被載入記憶體後有個很重要的工作是負責檢查並掛載(mount) root filesystem,initramfs同時也會載入file system中一些kernel的重要程式或binary files,以及掛載[註5] udev (User Device)起來。
initramfs成功mount root filesystem後就會從記憶體中功成身退(移除),並且將電腦控制權轉交給/sbin/init (PID為1)系統內的第一支程式。
/sbin/init會啟動系統中其他user space 中的processes與daemons,所以init也被稱為 “manager of last resort”。在init啟動的眾多process中有關於使用者登入的process為getty。
Getty負責生出login process負責使用者的帳號密碼確認,一旦登入成功就會跳出command line shell,通常linux中常用的shell包含bash、tcsh、ksh…等
最後,使用者成功登入以後,若系統有安裝X-windows桌面環境,則會進入到linux桌面,其中桌面環境的設定與管理由Display Manager進行統一管理。
總結,系統開機牽扯到非常多的名詞與工具,非一言兩語就可以說完。
我盡量補充相關的名詞解釋與介紹,更詳細的說明可以查看 鳥哥的Linux私房菜。
註 1:BIOS 通常以軟體形式存放於主機板中的ROM chip上
註 2:在此過程中,系統會讀取CMOS values來延續上次關機時的日期與時間。
註 3:在安裝系統時常常會遇到MBR與GPT兩種格式上的問題,這兩種格式的差異可參考分區MBR和GPT的區別,以及我們到底選哪一種好
註 4 : 在linux上最常用的bootloader為Grub2。
註 5 : udev負責控制系統中有哪些device driver,並且正確地載入與定位device driver。 有關更多udev的介紹可以參考 Debain官方介紹的udev 與 udev維基百科