GRUB2 Bootloader Configuration on RHEL
Objective
This guide covers GRUB2 bootloader management on Red Hat Enterprise Linux. By the end, you will know how to:
- Understand the relationship between
/etc/default/grub,grub.cfg, and BLS entries - Inspect and modify GRUB2 configuration settings safely
- Configure the GRUB boot menu timeout
- Add and remove kernel command-line parameters
- Regenerate the GRUB2 configuration using
grub2-mkconfig - Use
grubbyto manage kernel parameters and default boot entries - Verify kernel parameters after reboot using
/proc/cmdline - Troubleshoot bootloader issues using system logs and GRUB tools
- Safely back up and restore GRUB configuration after making changes
GRUB2 is the first software that runs when your RHEL system powers on. It loads the kernel, passes parameters to it, and hands control over to the Linux operating system. Understanding how GRUB2 works, how to configure it correctly, and how to recover when it is misconfigured is an essential skill for any Linux administrator. On RHEL, this is also directly tested on the RHCSA exam.
The GRUB2 Configuration Architecture
GRUB2 on RHEL has three distinct layers that work together. Understanding which layer does what prevents the most common mistakes.
| File / Location | Purpose | Edit Directly? |
|---|---|---|
/etc/default/grub |
Human-edited source file: timeout, kernel command line defaults, menu behaviour | Yes, this is the file you edit |
/boot/grub2/grub.cfg |
Generated GRUB configuration used by the bootloader at runtime. Never edit this directly. | No, generated by grub2-mkconfig |
/boot/loader/entries/*.conf |
Boot Loader Specification (BLS) entries: one file per installed kernel with its specific parameters | Via grubby (not directly) |
/proc/cmdline |
Runtime read-only view of the kernel parameters used by the currently running kernel | No, read-only kernel interface |
The workflow for making persistent changes:
- Global settings (timeout, default menu options): edit
/etc/default/grub, then rungrub2-mkconfig - Kernel-specific parameters (adding or removing arguments for a specific kernel): use
grubby, which updates BLS entries directly without needinggrub2-mkconfig
Step 1: Inspect the Current GRUB2 Configuration
# View the human-editable GRUB settings file
cat /etc/default/grub
# Sample output:
# GRUB_TIMEOUT=5
# GRUB_DISTRIBUTOR="$(sed 's, release .*$,,g' /etc/system-release)"
# GRUB_DEFAULT=saved
# GRUB_DISABLE_SUBMENU=true
# GRUB_TERMINAL_OUTPUT="console"
# GRUB_CMDLINE_LINUX="crashkernel=1G-4G:192M,4G-64G:256M,64G-:512M resume=/dev/mapper/rhel-swap rd.lvm.lv=rhel/root rd.lvm.lv=rhel/swap rhgb quiet"
# GRUB_DISABLE_RECOVERY="true"
# GRUB_ENABLE_BLSCFG=true
# List all installed kernels and their boot entries using grubby
grubby --info=ALL
# Show information about the default kernel only
grubby --default-kernel
# Show the index of the default kernel
grubby --default-index
# View BLS entry files for installed kernels
ls /boot/loader/entries/
# View a specific BLS entry file
cat /boot/loader/entries/*.conf
# Check what kernel parameters are currently active on the running system
cat /proc/cmdline
# Sample output:
# BOOT_IMAGE=(hd0,gpt2)/vmlinuz-5.14.0-427.el9.x86_64 root=/dev/mapper/rhel-root ro
# crashkernel=1G-4G:192M rhgb quiet rd.lvm.lv=rhel/root rd.lvm.lv=rhel/swap
Step 2: Back Up GRUB Configuration Before Making Changes
Always back up your GRUB configuration before making changes. A misconfigured bootloader can leave a system unbootable, and the backup gives you a recovery path.
# Back up the GRUB defaults file
cp /etc/default/grub /etc/default/grub.backup
# Back up the generated grub.cfg
cp /boot/grub2/grub.cfg /boot/grub2/grub.cfg.backup
# Back up the BLS entries directory
cp -r /boot/loader/entries/ /boot/loader/entries.backup/
# Verify backups exist
ls -la /etc/default/grub.backup
ls -la /boot/grub2/grub.cfg.backup
Step 3: Modify /etc/default/grub
The most common changes to /etc/default/grub are adjusting the boot menu timeout and modifying the default kernel command line.
# Key settings in /etc/default/grub and what they control:
# GRUB_TIMEOUT=5
# How many seconds the boot menu is displayed before booting the default entry
# Set to 0 to boot immediately, -1 to wait indefinitely for user input
# GRUB_DEFAULT=saved
# Which kernel to boot by default
# "saved" remembers the last selected entry
# A number (0, 1, 2...) selects by position
# A full kernel title string selects by name
# GRUB_CMDLINE_LINUX="..."
# Parameters appended to the kernel command line for ALL boot entries
# This is where you add persistent kernel parameters
# GRUB_ENABLE_BLSCFG=true
# Enables Boot Loader Specification mode (default on RHEL 8+)
# When true, grubby manages kernel-specific parameters in BLS entries
# Example: Change the boot menu timeout to 10 seconds
# Edit /etc/default/grub and change GRUB_TIMEOUT=5 to GRUB_TIMEOUT=10
# Using sed to change it without opening an editor
sed -i 's/^GRUB_TIMEOUT=.*/GRUB_TIMEOUT=10/' /etc/default/grub
# Verify the change
grep GRUB_TIMEOUT /etc/default/grub
# Example: Remove 'rhgb quiet' from the kernel command line
# rhgb = Red Hat Graphical Boot (Plymouth splash screen)
# quiet = suppress kernel messages during boot
# Removing these shows detailed boot messages, useful for troubleshooting
# Edit GRUB_CMDLINE_LINUX in /etc/default/grub
# Remove 'rhgb quiet' from the end of the line
# Save the file
# Verify
grep GRUB_CMDLINE_LINUX /etc/default/grub
Step 4: Regenerate grub.cfg with grub2-mkconfig
After editing /etc/default/grub, you must regenerate the active GRUB configuration. The grub2-mkconfig command reads /etc/default/grub and all BLS entries and produces a new grub.cfg.
# Regenerate grub.cfg for BIOS systems
grub2-mkconfig -o /boot/grub2/grub.cfg
# Regenerate grub.cfg for UEFI systems
grub2-mkconfig -o /boot/efi/EFI/redhat/grub.cfg
# Check which boot mode your system uses
[ -d /sys/firmware/efi ] && echo "UEFI" || echo "BIOS"
# Verify the generated configuration was updated
ls -la /boot/grub2/grub.cfg
head -20 /boot/grub2/grub.cfg
The correct output path depends on whether the system uses BIOS or UEFI firmware. Always check before running grub2-mkconfig.
Step 5: Use grubby to Manage Kernel Parameters
grubby is the recommended tool for managing kernel-specific boot entries on RHEL. It modifies BLS entry files directly and does not require running grub2-mkconfig afterward. This makes it the safer and simpler tool for adding or removing kernel parameters.
# View information about all installed kernels
grubby --info=ALL
# View information about the currently running kernel
grubby --info=$(uname -r | xargs -I{} find /boot -name "vmlinuz-{}")
# View information about the default kernel
grubby --info=DEFAULT
# Show which kernel is set as default
grubby --default-kernel
# Add a kernel parameter to the default kernel
grubby --update-kernel=DEFAULT --args="audit=1"
# Add a parameter to ALL installed kernels
grubby --update-kernel=ALL --args="audit=1"
# Add multiple parameters at once
grubby --update-kernel=DEFAULT --args="audit=1 selinux=1"
# Remove a kernel parameter from the default kernel
grubby --update-kernel=DEFAULT --remove-args="rhgb quiet"
# Remove a parameter from ALL installed kernels
grubby --update-kernel=ALL --remove-args="quiet"
# Verify the change was applied
grubby --info=DEFAULT
# Change the default boot kernel
# First, find the kernel path you want to set as default
grubby --info=ALL | grep "^kernel"
# Set a specific kernel as default using its path
grubby --set-default=/boot/vmlinuz-5.14.0-427.el9.x86_64
# Or set by index position
grubby --set-default-index=0
# Verify the default changed
grubby --default-kernel
grubby --default-index
Step 6: Verify Changes After a Reboot
# Reboot to apply GRUB changes
reboot
# After reboot: verify the kernel parameters that were actually used
cat /proc/cmdline
# Verify the running kernel version
uname -r
# Confirm the parameters match what you configured
# If you added audit=1, it should appear in /proc/cmdline
grep audit=1 /proc/cmdline && echo "Parameter applied" || echo "Parameter missing"
Understanding BLS Entries
The Boot Loader Specification (BLS) is a standard for storing individual kernel boot entries as separate files. On RHEL 8 and later, each installed kernel has its own .conf file under /boot/loader/entries/. This replaces the older approach where all kernel entries were embedded directly in grub.cfg.
# List all BLS entry files
ls /boot/loader/entries/
# Sample output:
# 8dc48e2d0e974c9488d16e0fa07b0f0c-5.14.0-427.el9.x86_64.conf
# 8dc48e2d0e974c9488d16e0fa07b0f0c-5.14.0-362.el9.x86_64.conf
# View a BLS entry file
cat /boot/loader/entries/$(ls /boot/loader/entries/ | head -1)
# Sample BLS entry contents:
# title Red Hat Enterprise Linux (5.14.0-427.el9.x86_64) 9.4
# version 5.14.0-427.el9.x86_64
# linux /vmlinuz-5.14.0-427.el9.x86_64
# initrd /initramfs-5.14.0-427.el9.x86_64.img
# options root=/dev/mapper/rhel-root ro crashkernel=1G-4G:192M audit=1
# grub_users $grub_users
# grub_arg --unrestricted
# grub_class kernel
The options line in the BLS entry is what grubby modifies when you use --args and --remove-args. This is the actual kernel command line that will be used when this kernel is booted.
Common Kernel Parameters
| Parameter | What It Does | When to Use It |
|---|---|---|
quiet |
Suppresses most kernel boot messages | Normal operation. Remove for verbose boot troubleshooting. |
rhgb |
Enables the Red Hat Graphical Boot (Plymouth) splash screen | Desktop systems. Remove on servers or when troubleshooting boot. |
audit=1 |
Enables the kernel audit subsystem | Security auditing, compliance environments |
selinux=0 |
Disables SELinux at boot | Temporary troubleshooting only. Never in production. |
enforcing=0 |
Boots SELinux in permissive mode (logs denials, does not block) | SELinux troubleshooting when you need to identify denials without blocking |
rd.break |
Breaks into an initramfs shell before the root filesystem is mounted | Root password recovery, initramfs troubleshooting |
systemd.unit=rescue.target |
Boots into rescue mode | Single-user recovery when set in GRUB at boot time |
crashkernel=auto |
Reserves memory for kdump crash dumps | Systems where crash analysis is needed |
Troubleshooting GRUB2 Issues
System Fails to Boot After GRUB Change
# At the GRUB menu, press 'e' to edit the current boot entry temporarily
# Find the 'linux' line and fix or remove the problematic parameter
# Press Ctrl+X to boot with the temporary change (does not persist)
# After booting successfully, restore your backup
cp /etc/default/grub.backup /etc/default/grub
cp /boot/grub2/grub.cfg.backup /boot/grub2/grub.cfg
# Or use grubby to remove the bad parameter
grubby --update-kernel=DEFAULT --remove-args="bad-parameter"
Check Boot-Time Messages for Errors
# View kernel messages from the current boot
journalctl -b -k
# View kernel messages from the previous boot
journalctl -b -1 -k
# View all errors from the current boot
journalctl -b -p err
# Check for specific boot issues
journalctl -b | grep -i "error\|failed\|warning"
# View boot messages related to a specific kernel module
journalctl -b -k | grep "module_name"
Restore the Original GRUB Configuration
# Restore /etc/default/grub from backup
cp /etc/default/grub.backup /etc/default/grub
# Restore the generated grub.cfg from backup
cp /boot/grub2/grub.cfg.backup /boot/grub2/grub.cfg
# Or regenerate grub.cfg from the restored defaults file
grub2-mkconfig -o /boot/grub2/grub.cfg
# Verify the restoration
grep GRUB_TIMEOUT /etc/default/grub
cat /proc/cmdline # After next reboot
grubby vs grub2-mkconfig: When to Use Each
| Task | Use This Tool | Why |
|---|---|---|
| Add or remove a kernel parameter | grubby --update-kernel --args |
Modifies BLS entries directly, safer and simpler, no regeneration needed |
| Change the boot menu timeout | Edit /etc/default/grub then grub2-mkconfig |
Timeout is a global GRUB setting, not kernel-specific |
| Change the default boot kernel | grubby --set-default |
Manages default entry in BLS without touching /etc/default/grub |
| Add global kernel parameters for all kernels | Edit GRUB_CMDLINE_LINUX then grub2-mkconfig OR grubby --update-kernel=ALL --args |
Either works; grubby is simpler for parameter-only changes |
| Change GRUB menu appearance or other global options | Edit /etc/default/grub then grub2-mkconfig |
These settings live in /etc/default/grub, not BLS entries |
Common Mistakes
- Editing grub.cfg directly. The file at
/boot/grub2/grub.cfgis generated. Any direct edits are overwritten the next timegrub2-mkconfigruns. Always edit/etc/default/grubor usegrubbyfor BLS entries.- The comment at the top of grub.cfg says "DO NOT EDIT THIS FILE" for exactly this reason
- Forgetting to run grub2-mkconfig after editing /etc/default/grub. Editing
/etc/default/grubchanges the source but not the active configuration. The bootloader readsgrub.cfg, not/etc/default/grub. Without regenerating, your changes have no effect.- grubby does not require grub2-mkconfig because it modifies BLS entries, which are read directly
- Using the wrong grub.cfg path for UEFI systems. BIOS systems use
/boot/grub2/grub.cfg. UEFI systems use/boot/efi/EFI/redhat/grub.cfg. Always check firmware type before runninggrub2-mkconfig -o.- Quick check:
[ -d /sys/firmware/efi ] && echo UEFI || echo BIOS
- Quick check:
- Not backing up before making changes. A typo in a kernel parameter or the wrong output path for grub2-mkconfig can leave a system unbootable. The backup takes 30 seconds and has saved many administrators hours of recovery work.
- Not verifying with /proc/cmdline after reboot. The configuration looked correct but the change didn't take effect.
/proc/cmdlineshows exactly what parameters the running kernel was actually given. Always check it after a reboot to confirm.
GRUB2 and the RHCSA Exam
GRUB2 configuration is a direct RHCSA exam objective. Exam tasks in this area typically require:
- Adding a specific kernel parameter using
grubbyand verifying it appears in/proc/cmdlineafter a reboot - Removing a kernel parameter (commonly
quietorrhgb) to enable verbose boot output - Changing the GRUB boot timeout in
/etc/default/gruband regenerating the configuration - Identifying the default kernel and optionally changing it
- Using GRUB at boot time to pass a one-time parameter (appended at the GRUB menu, not persistent)
The exam also tests root password recovery using rd.break, which is a separate topic but relies on the same skill of adding kernel parameters at the GRUB boot menu.
Practice This in a Real Environment
GRUB2 configuration is a topic where you really need to break something and fix it to build genuine confidence. Reading about grub2-mkconfig is not the same as running it wrong on a UEFI system and watching the system fail to boot, then recovering by editing the GRUB menu at boot time.
LinuxCert.Guru has a dedicated hands-on lab for this: GRUB2 Bootloader. It covers inspecting the GRUB configuration, modifying /etc/default/grub, running grub2-mkconfig, using grubby to manage kernel parameters, verifying changes after a reboot, and safely restoring the original configuration, all on real RHEL hosts with auto-graded tasks.
Practice the GRUB2 Bootloader lab at LinuxCert.Guru → https://linuxcert.guru/?name=rh134-grub2-bootloader
Conclusion
GRUB2 management on RHEL involves three distinct layers and two different tools. Once you understand which layer each tool modifies, the whole system makes sense:
/etc/default/grubis the source you edit for global settings: timeout, default kernel, global command-line parametersgrub2-mkconfigregeneratesgrub.cfgfrom/etc/default/grub: always required after editing the defaults file- BLS entries in
/boot/loader/entries/store kernel-specific parameters: managed bygrubby, not edited directly grubbyis the right tool for adding or removing kernel parameters: nogrub2-mkconfigneeded afterward/proc/cmdlineis ground truth: always verify here after a reboot to confirm parameters actually took effect- Always back up before making changes: a bootloader misconfiguration is unrecoverable without physical or console access
- For UEFI systems:
grub2-mkconfig -o /boot/efi/EFI/redhat/grub.cfg, not the BIOS path