Boot loader: Grub入門(轉)


Boot Loader: Grub

在看完了前面的整個啟動流程,以及核心模塊的整理之后,你應該會發現到一件事情, 那就是『 boot loader 是加載核心的重要工具』啊!沒有 boot loader 的話,那么 kernel 根本就沒有辦法被系統加載的呢!所以,底下我們會先談一談 boot loader 的功能, 然后再講一講現階段 Linux 里頭最主流的 grub 這個 boot loader 吧!

 

boot loader 的兩個 stage

我們在第一小節啟動流程的地方曾經講過,在 BIOS 讀完資訊后,接下來就是會到第一個啟動裝置的 MBR 去讀取 boot loader了。這個 boot loader 可以具有菜單功能、直接加載核心文件以及控制權移交的功能等, 系統必須要有 loader 才有辦法加載該操作系統的核心就是了。但是我們都知道, MBR 是整個硬盤的第一個 sector 內的一個區塊,充其量整個大小也才 446 bytes 而已。 我們的 loader 功能這么強,光是程序碼與配置數據不可能只占不到 446 bytes 的容量吧?那如何安裝?

為了解決這個問題,所以 Linux 將 boot loader 的程序碼運行與配置值加載分成兩個階段 (stage) 來運行:

  • Stage 1:運行 boot loader 主程序:
    第一階段為運行 boot loader 的主程序,這個主程序必須要被安裝在啟動區,亦即是 MBR 或者是 boot sector 。但如前所述,因為 MBR 實在太小了,所以,MBR 或 boot sector 通常僅安裝 boot loader 的最小主程序, 並沒有安裝 loader 的相關配置檔;

  • Stage 2:主程序加載配置檔:
    第二階段為透過 boot loader 加載所有配置檔與相關的環境參數文件 (包括文件系統定義與主要配置檔 menu.lst), 一般來說,配置檔都在 /boot 底下。

那么這些配置檔是放在哪里啊?這些與 grub 有關的文件都放置到 /boot/grub 中,那我們就來看看有哪些文件吧!

[root@www ~]# ls -l /boot/grub
-rw-r--r--  device.map              <==grub 的裝置對應檔(底下會談到)
-rw-r--r--  e2fs_stage1_5           <==ext2/ext3 文件系統之定義檔
-rw-r--r--  fat_stage1_5            <==FAT 文件系統之定義檔
-rw-r--r--  ffs_stage1_5            <==FFS 文件系統之定義檔
-rw-------  grub.conf               <==grub 在 Red Hat 的配置檔
-rw-r--r--  iso9660_stage1_5        <==光驅文件系統定義檔
-rw-r--r--  jfs_stage1_5            <==jfs 文件系統定義檔
lrwxrwxrwx  menu.lst -> ./grub.conf <==其實 menu.lst 才是配置檔!
-rw-r--r--  minix_stage1_5          <==minix 文件系統定義檔
-rw-r--r--  reiserfs_stage1_5       <==reiserfs 文件系統定義檔
-rw-r--r--  splash.xpm.gz           <==啟動時在 grub 底下的背景圖示
-rw-r--r--  stage1                  <==stage 1 的相關說明
-rw-r--r--  stage2                  <==stage 2 的相關說明
-rw-r--r--  ufs2_stage1_5           <==UFS 的文件系統定義檔
-rw-r--r--  vstafs_stage1_5         <==vstafs 文件系統定義檔
-rw-r--r--  xfs_stage1_5            <==xfs 文件系統定義檔

從上面的說明你可以知道 /boot/grub/ 目錄下最重要的就是配置檔 (menu.lst) 以及各種文件系統的定義! 我們的 loader 讀取了這種文件系統定義數據后,就能夠認識文件系統並讀取在該文件系統內的核心文件羅。 至於 grub 的配置檔檔名,其實應該是 menu.lst 的,只是在 Red Hat 里面被定義成為 /boot/grub.conf 而已。 鳥哥建議您還是記憶 menu.lst 比較好喔!

所以從上面的文件來看, grub 認識的文件系統真的非常多喔!正因為如此,所以 grub 才會取代 Lilo 這個老牌的 boot loader 嘛!好了,接下來就來瞧瞧配置檔內有啥配置值吧!

 

grub 的配置檔 /boot/grub/menu.lst 與菜單類型

grub 是目前使用最廣泛的 Linux 啟動管理程序,舊的 Lilo 這個啟動管理程序現在已經很少見了, 所以本章才會將 Lilo 的介紹舍棄的說。grub 的優點挺多的,包括有:

  • 認識與支持較多的文件系統,並且可以使用 grub 的主程序直接在文件系統中搜尋核心檔名;
  • 啟動的時候,可以『自行編輯與修改啟動配置項目』,類似 bash 的命令模式;
  • 可以動態搜尋配置檔,而不需要在修改配置檔后重新安裝 grub 。亦即是我們只要修改完 /boot/grub/menu.lst 里頭的配置后,下次啟動就生效了!

上面第三點其實就是 Stage 1, Stage 2 分別安裝在 MBR (主程序) 與文件系統當中 (配置檔與定義檔) 的原因啦! 好了,接下來,讓我們好好了解一下 grub 的配置檔: /boot/grub/menu.lst 這玩意兒吧! 要注意喔,那個 lst 是 LST 的小寫,不要搞錯羅!

 

硬盤與分割槽在 grub 中的代號

安裝在 MBR 的 grub 主程序,最重要的任務之一就是從磁碟當中加載核心文件, 以讓核心能夠順利的驅動整個系統的硬件。所以羅, grub 必須要認識硬盤才行啊!那么 grub 到底是如何認識硬盤的呢? 嘿嘿! grub 對硬盤的代號配置與傳統的 Linux 磁碟代號可完全是不同的!grub 對硬盤的識別使用的是如下的代號:

(hd0,0)

夠神了吧?跟 /dev/hda1 風馬牛不相干~怎么辦啊?其實只要注意幾個東西即可,那就是:

  • 硬盤代號以小括號 ( ) 包起來;
  • 硬盤以 hd 表示,后面會接一組數字;
  • 以『搜尋順序』做為硬盤的編號,而不是依照硬盤排線的排序!(這個重要!)
  • 第一個搜尋到的硬盤為 0 號,第二個為 1 號,以此類推;
  • 每顆硬盤的第一個 partition 代號為 0 ,依序類推。

所以說,第一顆『搜尋到的硬盤』代號為:『(hd0)』,而該顆硬盤的第一號分割槽為『(hd0,0)』,這樣說了解了吧? 反正你要記得,在 grub 里面,他開始的數字是 0 而不是 1 就是了!

 

在較舊的主板上面,通常第一顆硬盤會插在 IDE 1 的 master 上,就會是 /dev/hda,所以常常我們可能會誤會 /dev/hda 就是 (hd0),其實不是喔!要看你的 BIOS 配置值才行!有的主板 BIOS 可以調整啟動的硬盤搜尋順序,那么就要注意了,因為 grub 的硬盤代號可能會跟著改變吶!留意留意!

所以說,整個硬盤代號為:

硬盤搜尋順序 在 Grub 當中的代號
第一顆 (hd0) (hd0,0) (hd0,1) (hd0,4)....
第二顆 (hd1) (hd1,0) (hd1,1) (hd1,4)....
第三顆 (hd2) (hd2,0) (hd2,1) (hd2,4)....

這樣應該比較好看出來了吧?第一顆硬盤的 MBR 安裝處的硬盤代號就是『(hd0)』, 而第一顆硬盤的第一個分割槽的 boot sector 代號就是『(hd0,0)』第一顆硬盤的第一個邏輯分割槽的 boot sector 代號為『(hd0,4)』了了吧!

 

假設你的系統僅有一顆 SATA 硬盤,請說明該硬盤的第一個邏輯分割槽在 Linux 與 grub 當中的檔名與代號:

因為是 SATA 磁碟,加上使用邏輯分割槽,因此 Linux 當中的檔名為 /dev/sda5 才對 (1~4 保留給 primary 與 extended 使用)。 至於 grub 當中的磁碟代號則由於僅有一顆磁碟,因此代號會是『 (hd0,4) 』才對。

 

/boot/grub/menu.lst 配置檔

了解了 grub 當中最麻煩的硬盤代號后,接下來,我們就可以瞧一瞧配置檔的內容了。先看一下鳥哥的 CentOS 內的 /boot/grub/menu.lst 好了:

[root@www ~]# vim /boot/grub/menu.lst
default=0     <==默認啟動選項,使用第 1 個啟動菜單 (title)
timeout=5     <==若 5 秒內未動鍵盤,使用默認菜單啟動
splashimage=(hd0,0)/grub/splash.xpm.gz <==背景圖示所在的文件
hiddenmenu    <==讀秒期間是否顯示出完整的菜單畫面(默認隱藏)
title CentOS (2.6.18-92.el5)    <==第一個菜單的內容
        root (hd0,0)
        kernel /vmlinuz-2.6.18-92.el5 ro root=LABEL=/1 rhgb quiet
        initrd /initrd-2.6.18-92.el5.img

在 title 以前的四行,都是屬於 grub 的整體配置,包括默認的等待時間與默認的啟動項目, 還有顯示的畫面特性等等。至於 title 后面才是指定啟動的核心文件或者是 boot loader 控制權。 在整體配置方面的項目主要常見的有:

  • default=0
    這個必須要與 title 作為對照,在配置檔里面有幾個 title ,啟動的時候就會有幾個菜單可以選擇。 由於 grub 啟始號碼為 0 號,因此 default=0 代表使用『第一個 title 項目』來啟動的意思。 default 的意思是,如果在讀秒時間結束前都沒有動到鍵盤, grub 默認使用此 title 項目 (在此為 0 號) 來啟動。

  • timeout=5
    啟動時會進行讀秒,如果在 5 秒鍾內沒有按下任何按鍵,就會使用上面提到的 default 后面接的那個 title 項目來啟動的意思。如果你覺得 5 秒太短,那可以將這個數值調大 (例如 30 秒) 即可。此外,如果 timeout=0 代表直接使用 default 值進行啟動而不讀秒,timeout=-1 則代表直接進入菜單不讀秒了!

  • splashimage=(hd0,0)/grub/splash.xpm.gz
    有沒有發現你的 CentOS 在啟動的時候背景不是黑白而是有色彩變化的呢?那就是這個文件提供的背景圖示啦(注3)!不過這個文件的實際路徑寫法怎么會是這樣啊?很簡單啊~上述的意思是:在 (hd0,0) 這個分割槽內的最頂層目錄中,底下的 grub/splash.xpm.gz 那個文件的意思。 由於鳥哥將 /boot 這個目錄獨立成為 /dev/hda1 ,因此這邊就會寫成『在 /dev/hda1 里面的 grub/splash.xpm.gz 』的意思啦!想一想,如果你的 /boot 目錄並沒有獨立成為一個分割槽, 這里會寫成如何?

  • hiddenmenu
    這個說的是,啟動時是否要顯示菜單?目前 CentOS 默認是不要顯示菜單, 如果您想要顯示菜單,那就將這個配置值注解掉!

整體配置的地方大概是這樣,而底下那個 title 則是顯示啟動的配置項目。如同前一小節提到的,啟動時可以選擇 (1)直接指定核心文件啟動或 (2)將 boot loader 控制權轉移到下個 loader (此過程稱為 chain-loader)。每個 title 后面接的是『該啟動項目名稱的顯示』,亦即是在菜單出現時,菜單上面的名稱而已。 那么這兩種方式的配置有啥不同呢?

 

直接指定核心啟動

既然要指定核心啟動,所以當然要找到核心文件啦!此外,有可能還需要用到 initrd 的 RAM Disk 配置檔。但是如前說的, 尚未啟動完成,所以我們必須要以 grub 的硬盤識別方式找出完整的 kernel 與 initrd 檔名才行。 因此,我們可能需要有底下的方式來配置才行!

1. 先指定核心文件放置的 partition,再讀取文件 (目錄樹),
   最后才加入文件的實際檔名與路徑 (kernel 與 initrd);
   鳥哥的 /boot 為 /dev/hda1 ,因此核心文件的配置則成為:
root    (hd0,0)          <==代表核心文件放在那個 partition 當中
kernel  /vmlinuz-2.6.18-92.el5 ro root=LABEL=/1 rhgb quiet
initrd  /initrd-2.6.18-92.el5.img

上面的 root, kernel, initrd 后面接的參數的意義說明如下:

root :代表的是『核心文件放置的那個 partition 而不是根目錄』喔!不要搞錯了! 以鳥哥的案例來說,我的根目錄為 /dev/hda2 而 /boot 獨立為 /dev/hda1 ,因為與 /boot 有關, 所以磁碟代號就會成為 (hd0,0) 羅。

kernel :至於 kernel 后面接的則是核心的檔名,而在檔名后面接的則是核心的參數。 由於啟動過程中需要掛載根目錄,因此 kernel 后面接的那個 root=LABEL=/1 指的是『Linux 的根目錄在哪個 partition 』的意思。

這里使用 LABEL 來掛載根目錄。至於 rhgb 為色彩顯示而 quiet 則是安靜模式 (螢幕不會輸出核心偵測的資訊)。 

initrd :就是前面提到的 initrd 制作出 RAM Disk 的文件檔名啦!

2. 直接指定 partition 與檔名,不需要額外指定核心文件所在裝置代號
kernel  (hd0,0)/vmlinuz-2.6.18-92.el5 ro root=LABEL=/1 rhgb quiet
initrd  (hd0,0)/initrd-2.6.18-92.el5.img

老實說,鳥哥比較喜歡這種樣式的檔名寫法,因為這樣我們就能夠知道核心文件是在哪個裝置內的某個檔名, 而不會去想到我們的根目錄 (/, root) 啦!讓我們來想想 /boot 有獨立分割與無獨立分割的情況吧!

 

我的系統分割是: /dev/hda1 (/), /dev/hda2 (swap) 而已,且我的核心文件為 /boot/vmlinuz,請問 grub 的 menu.lst 內該如何撰寫核心文件位置?

我們使用疊代的方式來了解一下好了。由於核心檔名為 /boot/vmlinuz,轉成裝置檔名與代號會成為如下的過程:
原始文件:  /boot/vmlinuz ↓
Linux 裝置:(/dev/hda1)/boot/vmlinuz ↓
grub  裝置:(hd0,0)/boot/vmlinuz
所以最終的 kernel 寫法會變成:
kernel (hd0,0)/boot/vmlinuz root=/dev/hda1 ...

 

同上,只是我的分割情況變成: /dev/sda1 (/boot), /dev/sda5 (/) 時?

由於 /boot 被獨立出來了,所以情況會不一樣喔!如下所示:
原始文件:  /boot/vmlinuz ↓
Linux 裝置:(/dev/sda1)/vmlinuz ↓
grub  裝置:(hd0,0)/vmlinuz
所以最終的 kernel 寫法會變成:
kernel (hd0,0)/vmlinuz root=/dev/sda5 ...

 

利用 chain loader 的方式轉交控制權

所謂的 chain loader (啟動管理程序的鏈結) 僅是在將控制權交給下一個 boot loader 而已, 所以 grub 並不需要認識與找出 kernel 的檔名 ,『 他只是將 boot 的控制權交給下一個 boot sector 或 MBR 內的 boot loader 而已 』 所以通常他也不需要去查驗下一個 boot loader 的文件系統!

一般來說, chain loader 的配置只要兩個就夠了,一個是預計要前往的 boot sector 所在的分割槽代號, 另一個則是配置 chainloader 在那個分割槽的 boot sector (第一個磁區) 上!假設我的 Windows 分割槽在 /dev/hda1 ,且我又只有一顆硬盤,那么要 grub 將控制權交給 windows 的 loader 只要這樣就夠了:

[root@www ~]# vi /boot/grub/menu.lst
....前略....
title Windows partition
    root (hd0,0)    <==配置使用此分割槽
    chainloader +1  <== +1 可以想成第一個磁區,亦即是 boot sector

 

上面的范例中,我們可以很簡單的這樣想:那個 (hd0,0) 就是 Windows 的 C 槽所在磁碟, 而 chainloader +1 就是讓系統加載該分割槽當中的第一個磁區 (就是 boot sector) 內的啟動管理程序。 不過,由於 Windows 的啟動碟需要配置為活化 (active) 狀態,且我們的 grub 默認會去檢驗該分割槽的文件系統。 因此我們可以重新將上面的范例改寫成這樣:

[root@www ~]# vi /boot/grub/menu.lst
....前略....
title Windows partition
    rootnoverify (hd0,0)   <==不檢驗此分割槽
    chainloader +1
    makeactive             <==配置此分割槽為啟動碟(active)

grub 的功能還不止此,他還能夠隱藏某些分割槽。舉例來說,我的 /dev/hda5 是安裝 Linux 的分割槽, 我不想讓 Windows 能夠認識這個分割槽時,你可以這樣做:

[root@www ~]# vi /boot/grub/menu.lst
....前略....
title Windows partition
    hide (hd0,4)           <==隱藏 (hd0,4) 這個分割槽
    rootnoverify (hd0,0)
    chainloader +1
    makeactive

 

initrd 的重要性與創建新 initrd 文件

initrd 這玩意兒,他的目的在於提供啟動過程中所需要的最重要核心模塊,以讓系統啟動過程可以順利完成。 會需要 initrd 的原因,是因為核心模塊放置於 /lib/modules/$(uname -r)/kernel/ 當中, 這些模塊必須要根目錄 (/) 被掛載時才能夠被讀取。但是如果核心本身不具備磁碟的驅動程序時, 當然無法掛載根目錄,也就沒有辦法取得驅動程序,因此造成兩難的地步。

initrd 可以將 /lib/modules/.... 內的『啟動過程當中一定需要的模塊』包成一個文件 (檔名就是 initrd), 然后在啟動時透過主機的 INT 13 硬件功能將該文件讀出來解壓縮,並且 initrd 在內存內會模擬成為根目錄, 由於此虛擬文件系統 (Initial RAM Disk) 主要包含磁碟與文件系統的模塊,因此我們的核心最后就能夠認識實際的磁碟, 那就能夠進行實際根目錄的掛載啦!所以說:『initrd 內所包含的模塊大多是與啟動過程有關,而主要以文件系統及硬盤模塊 (如 usb, SCSI 等) 為主』的啦!

一般來說,需要 initrd 的時刻為:

  • 根目錄所在磁碟為 SATA、U盤 或 SCSI 等連接介面;
  • 根目錄所在文件系統為 LVM, RAID 等特殊格式;
  • 根目錄所在文件系統為非傳統 Linux 認識的文件系統時;
  • 其他必須要在核心加載時提供的模塊。

一般來說,各 distribution 提供的核心都會附上 initrd 文件,但如果你有特殊需要所以想重制 initrd 文件的話, 可以使用 mkinitrd 來處理的。這個文件的處理方式很簡單, man mkinitrd 就知道了! ^_^。 我們還是簡單的介紹一下去!

[root@www ~]# mkinitrd [-v] [--with=模塊名稱] initrd檔名 核心版本
選項與參數:
-v  :顯示 mkinitrd 的運行過程
--with=模塊名稱:模塊名稱指的是模塊的名字而已,不需要填寫檔名。舉例來說,
       目前核心版本的 ext3 文件系統模塊為底下的檔名:
       /lib/modules/$(uname -r)/kernel/fs/ext3/ext3.ko
       那你應該要寫成: --with=ext3 就好了 (省略 .ko)
initrd檔名:你所要創建的 initrd 檔名,盡量取有意義又好記的名字。
核心版本  :某一個核心的版本,如果是目前的核心則是『 $(uname -r) 』

范例一:以 mkinitrd 的默認功能創建一個 initrd 虛擬磁碟文件
[root@www ~]# mkinitrd -v initrd_$(uname -r) $(uname -r)
Creating initramfs
Looking for deps of module ehci-hcd
Looking for deps of module ohci-hcd
....(中間省略)....
Adding module ehci-hcd  <==最終加入 initrd 的就是底下的模塊
Adding module ohci-hcd
Adding module uhci-hcd
Adding module jbd
Adding module ext3
Adding module scsi_mod
Adding module sd_mod
Adding module libata
Adding module pata_sis

[root@www ~]# ll initrd_*
-rw------- 1 root root 2406443 Apr 30 02:55 initrd_2.6.18-92.el5
# 由於目前的核心版本可使用 uname -r 取得,因此鳥哥使用較簡單的命令來處理羅~
# 此時 initrd 會被創建起來,你可以將他移動到 /boot 等待使用。

范例二:添加 8139too 這個模塊的 initrd 文件
[root@www ~]# mkinitrd -v --with=8139too initrd_vbirdtest $(uname -r)
....(前面省略)....
Adding module mii
Adding module 8139too  <==看到沒!這樣就加入了!

initrd 創建完成之后,同時核心也處理完畢后,我們就可以使用 grub 來創建菜單了!底下繼續瞧一瞧吧!

 

測試與安裝 grub

如果你的 Linux 主機本來就是使用 grub 作為 loader 的話,那么你就不需要重新安裝 grub 了, 因為 grub 本來就會主動去讀取配置檔啊!您說是吧!但如果你的 Linux 原來使用的並非 grub , 那么就需要來安裝啦!如何安裝呢?首先,你必須要使用 grub-install 將一些必要的文件復制到 /boot/grub 里面去,你應該這樣做的:

[root@www ~]# grub-install [--root-directory=DIR] INSTALL_DEVICE
選項與參數:
--root-directory=DIR 那個 DIR 為實際的目錄,使用 grub-install 默認會將
  grub 所有的文件都復制到 /boot/grub/* ,如果想要復制到其他目錄與裝置去,
  就得要用這個參數。
INSTALL_DEVICE 安裝的裝置代號啦!

范例一:將 grub 安裝在目前系統的 MBR 底下,我的系統為 /dev/hda:
[root@www ~]# grub-install /dev/hda
# 因為原本 /dev/hda 就是使用 grub ,所以似乎不會出現什么特別的信息。
# 如果去查閱一下 /boot/grub 的內容,會發現所有的文件都升級了,因為我們重裝了!

范例二:我的 /home 為獨立的 /dev/hda3 ,如何安裝 grub 到 /dev/hda3 (boot sector)
[root@www ~]# grub-install --root-directory=/home /dev/hda3
Probing devices to guess BIOS drives. This may take a long time.
Installation finished. No error reported.
This is the contents of the device map /home/boot/grub/device.map.
Check if this is correct or not. If any of the lines is incorrect,
fix it and re-run the script `grub-install'.

(fd0)   /dev/fd0
(hd0)   /dev/hda   <==會給予裝置代號的對應表!

[root@www ~]# ll /home/boot/grub/
-rw-r--r-- 1 root root     30 Apr 30 11:12 device.map
-rw-r--r-- 1 root root   7584 Apr 30 11:12 e2fs_stage1_5
....(底下省略)....
# 看!文件都安裝進來了!但是注意到,我們並沒有配置檔喔!那要自己創建!

所以說, grub-install 是安裝 grub 相關的文件 (例如文件系統定義檔) 到你的裝置上面去等待在啟動時被讀取,但還需要配置好配置檔 (menu.lst) 后,再以 grub shell 來安裝 grub 主程序到 MBR 或者是 boot sector 上面去喔!好了,那我們來思考一下想要安裝的數據。

我預計啟動時要直接顯示菜單,且菜單倒數為 30 秒。另外,在原本的 menu.lst 當中新增三個啟動菜單,分別如下說明:
  1. 假設 /dev/hda1 內含有 boot loader ,此 loader 如何取得控制權?
  2. 如何重新讀取 MBR 內的 loader ?
  3. 利用你原本的系統核心文件,創建一個可強制進入單人維護模式的菜單

第一點很簡單,就利用上一小節的說明來處理即可。至於第二點,MBR 的讀取讀的是整顆硬盤的第一個磁區, 因此 root (hd0) 才是對的。第三點則與核心的后續參數有關。整個文件可以被改寫成這樣:

[root@www ~]# vim /boot/grub/menu.lst
default=0
timeout=30
splashimage=(hd0,0)/grub/splash.xpm.gz
#hiddenmenu
title CentOS (2.6.18-92.el5)
        root (hd0,0)
        kernel /vmlinuz-2.6.18-92.el5 ro root=LABEL=/1 rhgb quiet
        initrd /initrd-2.6.18-92.el5.img
title /dev/hda1 boot sector  <==本例中的第一個新增菜單
        root (hd0,0)
        chainloader +1
title MBR loader             <==新增的第二個菜單
        root (hd0)           <==MBR 為整顆磁碟的第一個磁區,所以用整顆磁碟的代號
        chainloader +1
title single user mode       <==新增的第三個菜單(其實由原本的title復制來的)
        root (hd0,0)
        kernel /vmlinuz-2.6.18-92.el5 ro root=LABEL=/1 rhgb quiet single
        initrd /initrd-2.6.18-92.el5.img

下次啟動時,你就會發現有四個菜單可以選擇,而默認會以第一個菜單來啟動喔!

我們已經將配置檔處理完畢,但是你要知道的是,我們並不知道 /dev/hda1 到底有沒有包含 grub 的主程序, 因此我們想要將 grub 主程序再次的安裝到 /dev/hda1 的 boot sector ,也想要重新安裝 grub 到 MBR 上面去。 此時我們就得要使用 grub shell 羅!整個安裝與 grub shell 的動作其實很簡單, 如果您有興趣研究的話,可以使用 info grub 去查閱~鳥哥這里僅介紹幾個有用的命令而已。

  • 用『 root (hdx,x) 』選擇含有 grub 目錄的那個 partition 代號;
  • 用『 find /boot/grub/stage1 』看看能否找到安裝資訊文件;
  • 用『 find /boot/vmlinuz 』看看能否找到 kernel file (不一定要成功!);
  • 用『 setup (hdx,x) 』或『 setup (hdx) 』將 grub 安裝在 boot sector 或 MBR;
  • 用『 quit 』來離開 grub shell !

由於我們最需要安裝的就是那個 stage1 啦!那才是 grub 的主程序嘛!而且配置檔通常與主程序擺在同一個目錄下。 因此我們需要使用 root (hd0,0) 去找到 /boot/grub/stage1 喔!接下來,請用 grub 來進入 grub shell 吧!進入 grub 后,會出現一個『 grub> 』的提示字節啊!

[root@www ~]# grub

# 1. 先配置一下含有 grub 目錄的那個 partition 啊!
grub> root (hd0,0)
 Filesystem type is ext2fs, partition type 0x83
# 鳥哥主機的分割中,/boot/grub 在 /boot 的分割槽,亦即是 /dev/hda1 內喔!
# 另外, grub 也能夠分辨出該分割槽的文件系統 (ext2)。

# 2. 搜尋一下,是否存在 stage1 這個資訊文件?
grub> find /boot/grub/stage1
 (hd0,2)
# 見鬼!怎么會只有一個!我們明明有 /boot/grub 與 /home/boot/grub 啊!
# 因為 /boot 是獨立的,因此要找到該檔名就得要用如下的方式:

grub> find /grub/stage1
 (hd0,0)
# 這樣就能夠找到羅!要特別注意 grub 找到不是目錄樹,而是裝置內的文件。

# 3. 搜尋一下是否可以找到核心? /boot/vmlinuz-2.6.18-92.el5 ?
grub> find /boot/vmlinuz-2.6.18-92.el5
Error 15: File not found
grub> find /vmlinuz-2.6.18-92.el5
 (hd0,0)
# 再次強調,因為 /boot/ 是獨立的,因此就會變成上頭的模樣羅!

# 4. 將主程序安裝上去吧!安裝到 MBR 看看!
grub> setup (hd0)
 Checking if "/boot/grub/stage1" exists... no <==因為 /boot 是獨立的
 Checking if "/grub/stage1" exists... yes     <==所以這個檔名才是對的!
 Checking if "/grub/stage2" exists... yes
 Checking if "/grub/e2fs_stage1_5" exists... yes
 Running "embed /grub/e2fs_stage1_5 (hd0)"...  15 sectors are embedded.
succeeded
 Running "install /grub/stage1 (hd0) (hd0)1+15 p (hd0,0)/grub/stage2 
/grub/grub.conf"... succeeded  <==將 stage1 程序安裝妥當羅!
Done.
# 很好!確實有裝起來~這樣 grub 就在 MBR 當中了!

# 5. 那么重復安裝到我的 /dev/hda1 呢?亦即是 boot sector 當中?
grub> setup (hd0,0)
 Checking if "/boot/grub/stage1" exists... no
 Checking if "/grub/stage1" exists... yes
 Checking if "/grub/stage2" exists... yes
 Checking if "/grub/e2fs_stage1_5" exists... yes
 Running "embed /grub/e2fs_stage1_5 (hd0,0)"... failed (this is not fatal)
 Running "embed /grub/e2fs_stage1_5 (hd0,0)"... failed (this is not fatal)
 Running "install /grub/stage1 (hd0,0) /grub/stage2 p /grub/grub.conf "... 
succeeded
Done.
# 雖然無法將 stage1_5 安裝到 boot sector 去,不過,還不會有問題,
# 重點是最后面那個 stage1 要安裝后,顯示 succeeded 字樣就可以了!

grub> quit

如此一來,就已經將 grub 安裝到 MBR 及 /dev/hda1 的 boot sector 里面去了! 而且讀取的是 (hd0,0) 里面的 /grub/menu.lst 那個文件喔!真是很重要啊!重要到不行!

最后總結一下:

  1. 如果是從其他 boot loader 轉成 grub 時,得先使用 grub-install 安裝 grub 配置檔;
  2. 開始編輯 menu.lst 這個重要的配置檔;
  3. 透過 grub 來將主程序安裝到系統中,如 MBR 的 (hd0) 或 boot sector 的 (hd0,0) 等等。

 

啟動前的額外功能修改

事實上,上一個小節配置好之后,你的 grub 就已經在你的 Linux 系統上面了,而且同時存在於 MBR 與 boot sector 當中呢!所以,我們已經可以重新啟動來查閱看看啦! 另外,如果你正在進行啟動,那么請注意,我們可以在默認菜單 (鳥哥的范例當中是 30 秒) 按下任意鍵, 還可以進行 grub 的『線上編修』功能喔!真是棒啊!先來看看啟動畫面吧!

 

由於鳥哥將隱藏菜單的功能取消了,因此你會直接看到這四個菜單,同時會有讀秒的咚咚在倒數。 菜單部分的畫面其實就是 title 后面的文字啦!你現在知道如何修改 title 后面的文字了吧! ^_^。 如果你使用上下鍵去選擇第二 (/dev/hda1 boot sector) 或第三 (MBR loader) 時,會發現同樣的畫面重復出現! 這是因為那兩個是 loader 移交而已嘛!而我們都使用相同的 grub 與相同的 menu.lst 配置檔! 因此這個畫面就會重復出現了!這樣了解乎?

另外,如果你再仔細看的話,會發現到上圖中底部還有一些細部的選項,似乎有個 'e' edit 的樣子! 沒錯~ grub 支持線上編修命令喔!這是個很有用的功能!假如剛剛你將 menu.lst 的內容寫錯了,導致出現無法啟動的問題時, 我們可以查閱該 title 菜單的內容並加以修改喔!舉例來說,我想要知道第一個菜單的實際內容時,將反白光棒移動到第一個菜單, 再按下 'e' 會進入如下畫面:

 

哈哈!這不就是我們在 menu.lst 里面配置的東西嗎?沒錯!此時你還可以繼續進一步修改喔! 注意看到上圖最底下的說明,你還可以使用:

  • e:進入 grub shell 的編輯畫面;
  • o:在光標所在行底下再新增一行;
  • d:將光標所在行刪除。

我們說過, grub 是可以直接使用核心文件來啟動的,所以,如果您很清楚的知道你的根目錄 (/) 在那個 partition ,而且知道你的核心文件檔名 (通常都會有個 /boot/vmlinuz 連結到正確的檔名), 那么直接在圖三的畫面當中,以上述的 o, d, e 三個按鍵來編修,成為類似底下這樣:

 

按下 [Enter] 按鍵后,然后輸入 b 來 boot ,就可以啟動啦!所以說,萬一你的 /boot/grub/menu.lst 配置錯誤,或者是因為安裝的緣故,或者是因為核心文件的緣故,導致無法順利啟動時,記得啊,可以在 grub 的菜單部分, 使用 grub shell 的方式去查詢 (find) 或者是直接指定核心文件,就能夠啟動啦! ^_^

另外,很多時候我們的 grub 可能會發生錯誤,導致『連 grub 都無法啟動』,那么根本就無法使用 grub 的線上編修功能嘛!怎么辦?沒關系啊!我們可以利用具有 grub 啟動的 CD 來啟動, 然后再以 CD 的 grub 的線上編修,嘿嘿!同樣可以使用硬盤上面的核心文件來啟動啦!很好玩吧! ^_^

 

轉自 http://vbird.dic.ksu.edu.tw/linux_basic/0510osloader_3.php


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM