冯冬艳
(山西职业技术学院,山西 太原 030006)
Linux操作系统诞生于1991年10月,是一套免费使用和自由传播的类Unix操作系统。其具有免费、开源、安全、稳定、高效等优点,因此在商用领域使用非常普遍。目前Linux操作系统的内核由林纳斯·托瓦兹及其团队维护,众多的应用程序则由GNU组织来维护。为了方便用户使用,很多第三方的个人、组织或商业机构对Linux内核、应用程序等编译后制作成Linux不同的发行版。当前社会上存在着众多的Linux发行版,主流的有RedHat、CentOS、Suse、Debian、Ubuntu、Arch Linux等,本文将以CentOS 6为例。大多数发行版的Linux系统在启动时都需要用到GRUB,GRUB是一个在Linux操作系统上使用比较广泛的系统引导程序。其主要有支持大硬盘、支持开机画面、支持传递参数、提供交互式接口、提供菜单保护机制等特点。本文重点分析了Linux操作系统的启动流程,并对GRUB可能出现故障的情况进行了分析、总结、归纳,并对每一种故障情况进行了还原,最后进行了修复。
1) 加电自检(POST,Power On Self Test)。计算机在按下开机键后,首先进行的是加电自检,它是BIOS的一个基本功能,主要完成对CPU、主板、内存、串并口、显示器、磁盘、键盘等硬件设备的检测。一般此过程检测到的故障都是致命的,会导致系统启动挂起,因此会通过不同的蜂鸣声对用户发出警报。此过程检测无故障则进入下一步。
2) 加载引导程序。加电自检成功完成后,BIOS将根据用户所指定的引导次序(Boot Sequence),按照顺序依次在相应的存储介质上寻找主引导记录(MBR,Master Boot Record)。在找到的第一个具有可用主引导记录的存储介质上读取出引导加载器(Boot Loader)、磁盘分区表(DPT,Disk Partition Table)、分区有效性标志(55AA),共512个字节。此过程顺利完成后,Linux内核被加载至内存。
3) 系统的初始化。Linux内核文件都是以压缩格式存放的,在上一步骤成功完成后,Linux内核被加载至内存中,内核文件首先完成自解压,并在ramdisk文件的帮助下,内核拥有了访问磁盘及文件系统等基本设备的驱动程序。随后内核在完成探测可识别的硬件设备并加载相应驱动,以只读方式加载根文件系统等操作后,内核就可以启动位于磁盘上的第一个应用程序init,进而完成系统的初始化。
在Linux启动流程的第二步中需要进行加载引导程序,MBR的前446个字节是用于存放Boot Loader的。Linux上常见的引导加载器有LILO、Syslinux、GRUB等。
1) LILO(LInux LOader)。LILO是一个轻量、稳定的Linux引导加载器,由于其比较古老、不提供交互式命令行界面、不支持将系统安装在1024柱面以后的存储空间等原因,2015年12月开始LILO的开发已经停止。但目前Android系统广泛使用,LILO由于其小巧、稳定,依然具有此类设备上较高的使用率。
2) Syslinux。Syslinux是一种能从光盘驱动器、网络等进行引导的轻型引导加载器。Syslinux 支持诸如微软的 FAT, Linux 上的 ext2、ext3、ext4 等文件系统。Syslinux 也支持未压缩的单一设备上的 Btrfs。但由于 Syslinux 仅能访问自己分区上的文件,因此不具备多重文件系统引导能力。
3) GRUB(GRand Unified Bootloader)。GRUB是众多Linux发行版普遍使用的多操作系统引导加载器,并且可以向内核传递启动参数,从而实现不同的启动效果。GRUB可以分为GRUB Legacy和GRUB 2,本文以GRUB Legacy为例。GRUB Legacy与LILO最大的区别就是其突破了Boot Loader只有446字节的限制,其可以将Boot Loader存放于文件系统的某一路径下。具体过程如下:GRUB Legacy将引导过程分为了两个阶段。第一个阶段为stage1,位于MBR中,其主要功能就是找到位于磁盘上的stage2。第二个阶段为stage2,其位于文件系统/boot/grub下。但在stage1结束后,此时的内核无法识别文件系统,严格的来说,应该还包含其中一个过度阶段,称之为stage1_5。在此阶段,内核将装载对应文件系统的驱动程序,使得在stage2,内核可以找到位于文件系统上/boot/grub/stage2文件,进而完成引导加载过程。
1) 故障描述。MBR的前446个字节以内的数据被损坏,未重启时不会有明显的故障现象,但万一重启计算机将无法启动系统。
2) 故障分析。MBR位于整个磁盘的0磁道0柱面1扇区。MBR由446个字节的Boot Loader, 64个字节为磁盘分区表,2个字节的分区有效性标志组成,共512个字节。由于分区表被损坏需要用其他工具查找恢复,本文暂不讨论磁盘分区表被损坏的情况。此类故障本质上来说是GRUB的stage1损坏。虽然GRUB已经被损坏,但是由于操作系统未重启,暂时用不到GRUB,因此此时修复GRUB只需要重新安装MBR内的Boot Loader即GRUB的stage1即可。
3) 故障还原。使用dd if=/dev/zero of=/dev/sda1 bs=446 count=1命令模拟MBR的前446个以内字节被损坏。
4) 故障修复。此时的修复只需重新安装GRUB即可,有两种常用的修复方法,其中第一种方法为:使用grub-install --root-directory=/ /dev/sda命令重新安装GRUB的stage1。需要注意的是此处—root-directory应指向boot目录的父目录,而/dev/sda为MBR所存放的设备。第二种方法为:键入grub命令,出现grub命令提示符;使用root (hd0,0)命令指定根所在位置;使用setup (hd0)命令安装MBR。需要注意的是(hd0,0)为固定格式指明根所在位置为第一块磁盘的第一个分区,读者需要注意,这个设置可能会因人而异。setup (hd0)指明要在那一块磁盘上安装MBR。最后使用reboot命令重启系统,故障修复。
1) 故障描述。接上题故障,MBR前446个字节以内的数据被损坏,但已重启,此时将无法进行任何引导,系统启动将挂起。
2) 故障分析。MBR中的前446个字节被损坏,即Boot Loader被损坏,其本质就是GRUB中的stage1被损坏,因此无法引导加载系统。此时需要使用系统的安装光盘,在开始界面中选择紧急救援模式,再进行一系列处理,恢复被损坏的MBR中的Boot Loader即可。
3) 故障还原。先使用dd if=/dev/zero of=/dev/sda1 bs=446 count=1命令模拟MBR的前446个以内字节被损坏。然后使用reboot命令重启系统。
4) 故障修复。此时装入系统安装光盘;重启;在弹出的界面中选择紧急救援模式(Rescue installed system);在语言选择菜单中选择英文(English);在键盘类型菜单中选择美国(US);在启动网络菜单上选择不启动(No);在救援菜单上选择继续(Continue);在shell菜单上选择启动shell(Start shell);使用chroot /mnt/sysimage/命令切换根至系统提示的根文件系统挂载位置;使用grub-install --root-directory=/ /dev/sda命令重新安装GRUB的stage1;使用exit命令退出当前所在的根;最后使用reboot命令重启系统,故障修复。
1) 故障描述。GRUB的配置文件的格式损坏、内容缺失或文件丢失,系统启动时,将只会显示“grub>”的提示符, 无法完成进一步的系统启动过程。
2) 故障分析。GRUB的配置文件位于/boot/grub/grub.conf,而/etc/grub.conf是此文件的软链接。此文件中的内容有着固定的格式,常用的配置项有default、timeout、hiddenmenu、splashimage、title、password等,其中title可以多个,在每个title项下有二级项root、kernel、initrd、password等。其中default指明默认启动哪个title所代表的系统或内核;timeout指明用户选择的超时时间;title为某一个系统或内核用于显示和选择的标识;root指明此内核所在的磁盘及分区位置;kernel指明此系统或内核的内核文件位置,可以传递参数;initrd指明此系统或内核启动时所需要使用的ramdisk文件。
3) 故障还原。使用rm-rf /boot/grub/grub.conf命令将grub的配置文件删除;使用reboot命令重启电脑。
4) 故障修复。电脑启动后出现grub命令提示符,在grub提示符下输入root (hd0,0)后回车;在grub提示符下输入kernel /vmlinuz-2.6.32-696.el6.x86_64后回车;在grub提示符下输入initrd /initramfs-2.6.32-696.el6.x86_64.img后回车;在grub提示符下输入reboot命令,重启系统,故障修复。需要注意的是root用于指明根所在位置为第一块磁盘的第一个分区,kernel用于指明内核文件所在位置,initrd用于指明ramdisk文件所在位置。kernel有时需要附加一些内核参数,本处不予详述,有兴趣的读者可参考相关文章。此外,在使用root (hd0,0)后在指定kernel和initrd时可以灵活地使用路径补全的Tab键。最后使用reboot命令重启系统,故障修复。
本文详细介绍了Linux操作系统的启动流程,并对GRUB启动过程中的两个阶段的作用及GRUB配置文件格式进行了介绍。最后总结归纳了Linux系统启动过程中与GRUB损坏有关的各类故障,并进行了故障还原和修复。读者可以根据遇到的启动故障特征分析采用对应的故障修复方法,以实现快速排除故障,减少因为故障而引起的损失。