我正在使用 CentOS 7,并已将多个磁盘连接到它。我知道我的操作系统、内核、initramfs 等位于“/dev/sda”,并且这是可启动磁盘。但是 grub2 如何推断出这一点?它会逐个检查所有连接的磁盘吗?
答案1
从技术上讲:Linux 找不到任何可启动磁盘,因为在 Linux 运行时,引导加载程序已经完成了其工作 - 即:
- 将 Linux 从文件复制到 RAM 中的某个地方
- 将 initramfs 从文件复制到 RAM 中的某个位置
- 在某些架构上,比如 ARM,将设备树或架构描述符等其他内容复制到 RAM 的某个位置
- 将控制权传递给 RAM 中复制 Linux 的第一个位置,现在引导加载程序不再处于活动状态。
现代 UEFI 固件以及非 x86 平台上的固件(如 U-Boot)都会在固件中存储“启动项” - 启动项包含存储设备和文件名,固件将按顺序运行并加载/运行它找到的第一个文件。您可以通过进入 UEFI 设置并进行更改来更改顺序,或者使用操作系统中的实用程序来更改 UEFI NVRAM 设置。
现在 x86 上的 UEFI 会将单个二进制文件加载到 RAM 中,但通常 Linux 至少需要一个 initramfs 才能启动(尽管这不是 Linux 的严格要求)。
另外,从历史上看,x86 具有更原始的固件(BIOS),它只是从存储设备中加载第一个扇区(顺序由 BIOS 设置决定),甚至不尝试查找/加载文件。
因此,在大多数 Linux 系统上,UEFI 实际加载的东西(即遵循启动顺序/搜索可启动设备的东西)是 GRUB - 它是 Linux(以及其他操作系统,如果需要)的通用引导加载程序平台,它实际上会执行很多预启动工作。应该存在于固件中,但由于各种原因并未实现,并且还为您提供了在加载操作系统之前执行操作的环境。
安装 Linux 时,安装程序将通过生成 GRUB 可以访问的配置文件来配置 GRUB,并将在 GRUB 的菜单中添加条目,告诉 GRUB 去哪里加载内核和 initramfs。多个条目是可能的,甚至是常见的 - 例如,Debian 将为救援内核安装第二个菜单项 - 大致相当于 Windows 安全模式。但这些都是由安装程序在安装 Linux 时设置的,并且您将在 UEFI 完成其工作后访问这些选项。
(顺便说一句,我喜欢 U-Boot 的一点是它可以直接加载内核和 initramfs,所以根本不需要 GRUB。但那是一个具有可定制固件的 ARM 设备)。
Windows 有自己的“GRUB”,winload.exe
它可以完成 Windows 需要的工作,还可以选择性地提供启动前的菜单选项,而固件也无法提供这些选项。您可以使用bcdedit
它来更改菜单选项。Vista 之前的 Windows 版本使用 NTLDR,可以使用 C:\boot.ini 文件 IIRC 进行配置。
Linux 不需要 GRUB - 长期以来,人们使用一种名为 LILO(Linux Loader)的更简单的引导加载程序,并且一些发行版可能仍在使用它。