Translated most of the grub2official manual, and then sorted it out myself. Because the content is a bit complicated, the arrangement of chapters may not be very reasonable, so please understand.
Directory of this article:
##1.1 Basic content
1.2 Install grub2
##1.3 grub2 configuration file
1.4 Commands in the command line and menu items
1.5 Several common built-in variables
1.6 grub configuration and installation examples
1.7 Brief description of traditional grub
This article mainly introduces grub2. At the end of the article, traditional grub is briefly described, but the content of grub2 contains a lot of comparisons between grub2 and traditional grub.
If you just want to know the role of boot.img/core.img/diskboot.img/kernel.img in grub2 or the stage1/stage1_5/stage2 file in traditional grub, please directly Jump to related content to read.
1.1 Basic content
Only explain a few main ones:
1. The name of the configuration file has changed. In grub, the configuration file is grub.conf or menu.lst (a soft link to grub.conf), and is renamed grub.cfg in grub2.2.grub2 adds a lot of syntax, which is closer to a scripting language, such as supporting variables, conditional judgments, and loops.
3. In grub2, the device name starts from 1, but in grub it starts from 0.4.grub2 uses img files and no longer uses stage1, stage1.5 and stage2 in grub.
5. Supports the graphical interface to configure grub, but you need to install the grub-customizer package, which is provided by the epel source.
6. When the operating system environment has been entered, the grub command is no longer provided, that is, the grub interactive interface cannot be entered. It can only be entered when the computer is booted, which is a big shortcoming.
7. There is no useful find command in grub2, which is another major shortcoming.
1.1.2 Naming habits and file path representation
(fd0) :表示第一块软盘 (hd0,msdos2) :表示第一块硬盘的第二个mbr分区。grub2中分区从1开始编号,传统的grub是从0开始编号的 (hd0,msdos5) :表示第一块硬盘的第一个逻辑分区 (hd0,gpt1) :表示第一块硬盘的第一个gpt分区/boot/vmlinuz :相对路径,基于根目录,表示根目录下的boot目录下的vmlinuz, :如果设置了根目录变量root为(hd0,msdos1),则表示(hd0,msdos1)/boot/vmlinuz (hd0,msdos1)/boot/vmlinuz:绝对路径,表示第一硬盘第一分区的boot目录下的vmlinuz文件
grub2 supports two ways to boot the operating system:
1.1.4 File distribution after installation of grub2 program and traditional grub program
[root@xuexi ~]# ls /usr/share/grub/x86_64-redhat/e2fs_stage1_5 ffs_stage1_5 jfs_stage1_5 reiserfs_stage1_5 stage2 ufs2_stage1_5 xfs_stage1_5 fat_stage1_5 iso9660_stage1_5 minix_stage1_5 stage1 stage2_eltorito vstafs_stage1_5
[root@server7 ~]# ls /usr/lib/grub/i386-pc/*.mod | wc -l257[root@server7 ~]# ls -lh /usr/lib/grub/i386-pc/*.lst -rw-r--r--. 1 root root 3.7K Nov 24 2015 /usr/lib/grub/i386-pc/command.lst -rw-r--r--. 1 root root 936 Nov 24 2015 /usr/lib/grub/i386-pc/crypto.lst -rw-r--r--. 1 root root 214 Nov 24 2015 /usr/lib/grub/i386-pc/fs.lst -rw-r--r--. 1 root root 5.1K Nov 24 2015 /usr/lib/grub/i386-pc/moddep.lst -rw-r--r--. 1 root root 111 Nov 24 2015 /usr/lib/grub/i386-pc/partmap.lst -rw-r--r--. 1 root root 17 Nov 24 2015 /usr/lib/grub/i386-pc/parttool.lst -rw-r--r--. 1 root root 202 Nov 24 2015 /usr/lib/grub/i386-pc/terminal.lst -rw-r--r--. 1 root root 33 Nov 24 2015 /usr/lib/grub/i386-pc/video.lst[root@server7 ~]# ls -lh /usr/lib/grub/i386-pc/*.img-rw-r--r--. 1 root root 512 Nov 24 2015 /usr/lib/grub/i386-pc/boot_hybrid.img -rw-r--r--. 1 root root 512 Nov 24 2015 /usr/lib/grub/i386-pc/boot.img -rw-r--r--. 1 root root 2.0K Nov 24 2015 /usr/lib/grub/i386-pc/cdboot.img -rw-r--r--. 1 root root 512 Nov 24 2015 /usr/lib/grub/i386-pc/diskboot.img -rw-r--r--. 1 root root 28K Nov 24 2015 /usr/lib/grub/i386-pc/kernel.img -rw-r--r--. 1 root root 1.0K Nov 24 2015 /usr/lib/grub/i386-pc/lnxboot.img -rw-r--r--. 1 root root 2.9K Nov 24 2015 /usr/lib/grub/i386-pc/lzma_decompress.img -rw-r--r--. 1 root root 1.0K Nov 24 2015 /usr/lib/grub/i386-pc/pxeboot.img
当使用grub来管理启动菜单时,那么boot loader都是grub程序安装的。
传统的grub将stage1转换后的内容安装到MBR(VBR或EBR)中的boot loader部分,将stage1_5转换后的内容安装在紧跟在MBR后的扇区中,将stage2转换后的内容安装在/boot分区中。
grub2将boot.img转换后的内容安装到MBR(VBR或EBR)中的boot loader部分,将diskboot.img和kernel.img结合成为core.img,同时还会嵌入一些模块或加载模块的代码到core.img中,然后将core.img转换后的内容安装到磁盘的指定位置处。
它们之间更具体的关系见下文。
官方手册原文:
严格地说是core.img的安装位置,因为boot.img的位置是固定在MBR或VBR或EBR上的。
(1).MBR
MBR格式的分区表用于PC BIOS平台,这种格式允许四个主分区和额外的逻辑分区。使用这种格式的分区表,有两种方式安装GURB:
嵌入到MBR和第一个分区中间的空间,这部分就是大众所称的"boot track","MBR gap"或"embedding area",它们大致需要31kB的空间;
将core.img安装到某个文件系统中,然后使用分区的第一个扇区(严格地说不是第一个扇区,而是第一个block)存储启动它的代码。
这两种方法有不同的问题。
使用嵌入的方式安装grub,就没有保留的空闲空间来保证安全性,例如有些专门的软件就是使用这段空间来实现许可限制的;另外分区的时候,虽然会在MBR和第一个分区中间留下空闲空间,但可能留下的空间会比这更小。
方法二安装grub到文件系统,但这样的grub是脆弱的。例如,文件系统的某些特性需要做尾部包装,甚至某些fsck检测,它们可能会移动这些block。
GRUB开发团队建议将GRUB嵌入到MBR和第一个分区之间,除非有特殊需求,但仍必须要保证第一个分区至少是从第31kB(第63个扇区)之后才开始创建的。
现在的磁盘设备,一般都会有分区边界对齐的性能优化提醒,所以第一个分区可能会自动从第1MB处开始创建。
(2).GPT
一些新的系统使用GUID分区表(GPT)格式,这种格式是EFI固件所指定的一部分。但如果操作系统支持的话,GPT也可以用于BIOS平台(即MBR风格结合GPT格式的磁盘),使用这种格式,需要使用独立的BIOS boot分区来保存GRUB,GRUB被嵌入到此分区,不会有任何风险。
当在gpt磁盘上创建一个BIOS boot分区时,需要保证两件事:(1)它最小是31kB大小,但一般都会为此分区划分1MB的空间用于可扩展性;(2)必须要有合理的分区类型标识(flag type)。
例如使用gun parted工具时,可以设置为bios_grub标识:
# parted /dev/sda toggle partition_num bios_grub # parted /dev/sda set partiton_num bios_grub on
如果使用gdisk分区工具时,则分类类型设置为"EF02"。
如果使用其他的分区工具,可能需要指定guid,则可以指定其guid为"21686148-6449-6e6f-744e656564454649"。
下图是某个bios/gpt格式的bios boot分区信息,从中可见,它大小为1M,没有文件系统,分区表示为bios_grub。
下图为gpt磁盘在图形界面下安装操作系统时创建的Bios boot分区。
在传统的grub上,可以直接在bash下敲入grub命令进入命令交互模式,但grub2只能在系统启动前进入grub交互命令行。
按下e见可以编辑所选菜单对应的grub菜单配置项,按下c键可以进入grub命令行交互模式。
官方手册原文:
这里的安装指的不是安装grub程序,而是安装Boot loader,但一般都称之为安装grub,且后文都是这个意思。
安装方式非常简单,只需调用grub2-install,然后给定安装到的设备名即可。
shell> grub2-install /dev/sda
这样的安装方式,默认会将img文件放入到/boot目录下,如果想自定义放置位置,则使用--boot-directory选项指定,可用于测试练习grub的时候使用,但在真实的grub环境下不建议做任何改动。
shell> grub2-install --boot-director=/mnt/boot /dev/fd0
如果是EFI固件平台,则必须挂载好efi系统分区,一般会挂在/boot/efi下,这是默认的,此时可直接使用grub2-install安装。
shell> grub2-install
如果不是挂载在/boot/efi下,则使用--efi-directory指定efi系统分区路径。
shell> grub2-install --efi-directory=/mnt/efi
grub2-install is actually a shell script used to call other tools. The real functions are completed by other tools, so if you are very familiar with grub's internal commands and mechanisms, you don't need grub2-install at all.
The corresponding traditional grub installation command is grub-install, and its usage is the same as grub2-install.
Official manual original text:
The img file is generated by grub2, and the stage file is generated by traditional grub. Below are descriptions of the various files.
grub2 generates several img files, some are distributed in the /usr/lib/grub/i386-pc directory, and some are distributed in /boot/ In the grub2/i386-pc directory, I believe you will understand the relationship between them after reading the following.
The following figure describes the relationship between various img files. Among them, core.img is dynamically generated, and the path is /boot/grub2/i386-pc/core.img, while other img exists in the /usr/lib/grub/i386-pc directory. Of course, when installing grub, boot.img will be copied to the /boot/grub2/i386-pc directory.
(1)boot.img
Under the BIOS platform, boot.img is the first img file started by grub, and it is written to In the MBR or the boot sector of the partition, because the size of the boot sector is 512 bytes, the size of the img file is also 512 bytes.
The only function of boot.img is to read the first sector belonging to core.img and jump to it, giving control to the img of that sector. Due to size limitations, boot.img cannot understand the structure of the file system, so grub2-install will hard-code the location of core.img into boot.img, so that the location of core.img can be found.
(2)core.img
core.img is dynamically created by the grub2-mkimage program based on diskboot.img, kernel.img and a series of modules. There are enough functional modules embedded in core.img to ensure that grub can access /boot/grub, and relevant modules can be loaded to implement related functions, such as loading the boot menu, loading information about the target operating system, etc. Since grub2 is used extensively The dynamic function module makes the size of core.img small enough.
core.img contains the contents of multiple img files, including diskboot.img/kernel.img, etc.
The installation location of core.img varies with MBR disks and GPT disks, which has been explained above.
(3)diskboot.img
If the boot device is a hard disk, that is, when booting from the hard disk, the content of the first sector in core.img is diskboot.img. The function of diskboo.img is to read the remaining parts of core.img into memory and transfer control to kernel.img. Since the file system is not recognized at this time, all locations of core.img are listed in the block list. Encoded in such a way that diskboot.img can find the remaining content.
Because the img file occupies one sector, the size is 512 bytes.
(4)cdboot.img
If the boot device is an optical drive (cd-rom), that is, when booting from the optical drive, the content of the first sector in core.img is cdboo .img. Its function is the same as diskboot.img.
(5)pexboot.img
If booted from the PXE environment of the network, the content of the first sector in core.img is pxeboot.img.
(6)kernel.img
The kernel.img file contains the basic runtime environment of grub: device framework, file handle, environment variables, command line parser in rescue mode, etc. . It is rarely used directly because they are fully embedded in core.img. Note that kernel.img is grub's kernel and has nothing to do with the operating system's kernel.
If you are careful, you will find that kernel.img itself takes up 28KB of space, but after being embedded into core.img, the core.img file is only 26KB in size. This is because kernel.img in core.img is compressed.
(7)lnxboot.img
The img file is placed at the front of core.img, making grub like the Linux kernel, so that core.img can be used by LILO's "image ="identify. Of course, this is used in conjunction with LILO, but who still uses LILO now?
(8)*.mod
Various functional modules, some of which have been embedded in core.img, or will be automatically loaded by grub, but sometimes it is also necessary to use the insmod command to load them manually.
grub2的设计方式和传统grub大不相同,因此和stage之间的对比关系其实没那么标准,但是将它们拿来比较也有助于理解img和stage文件的作用。
stage文件也分布在两个地方:/usr/share/grub/RELEASE目录下和/boot/grub目录下,/boot/grub目录下的stage文件是安装grub时从/usr/share/grub/RELEASE目录下拷贝过来的。
(1)stage1
stage1文件在功能上等价于boot.img文件。目的是跳转到stage1_5或stage2的第一个扇区上。
(2)*_stage1_5
*stage1_5文件包含了各种识别文件系统的代码,使得grub可以从文件系统中读取体积更大功能更复杂的stage2文件。从这一方面考虑,它类似于core.img中加载对应文件系统模块的代码部分,但是core.img的功能远比stage1_5多。
stage1_5一般安装在MBR后、第一个分区前的那段空闲空间中,也就是MBR gap空间,它的作用是跳转到stage2的第一个扇区。
其实传统的grub在某些环境下是可以不用stage1_5文件就能正常运行的,但是grub2则不能缺少core.img。
(3)stage2
stage2的作用是加载各种环境和加载内核,在grub2中没有完全与之相对应的img文件,但是core.img中包含了stage2的所有功能。
当跳转到stage2的第一个扇区后,该扇区的代码负责加载stage2剩余的内容。
注意,stage2是存放在磁盘上的,并没有像core.img一样嵌入到磁盘上。
(4)stage2_eltorito
功能上等价于grub2中的core.img中的cdboot.img部分。一般在制作救援模式的grub时才会使用到cd-rom相关文件。
(5)pxegrub
功能上等价于grub2中的core.img中的pxeboot.img部分。
安装grub2的过程大体分两步:一是根据/usr/lib/grub/i386-pc/目录下的文件生成core.img,并拷贝boot.img和core.img涉及的某些模块文件到/boot/grub2/i386-pc/目录下;二是根据/boot/grub2/i386-pc目录下的文件向磁盘上写boot loader。
当然,到底是先拷贝,还是先写boot loader,没必要去搞清楚,只要/boot/grub2/i386-pc下的img文件一定能通过grub2相关程序再次生成boot loader。所以,既可以认为/boot/grub2/i386-pc目录下的img文件是boot loader的特殊备份文件,也可以认为是boot loader的源文件。
不过,img文件和boot loader的内容是不一致的,因为img文件还要通过grub2相关程序来转换才是真正的boot loader。
对于传统的grub而言,拷贝的不是img文件,而是stage文件。
以下是安装传统grub时,grub做的工作。很不幸,grub2上没有该命令,也没有与之等价的命令。
grub> setup (hd0) Checking if "/boot/grub/stage1" exists... yes Checking if "/boot/grub/stage2" exists... yes Checking if "/boot/grub/e2fs_stage1_5" exists... yes Running "embed /boot/grub/e2fs_stage1_5 (hd0)"... 15 sectors are embedded. succeeded Running "install /boot/grub/stage1 (hd0) (hd0)1+15 p (hd0,0)/boot/grub/stage2 /boot/grub/menu.lst"... succeeded Done.
首先检测各stage文件是否存在于/boot/grub目录下,随后嵌入stage1_5到磁盘上,该文件系统类型的stage1_5占用了15个扇区,最后安装stage1,并告知stage1 stage1_5的位置是第1到第15个扇区,之所以先嵌入stage1_5再嵌入stage1就是为了让stage1知道stage1_5的位置,最后还告知了stage1 stage2和配置文件menu.lst的路径。
grub2的默认配置文件为/boot/grub2/grub.cfg,该配置文件的写法弹性非常大,但绝大多数需要修改该配置文件时,都只需修改其中一小部分内容就可以达成目标。
grub2-mkconfig程序可用来生成符合绝大多数情况的grub.cfg文件,默认它会自动尝试探测有效的操作系统内核,并生成对应的操作系统菜单项。使用方法非常简单,只需一个选项"-o"指定输出文件即可。
shell> grub2-mkconfig -o /boot/grub2/grub.cfg
官方手册原文:
grub2-mkconfig是根据/etc/default/grub文件来创建配置文件的。该文件中定义的是grub的全局宏,修改内置的宏可以快速生成grub配置文件。实际上在/etc/grub.d/目录下还有一些grub配置脚本,这些shell脚本读取一些脚本配置文件(如/etc/default/grub),根据指定的逻辑生成grub配置文件。若有兴趣,不放读一读/etc/grub.d/10_linux文件,它指导了创建grub.cfg的细节,例如如何生成启动菜单。
[root@xuexi ~]# ls /etc/grub.d/00_header 00_tuned 01_users 10_linux 20_linux_xen 20_ppc_terminfo 30_os-prober 40_custom 41_custom README
在/etc/default/grub中,使用"key=vaule"的格式,key全部为大小字母,如果vaule部分包含了空格或其他特殊字符,则需要使用引号包围。
例如,下面是一个/etc/default/grub文件的示例:
[root@xuexi ~]# cat /etc/default/grubGRUB_TIMEOUT=5GRUB_DISTRIBUTOR="$(sed 's, release .*$,,g' /etc/system-release)"GRUB_DEFAULT=saved GRUB_DISABLE_SUBMENU=trueGRUB_TERMINAL_OUTPUT="console"GRUB_CMDLINE_LINUX="crashkernel=auto biosdevname=0 net.ifnames=0 rhgb quiet"GRUB_DISABLE_RECOVERY="true"
虽然可用的宏较多,但可能用的上的就几个:GRUB_DEFAULT、GRUB_TIMEOUT、GRUB_CMDLINE_LINUX和GRUB_CMDLINE_LINUX_DEFAULT。
以下列出了部分key。
(1).GRUB_DEFAULT
默认的菜单项,默认值为0。其值可为数值N,表示从0开始计算的第N项是默认菜单,也可以指定对应的title表示该项为默认的菜单项。使用数值比较好,因为使用的title可能包含了容易改变的设备名。例如有如下菜单项:
menuentry 'Example GNU/Linux distribution' --class gnu-linux --id example-gnu-linux { ... }Copy after login
如果想将此菜单设为默认菜单,则可设置"GRUB_DEFAULT=example-gnu-linux"。
如果GRUB_DEFAULT的值设置为"saved",则表示默认的菜单项是"GRUB_SAVEDEFAULT"或"grub-set-default"所指定的菜单项。
(2).GRUB_SAVEDEFAULT
默认该key的值未设置。如果该key的值设置为true时,如果选定了某菜单项,则该菜单项将被认为是新的默认菜单项。该key只有在设置了"GRUB_DEFAULT=saved"时才有效。
不建议使用该key,因为GRUB_DEFAULT配合grub-set-default更方便。
(3).GRUB_TIMEOUT
在开机选择菜单项的超时时间,超过该时间将使用默认的菜单项来引导对应的操作系统。默认值为5秒。等待过程中,按下任意按键都可以中断等待。
设置为0时,将不列出菜单直接使用默认的菜单项引导与之对应的操作系统,设置为"-1"时将永久等待选择。
是否显示菜单,和"GRUB_TIMEOUT_STYLE"的设置有关。
(4).GRUB_TIMEOUT_STYLE
如果该key未设置值或者设置的值为"menu",则列出启动菜单项,并等待"GRUB_TIMEOUT"指定的超时时间。
如果设置为"countdown"和"hidden",则不显示启动菜单项,而是直接等待"GRUB_TIMEOUT"指定的超时时间,如果超时了则启动默认菜单项并引导对应的操作系统。在等待过程中,按下"ESC"键可以列出启动菜单。设置为countdown和hidden的区别是countdown会显示超时时间的剩余时间,而hidden则完全隐藏超时时间。
(5).GRUB_DISTRIBUTOR
设置发行版的标识名称,一般该名称用来作为菜单的一部分,以便区分不同的操作系统。
(6).GRUB_CMDLINE_LINUX
添加到菜单中的内核启动参数。例如:
GRUB_CMDLINE_LINUX="crashkernel=ro root=/dev/sda3 biosdevname=0 net.ifnames=0 rhgb quiet"
(7).GRUB_CMDLINE_LINUX_DEFAULT
除非"GRUB_DISABLE_RECOVERY"设置为"true",否则该key指定的默认内核启动参数将生成两份,一份是用于默认启动参数,一份用于恢复模式(recovery mode)的启动参数。
该key生成的默认内核启动参数将添加在"GRUB_CMDLINE_LINUX"所指定的启动参数之后。
(8).GRUB_DISABLE_RECOVERY
该项设置为true时,将不会生成恢复模式的菜单项。
(9).GRUB_DISABLE_LINUX_UUID
默认情况下,grub2-mkconfig在生产菜单项的时候将使用uuid来标识Linux 内核的根文件系统,即"root=UUID=..."。
例如,下面是/boot/grub2/grub.cfg中某菜单项的部分内容。
menuentry 'CentOS Linux (3.10.0-327.el7.x86_64) 7 (Core)' --class centos --class gnu-linux --class gnu --class os --unrestricted $menuentry_id_option 'gnulinux-3.10.0-327.el7.x86_64-advanced-b2a70faf-aea4-4d8e-8be8-c7109ac9c8b8' {
......
linux16 /vmlinuz-3.10.0-327.el7.x86_64 root=UUID=b2a70faf-aea4-4d8e-8be8-c7109ac9c8b8 ro crashkernel=auto biosdevname=0 net.ifnames=0 quiet LANG=en_US.UTF-8
initrd16 /initramfs-3.10.0-327.el7.x86_64.img
}
虽然使用UUID的方式更可靠,但有时候不太方便,所以可以设置该key为true来禁用。
(10).GRUB_BACKGROUND
Set the background image. The background image must be readable by grub. The image file name suffix must be ".png", ".tga", ".jpg", ".jpeg". When needed, grub will press Scale down the size of the image to fit the screen.
(11).GRUB_THEME
Set the theme of grub menu.
(12).GRUB_GFXPAYLOAD_LINUX
When set to "text", Linux will be forced to start in text mode. In some cases, graphics mode may not be supported.
(13).GRUB_DISABLE_OS_PROBER
By default, grub2-mkconfig will try to use the os-prober program (if it is already installed, it should be installed by default) to detect other available operating system kernels , and generate corresponding startup menu items for it. Set to "true" to disable automatic detection.
(14).GRUB_DISABLE_SUBMENU
By default, if grub2-mkconfig finds multiple kernels of the same version or a lower version, it will only generate a top-level menu for the highest version of the kernel. All other lower-version kernel menus are placed into submenus, and setting them to "y" will generate them all as top-level menus.
(15).GRUB_HIDDEN_TIMEOUT (obsolete, but still valid for backward compatibility)
Use "GRUB_TIMEOUT_STYLE={countdown|hidden}" to replace this item
( 16).GRUB_HIDDEN_TIMEOUT_QUIET (obsolete, but still valid for backward compatibility)
Used with GRUB_HIDDEN_TIMEOUT, you can use GRUB_TIMEOUT_STYLE=countdown to replace these two items.
Official manual original text:
Comment symbol: Characters starting with # are considered comments, so grub supports in-line comments
Not all keywords are useful, they are only provided in advance for future function expansion.
该命令定义了一个名为title的grub菜单项。当开机时选中该菜单项时,grub会将chosen环境变量的值赋给"--id"(如果给定了"--id"的话),执行大括号中的命令列表,如果直到最后一个命令都全部执行成功,且成功加载了对应的内核后,将执行boot命令。随后grub就将控制权交给了操作系统内核。
--class:该选项用于将菜单分组,从而使得grub可以通过主题样式为不同组的菜单显示不同的样式风格。一个menuentry中,可以使用多次class表示将该菜单分到多个组中去。
--users:该选项限定只有此处列出的用户才能访问该菜单项,不指定该选项时将表示所有用户都能访问该菜单。
--unrestricted:该选项表示所有用户都有权访问该菜单项。
--hotkey:该选项为该菜单项关联一个热键,也就是快捷键,关联热键后只要按下该键就会选中该菜单。热键只能是字母键、backspace键、tab键或del键。
--id:该选项为该菜单关联一个唯一的数值。id的值可以由ASCII字母、数字//下划线组成,且不得以数字开头。
所有其他的参数包括title都被当作位置参数传递给大括号中的命令,但title总是$1,除title外的其余参数,位置值从前向后类推。
break [n]:强制退出for/while/until循环
continue [n]:跳到下一次迭代,即进入下一次循环
return [n]:指定返回状态码
setparams [arg] …:从$1开始替换位置参数
shift [n]:踢掉前n个参数,使得第n+1个参数变为$1,但和shell中不一样的是,踢掉了前n个参数后,从$#-n+1到$#这些参数的位置不变
具体如何编写grub.cfg文件,继续看下文的命令和变量。
官方手册原文:
grub2支持很多命令,有些命令只能在交互式命令行下使用,有些命令可用在配置文件中。在救援模式下,只有insmod、ls、set和unset命令可用。
无需掌握所有的命令,掌握用的上的几个命令即可。
help [pattern]
显示能匹配到pattern的所有命令的说明信息和usage信息,如果不指定patttern,将显示所有命令的简短信息。
例如"help cmos"。
用于启动已加载的操作系统。
只在交互式命令行下可用。其实在menuentry命令的结尾就隐含了boot命令。
set [envvar=value] unset envvar
前者设置环境变量envvar的值,如果不给定参数,则列出当前环境变量。
后者释放环境变量envvar。
分别用于列出已加载的模块和调用指定的模块。
注意,若要导入支持ext文件系统的模块时,只需导入ext2.mod即可,实际上也没有ext3和ext4对应的模块。
linux file [kernel_args] linux16 file [kernel_args]
都表示装载指定的内核文件,并传递内核启动参数。linux16表示以传统的16位启动协议启动内核,linux表示以32位启动协议启动内核,但linux命令比linux16有一些限制。但绝大多数时候,它们是可以通用的。
在linux或linux16命令之后,必须紧跟着使用init或init16命令装载init ramdisk文件。
一般为/boot分区下的vmlinuz-RELEASE_NUM文件。
但在grub环境下,boot分区被当作root分区,即根分区,假如boot分区为第一块磁盘的第一个分区,则应该写成:
linux (hd0,msdos1)/vmlinuz-XXX
或者相对路径的:
set root='hd0,msdos1'
linux /vmlinuz-XXX
在grub阶段可以传递内核的启动参数(内核的参数包括3类:编译内核时参数,启动时参数和运行时参数),可以传递的启动参数非常非常多,完整的启动参数列表见:。这里只列出几个常用的:
init= :指定Linux启动的第一个进程init的替代程序。 root= :指定根文件系统所在分区,在grub中,该选项必须给定。 ro,rw :启动时,根分区以只读还是可读写方式挂载。不指定时默认为ro。 initrd :指定init ramdisk的路径。在grub中因为使用了initrd或initrd16命令,所以不需要指定该启动参数。 rhgb :以图形界面方式启动系统。 quiet :以文本方式启动系统,且禁止输出大多数的log message。 net.ifnames=0:用于CentOS 7,禁止网络设备使用一致性命名方式。 biosdevname=0:用于CentOS 7,也是禁止网络设备采用一致性命名方式。 :只有net.ifnames和biosdevname同时设置为0时,才能完全禁止一致性命名,得到eth0-N的设备名。
例如:
linux16 /vmlinuz-3.10.0-327.el7.x86_64 root=UUID=edb1bf15-9590-4195-aa11-6dac45c7f6f3 ro rhgb quiet LANG=en_US.UTF-8
另外,root启动参数有多种定义方式,可以使用UUID的方式指定,也可以直接指定根文件系统所在分区,如"root=/dev/sda2",
initrd file
只能紧跟在linux或linux16命令之后使用,用于为即将启动的内核传递init ramdisk路径。
同样,基于根分区,可以使用绝对路径,也可以使用相对路径。路径的表示方法和linux或linux16命令相同。例如:
linux16 /vmlinuz-0-rescue-d13bce5e247540a5b5886f2bf8aabb35 root=UUID=b2a70faf-aea4-4d8e-8be8-c7109ac9c8b8 ro crashkernel=auto quiet
initrd16 /initramfs-0-rescue-d13bce5e247540a5b5886f2bf8aabb35.img
search [--file|--label|--fs-uuid] [--set [var]] [--no-floppy] [--hint args] name
Search for devices by file [--file], volume label [--label], and file system UUID [--fs-uuid].
If the "--set" option is used, the first found device will be set to the value of the environment variable "var". The default variable "var" is 'root'.
When searching, you can use the "--no-floppy" option to disable searching for floppy disks, because floppy disks are very slow and have been eliminated.
Sometimes "--hint=XXX" is also specified, which means that devices that meet the prompt conditions are given priority. If multiple hint conditions are specified, the first hint is matched first, and then the second one is matched. And so on.
For example:
if [ x$feature_platform_search_hint = xy ]; then
search --no-floppy --fs-uuid --set=root - -hint-bios=hd0,msdos1 --hint-efi=hd0,msdos1 --hint-baremetal=ahci0,msdos1 --hint='hd0,msdos1' 367d6a77-033b-4037-bbcb-416705ead095
else
search --no-floppy --fs-uuid --set=root 367d6a77-033b-4037-bbcb-416705ead095
fi
linux16 /vmlinuz-3.10 .0-327.el7.x86_64 root=UUID=b2a70faf-aea4-4d8e-8be8-c7109ac9c8b8 ro crashkernel=auto quiet LANG=en_US.UTF-8
initrd16 /initramfs-3.10.0-327.el7 .x86_64.img
The first search in the above if statement searches for the device with uuid "367d6a77-033b-4037-bbcb-416705ead095", but multiple hint options are used, indicating that first Matches devices with the /boot partition (hd0, msdos1) under the bios platform, and then specifies several hints. However, because the search uses the uuid search method, these hint options are redundant, because the uuid of the partition on a single disk is only.
For another example, if there are two boot partitions on a boot device (such as when multiple systems coexist), they are (hd0, msdos1) and (hd0, msdos5). If uuid search is not used at this time , instead use label mode to search:
search --no-floppy --fs-label=boot --set=root --hint=hd0,msdos5
Then the boot partition (hd0, msdos5) will be selected at this time. If hint is not used, the boot partition (hd0, msdos1) will be selected.
Return true or false Boolean value directly.
Calculate whether the result of "expression" is true, return 0 if true, otherwise return non-0, mainly used for if, while or until in the structure.
string1 == string2 | string1 is the same as string2 | |
string1 != string2 | string1 and string2 are not the same Same | |
string1 < string2 | string1 in letters Sequentially less than string2 | |
string1 <= string2 | string1 is alphabetical less than or equal to string2 | |
##string1 > string2 | string1 is alphabetically greater than string2 | |
##string1 >= string2
| string1 is alphabetical greater than or equal to string2 | |
integer1 is greater than or equal to integer2 | ||
integer1 is greater than integer2 | ##integer1 -le integer2 | |
integer1 is less than or equal to integer2 | ##integer1 -lt integer2 | |
integer1 is less than integer2 | ##integer1 -ne integer2 | |
integer1 is not equal to integer2 | ##prefixinteger1 -pgt prefixinteger2 | |
##prefixinteger1 - plt prefixinteger2 | After removing the prefix part of the non-numeric string, integer1 is smaller than integer2 | |
##file1 - nt file2 | The modification time of file1 is newer than file2 | |
file1 -ot file2 | The modification time of file1 is older than file2 | |
-d file | file exists and is a directory | |
-e file | file exists | |
-f file | file exists and is not a directory | |
##-s file | file exists and the file occupied space is greater than zero | |
-n string | The length of string is greater than zero | |
string | The length of string is greater than zero, which is equivalent to -n string | |
-z string | The length of string is equal to zero | |
( expression ) | # Take expression as a whole | |
! expression | NOT (NOT) | |
expression1 -a expression2 | And (AND), you can also use expression1 expression2, but it is not recommended | |
expression1 -o expression2 | ## or (OR)