GRUB’s Short Memory: Making a Dual-Boot Machine Remember What You Picked

- by

My ThinkPad P15 dual-boots Fedora and Windows, and GRUB gives me five seconds to decide which one to choose. It picks Fedora by default, but depending on what I need that’s 50% wrong and since booting happens to fast, I just need a little extra time to make up my mind. Nine times out of ten I’m literally one second too late.

My other Z840 workstation has the same dual-boot arrangement, but somehow it never annoys me – because years ago I set it up to boot whatever I picked last time. I remember it being an ordeal of five half-explained articles before it worked, and for some reason I never wrote it down (likely because I ran out of patience back then). Which is how I ended up re-solving my own solved problem, this time with a proper write-up for future me.

Full solution is at the end of the article, but let’s talk about the mechanisms at play first.

Part one: more time to think

Every GRUB setting we care about lives in /etc/default/grub. It’s a plain shell-style file of KEY=value lines, and it’s not read directly by GRUB at boot – it’s the input to grub2-mkconfig, which compiles it into the real grub.cfg. That’s the one thing to remember: editing the file does nothing until you regenerate.

The timeout is the easy part. Open the file and change the first line:

GRUB_TIMEOUT=30

The value is in seconds; -1 waits forever. Thirty is comfortable without making an unattended reboot feel like an eternity. My desktop takes much onger to boot, so I often walk off to get coffee and I’ve changed it to wait for 60 seconds and that seems the right amount of time for me to catch it. Worth experimenting what feels good for your situation.

While you’re there, check that GRUB_TIMEOUT_STYLE is either absent or set to menu – Fedora’s default – rather than hidden, otherwise the countdown runs invisibly and you’ll wonder why nothing changed. Then regenerate:

sudo grub2-mkconfig -o /boot/grub2/grub.cfg

On modern Fedora that path is correct for both BIOS and UEFI installs. Older guides will send you to /boot/efi/EFI/fedora/grub.cfg on UEFI systems; these days that file is just a stub that hands over to the one in /boot/grub2, so leave it alone.

Part two: remembering the last choice

A longer timeout treats the symptom. The Z840 approach treats the cause: if I booted Windows last time, chances are I want Windows again, and vice versa. GRUB has supported this for ages, and it takes exactly two settings in the same file:

GRUB_DEFAULT=saved
GRUB_SAVEDEFAULT=true

Regenerate with the same grub2-mkconfig command, reboot, and from now on whatever you select in the menu becomes the default for the next boot. Pick Windows once, and the machine keeps booting Windows until you tell it otherwise.

The twist that makes the guides confusing

Here’s why I suspect this took me five articles the first time round. Most of them lead with GRUB_DEFAULT=saved as if it were the fix. Open /etc/default/grub on any Fedora system and you’ll find that line is already there. It ships that way. So you add it, nothing changes, and you conclude the article was wrong.

The two lines do different jobs. GRUB_DEFAULT=saved tells GRUB where to look for the default: not “entry 0”, not “the one called Windows”, but “whatever is written in the saved_entry variable in my environment block”. That block is a small file at /boot/grub2/grubenv, and you can read it any time with:

sudo grub2-editenv list

Fedora uses this on purpose. When a new kernel is installed, the kernel scripts write its identifier into saved_entry so the newest kernel boots by default. That’s the whole reason saved is the default: it’s Fedora’s mechanism for keeping the menu pointing at the current kernel. On its own, nothing about your menu choice ever gets saved.

GRUB_SAVEDEFAULT=true is the missing half. It makes grub2-mkconfig add a savedefault step to the menu entries, so that selecting one writes it back into saved_entry at boot time. Now the environment block is updated by two parties – kernel installs and you – and the last one to write wins. Run grub2-editenv list after a Windows boot and you’ll see saved_entry pointing at the Windows entry; boot Fedora and it flips back. That’s your proof it’s working.

One consequence worth knowing: a kernel update will grab the default back for itself, because it writes saved_entry too. After dnf update pulls in a new kernel, the next boot lands on Fedora regardless of what you chose before – pick Windows once and normal service resumes. On a machine that lives mostly in one OS you’ll barely notice; it’s mentioned here so it doesn’t look like the setting stopped working. This had me confused on the first few boots.

Why this works on Fedora (and where it doesn’t)

GRUB has to be able to write

Saving the default means GRUB writes to grubenv from inside the bootloader, before any operating system is running. GRUB can read dozens of filesystems but can only write to a very short list, and it does so by overwriting the file’s blocks in place. That rules out anything that relocates data on write – Btrfs, LVM, software RAID, encrypted volumes – where the write either fails silently or GRUB refuses with an error about sparse files.

Fedora sidesteps this because Anaconda always creates a small separate ext4 /boot partition, even on a Btrfs install. If you followed along with my ThinkPad dual-boot article you saw it in the installer’s review screen: a 2GB ext4 partition mounted at /boot, alongside the Btrfs root. That’s where grubenv lives, and ext4 is on GRUB’s write list. If you’re on a distro that puts /boot straight on Btrfs – some openSUSE and Arch layouts do – GRUB_SAVEDEFAULT will not work and the usual advice is to leave it off.

A one-off default without the memory

If you’d rather not have GRUB remember anything but still want to control the next boot from the command line – say, before a remote reboot – the same environment block does that too:

sudo grub2-set-default "Windows Boot Manager (on /dev/nvme0n1p1)"

Use the exact title as it appears in the menu; grep menuentry /boot/grub2/grub.cfg will show you the candidates. That’s the saved half doing its job on its own, no SAVEDEFAULT required.

The whole recipe

For the impatient, and for future me searching my own site:

sudo sed -i 's/^GRUB_TIMEOUT=.*/GRUB_TIMEOUT=30/' /etc/default/grub
grep -q '^GRUB_SAVEDEFAULT' /etc/default/grub || echo 'GRUB_SAVEDEFAULT=true' | sudo tee -a /etc/default/grub
sudo grub2-mkconfig -o /boot/grub2/grub.cfg

Three lines, one reboot, and the P15 now behaves like the Z840: it waits long enough for me to look up, and if I don’t, it makes the choice I’d have made anyway. Another mystery put to bed – and this time it’s written down.



If you enjoy my content, please consider supporting me on Ko-fi. In return you can browse this whole site without any pesky ads! More details here.

Leave a Comment!

This site uses Akismet to reduce spam. Learn how your comment data is processed.