星期四, 二月 01, 2007

引导器GNU GRUB简析

GNU GRUB是我见到的最灵活的、功能最强大的、加载速度最快的、最精炼的引导器。(除了GRUB,我还用过NT loader, OS/2 loader, DOS MBR loader, PQ BOOT, System Commander, Lilo等引导器)。因此,GRUB成为现在各大Linux发布版的主流引导器。

一、安装GRUB的四大要素

想玩转GRUB,必须理解GRUB的组成部分和其大概的功能、实现的思路。如下,是我的GRUB目录的文件:

menulst
stage1
stage2
e2fs_stage1_5
fat_stage1_5
ffs_stage1_5
jfs_stage1_5
minix_stage1_5
reiserfs_stage1_5
vstafs_stage1_5
xfs_stage1_5


如果你下载一个grub,编译后装上,那么产生的就是这些文件和一个从linux环境进入grub环境的程序grub,但是不包括menulst(也可能有个例子文件menulst.conf,记不清了)。这些文件是通用的,copy到别的机器上也能用,这就是一大灵活之处。

stage1是用来装入到MBR或者primary disk的super block的,它应该是16位环境引导模块;stage1引导完成后,就切换到32位保护模式,把stage2从磁盘读到内存,然后把控制权交给stage2执行。stage2会读取menulst,从而确定如何引导Linux。menulst文件中详细写明了引导菜单和内核的位置,这个纯文本文件是需要手工配置的。其余的那些文件,如e2fs_stage1_5那些,偶不说你也明白,是对应于各种类型文件系统的驱动程序,在stage1从磁盘读取stage2时会加载它先。

下面是偶得menulst,我用了最简捷的语法:

#-----------------------------------------

default 1
timeout 3

#-------------------------------
#-- Slackware Linux 10 kernel 2.4.26
title Slackware Linux 10 kernel 2.4.26
kernel (hd0,4)/boot/vmlinuz ro root=/dev/hda5
boot

#-----------------------------------------


default 指定默认引导的系统,对应序号是引导菜单的条目序号,从1开始计数。timeout 指定引导菜单延迟等待的时间,如果timeout为0你就看不到引导菜单了。title指定引导菜单上显示的文字,kernel指定引导内核和root设备的位置。这里要注意,(hd0,4)是grub指定文件设备的语法,跟Linux通用的/dev/hda5表示法类似,只不过它的数字是从0开始计数的,而/dev/hda5这种表示法是从1开始计数的。(hd0)指向/dev/hda, (hd1)指向/dev/hdb,(hd0,1)指向/dev/hda2,(hd2,6)指向/dev/hdc7,以此类推......

要注意,根设备前要加上ro,指定为只读挂载,不然后患无穷。

还有一点一定要注意,(hd0,4)/boot/vmlinuz中(hd0,4)指的是你的内核vmlinuz所在的设备根路径,和root设备未必相同(比方说我把vmlinuz放在(hd0,0)上,但是我的linux root确在(hd0,4)上),切记切记。有时候,你会看到grub中用root (hd0,0) 这里的root指的不是你的linux的root所在的设备路径,而指的是在grub中的 / 所对应的设备路径,如:
kernel (hd0,4)/boot/vmlinuz ro root=/dev/hda5
等同于:
root (hd0,4)
kernel /boot/vmlinuz ro root=/dev/hda5
这点要仔细理解。

二、灵活自如的安装方法

至少有2种方法来安装grub,1>在Linux中把grub安装包装上,会同时装一个从Linux中进入grub环境的工具grub,这样你就可以执行grub进入grub环境,然后再执行安装指令;2>从grub引导盘(很多D盘都有提供,还有那种光盘的Linux修复环境也有提供)进入grub,执行安装指令。

安装指令很简单,就1行命令:
install <要安装到那个引导位置> p

如我的,就是:
grub>install (hd0,0)/grub/stage1 (hd0) (hd0,0)/boot/grub/stage2 p (hd0,0)/grub/menulst

这里要说明一点,有很多人分不清/boot是什么意思,以至于老是在任何环境下都这么写(hd0,0)/boot/grub/stage1。这是不对的。Linux下的几乎所有目录都是可以挂载的,例如我把/boot挂载到了/dev/hda1上,这样,我写(hd0,0)/grub/stage1就相当于/boot/grub/stage1,这点一定要弄清楚!在举一个例子,如果我把/home挂载到/dev/hda7上,那么(hd0,6)/smileonce指向的就是/home/smileonce。

三、grub引导环境的使用技巧

有一些tip可能你花了很上时间才学到,比如我当初就想像不出在输入grub命令的时候,按tab键居然有提示,比如install (hd0,然后我按tab,那么会提示一堆设备列表的清单。在系统启动的时候,按c可以进入grub命令环境,按e可以编辑当前菜单条目的命令,按b重新执行boot等等。这些需要看一些grub的文档才能彻底掌握。

四、发烧级技巧

有很多人问:XX版本的Linux只有ISO能不能从硬盘安装?其实现在发行的版本(老版本可能不支持),都支持从硬盘安装,并且连ISO都不需要解压缩开。

实现原理说穿不值一钱:利用ISO一个叫做boot目录中提供的boot盘引导用的压缩内核,用grub挂载引导这个内核,而Linux安装程序又支持从ISO中寻找目录。注意,如果安装盘有几张,ISO应该除序号外名字都一致(默认你下载的光盘镜像都是这样的),这样安装程序才会自动换盘;否则就需要手动切换控制台,然后手动mount,就麻烦了。

举个例子如下:

title From HD
root (hd0,6)
kernel /isolinux/kernel devfs=nomount vga=normal load_ramdisk=1 prompt_ramdisk=0 ramdisk_size=22000 root=/dev/ram0 rw
initrd /isolinux/rescue.gz

(hd0,6)是ISO文件所在的设备位置(改成你的实际位置),把ISO放在该分区根目录。那个kernel和rescue.gz文件在你Linux安装盘的第一张盘的boot目录里面有,自己找一下,不同版本Linux可能名字不同。