Yet another bonkers bootloader: Limine

I recently found out about Limine. It’s a new and interesting bootloader, that is sleek and simple (it’s simplicity requires some slight changes to the mount layout, more on that below). It’s fast and can coexist next to other bootloaders (while it doesn’t have a snapshot booting tool (yet), you can still boot grub through it, meaning you still have perfect access to all your snapshots!).

Image from their github:

Note: Installing Limine comes at the unfortunate cost of pretty much losing the ability of booting into snapper snapshots. While you can still restore them, you’ll need to regenerate the kernel image and initramfs probably everytime, as we have established below.

What it took to set it up (requires root perms, aka sudo - all of this is at your own risk. Best you look up the details at the links below.):

  1. Open /etc/fstab, and replace /boot/efi with /boot/ (boot/efi is fat32, and also a separate boot partition. Limine requires both of those to function. This change doesn’t (to my knowledge) affect the system is any meaningful way)
  2. mv /boot/efi/** /boot (we want to finish the move away from a purely-efi boot partition - You will lose snapshot capabilities for most things related to booting!)
  3. sudo pacman -S limine
  4. cp /usr/share/limine/BOOTX64.EFI /boot/EFI (the EFI directory should still be present, already used by grub)
  5. cp /usr/share/limine/limine-bios.sys /boot/ (the EFI directory should still be present, already used by grub)
  6. grub-install --efi-directory /boot --boot-directory /boot /dev/sdXYReinstall grub to use /boot as the EFI directory. Replace sdXY with your root partition identifier.
  7. micro /boot/limine.cfg:
:Garuda Linux
    PROTOCOl=linux
    KERNEL_PATH=boot:///vmlinuz-linux-zen
    CMDLINE=root=UUID=<check "blkid" for the UUID of the root partition> rw rootflags=subvol=@
    MODULE_PATH=boot:///initramfs-linux-zen.img

:Grub
    PROTOCOL=efi_chainload
    IMAGE_PATH=boot:///EFI/garuda/grubx64.efi

If you’re using other kernels you can of course edit KERNEL_PATH? and MODULE_PATH to reflect the differences…

  1. run efibootmgr --create --disk /dev/sdX --part Y --loader '\EFI\BOOTX64.EFI' --label "Garuda Linux" --unicode (replace X with your system device which has the bootloader partition, for me it’s sda. Replace Y with the partition number of your boot partition. My boot partition is /dev/sda1, so I set it to 1)

Benefits:

  1. You still have access to Grub, so no further work for our overworked Garuda Forum voluntary supporters :wink:
  2. You can, at least temporarily, edit Limine’s config on the fly in the boot menu
  3. The config is - very human. very easy to use.
  4. It’s fast

For any further config, check:

4 Likes

Very interesting! And riscv64 support! :star_struck:

Are you sure about this? That definitely will affect the system in a meaningful way. Mounting the EFI partition at /boot means all your kernels and initramfs images will be stored on FAT32, so bye bye Btrfs snapshots.

I am not seeing anything in the docs you linked suggesting an EFI partition mounted at /boot/efi is problematic in any way, so I would say just leave it alone.

It is very easy to boot to Grub from rEFInd. In fact, rEFInd will detect existing Grub boot entries, automatically add them to the boot menu, and chainload Grub when you select one so you don’t even have to do anything.

You can also configure a stanza to boot to Grub from rEFInd like this: https://forum.garudalinux.org/t/how-i-installed-every-garuda-spin-on-one-partition/27353#configure-refind-7 Adding it into a stanza also allows setting up booting to Grub as a submenu entry, so it can be tucked away inside of your normal boot option if you want (as opposed to a separate boot option just for Grub).

…Huh. I mean, I suppose this boils down to a matter of preference, but…really?!

Look at this stuff!

There are tons of themes, it can look however you want! refind-theme · GitHub Topics · GitHub

I have to assume from this statement you are not writing your own rEFInd boot stanzas, and are just using the auto-generated ones for your boot routine. That’s no way to live!

If you write your own stanza, the submenus can be whatever you want. They can have alternate kernels or images, different boot parameters…you can even chainload other bootloaders like Grub. Here is an example of a custom submenu:

Writing a manual boot stanza is a little tricky if you have never done it before, but it’s not that bad once you get the hang of it. I wrote up a doc for the Garuda Wiki page that describes how to do it: Writing a rEFInd Boot Stanza | Garuda Linux wiki

6 Likes

I haven’t thought about that actually, but would you really need snapshots for kernels? Any sane person would always have at least the LTS kernel installed beside e.g. Zen, so you’d always have a backup. There’s also the fallback initramfs.

I also wanna mention that I forgot to include that you probably need to re-install grub to specifically use /boot for EFI. For anyone reading this, instructions are above

Ok you have a point there haha. I don’t like the mostly picture-based refind navigation that much. Booting snapshots is a pain and you have a pretty small and hard limit on the snapshots you cat view and thus boot if you’re using refind-btrfs.

Well I did write my own, but refind-btrfs cannot use those. I should clarify that.

1 Like

You cannot boot off of Btrfs snapshots if the kernel and images are not part of the snapshot. Once the kernel is updated, all your snapshots will become unbootable. You will have to leave them on the Btrfs partition if you want to be able to boot off of snapshots.

The user defines how many snapshots to put in the menu with refind-btrfs. :eyes: If you want more snapshots in the menu, just change the value of selection_count in refind-btrfs.conf.

I agree refind-btrfs is not as intuitive as grub-btrfs. After getting used to grub-btrfs where the snapshots are labeled with the Pacman transaction they are associated with, refind-btrfs with its humble timestamps just seems not as good.

Just to clarify, refind-btrfs is not part of rEFInd and you don’t have to install or use it if you don’t like it. Anyone who wants to can just boot from rEFInd to Grub for restoring snapshots with grub-btrfs like normal. This is what I would recommend for Garuda Linux users, since removing Grub is not possible anyway (at least not without breaking some Garuda stuff).

If refind-btrfs isn’t able to use your boot stanza, most likely there is a mistake in your stanza. In fact, having a properly-written boot stanza is a prerequisite of the application:

https://github.com/Venom1991/refind-btrfs#prerequisites

  • at least one manual boot stanza (found in rEFInd’s main config file or in any of the additional config files included within it) defined such that (see the ArchWiki for an example) its own “options” field or any such field belonging to at least one of its sub-menus contains definitions of the following boot loader options:

    • the “root” option must be matched with the root partition (by PARTUUID or PARTLABEL), its filesystem (by UUID or LABEL) or with a block device (by name) which itself represents the root partition
    • the “rootflags” option must define a “subvol” suboption which is matched with the root subvolume’s logical path and/or a “subvolid” suboption which is matched with the root subvolume’s ID

I haven’t used it in a while, but I never had any issues with refind-btrfs and submenus except the script does not run if there is a submenu entry that specifies a different option for volume.

To be clear, specifying a different value for volume is not a documented feature which is why refind-btrfs never added support for it. The only reason I use it is for allowing booting to Grub from a rEFInd submenu. In any case, if anyone runs into this I described the workaround in the issue above.

To think people would boot into a bootloader to boot into another bootloader. :rofl: I guess that’s just linux for you.

3 Likes

why would they? All the bootloader does is load the images into … ram or something like that. That will work regardless of their version. The images don’t have a timestamp in their filename so it should work nomatter what.

There seems to be an upper limit of what refind likes to display. I think it always stopped after the second or third page

No I was referring to the good, fancy menus, where you can boot into specific options. refind-btrfs only takes simple stanzas, anything else and it won’t generate them. I tried, and my config was good.

lol…it does sound kind of ridiculous when you put it that way. But there are many legitimate reasons this is a handy feature, for example multibooting with an OS which is tied to a specific bootloader. It makes it so you don’t have to select your OS from the BIOS boot menu every time, you can just use a single bootloader to manage everything.

These days, most bootloaders–including Grub and systemd-boot–support chainloading other bootloaders.

No, it will definitely break booting into all existing snapshots every time the kernel is updated. The Grub configs stored in the snapshots will reference a version of the kernel that no longer exists. The boot will immediately fail.

The filename of the image is not related to why the boot will fail. Timestamps do not have anything to do with it one way or the other. To boot into a Btrfs snapshot, the kernel referenced in the snapshot must be present.

It definitely sounds like you did not have refind-btrfs properly configured, or your stanzas were not written correctly. I can confirm that even with elaborate boot stanzas from testing unusual or complex boot configurations, refind-btrfs works as expected.

2 Likes

I don’t understand. Limine does the same thing, and it is simply loading the kernel image, and the initramfs and then starting. There is no config file that tells the bootloader about features that were added/changed, despite the fact that I don’t think the linux kernel suddenly changes its loading and starting procedure. if the file is present on the partition, it should just be able to load it, nomatter what. It’s not like it’ll be gone, it’ll just have a different kernel version.

I don’t even think that BTRFS snapshots take snapshots of the sysfs, so what would hinder it from loading?

Well I definitely had it configured correctly and it still wouldn’t work. strictly adhered to the docs.
I cannot fully remember the problem, but I think it was something about refind-btrfs not being able to put the snapshots into the submenu of a boot stanza even though that is theoretically possible.

Edit regarding the kernel update: Your terminology of “immediately fail” confused me a bit. I just updated the linux kernel, and tried to boot a snapshot with it. As you hinted at, it did fail, but not with something I’d expected: It seems to be missing pretty much all of the important kernel modules. No idea how/why it’s doing that, but that’s the problem anyway. I wonder if you could do something about that…

Edit 2:

If [the kernel version] has [changed], the kernel version no longer matches the version of the kernel modules.

I guess that’s where the real problems start. Address mismatches and stuff preventing the modules from being loaded. Too bad, since this renders BTRFS practically useless when used on the root partition. I read that you can fix that by re-running the kenel image generation though (after restoration).

From

/boot/grub/grub-btrfs.cfg
menuentry '  vmlinuz-linux-clear & initramfs-linux-clear-fallback.img & intel-ucode.img' --class snapshots --class gnu-linux --class gnu --class os $menu
entry_id_option 'gnulinux-snapshots-e0a08d20-208f-444a-a6f0-281ffd8a1e1b' {
        if [ x$feature_all_video_module = xy ]; then
        insmod all_video
        fi
        set gfxpayload=keep
        insmod btrfs
        if [ x$feature_platform_search_hint = xy ]; then
            search --no-floppy --fs-uuid  --set=root  e0a08d20-208f-444a-a6f0-281ffd8a1e1b
        else
            search --no-floppy --fs-uuid  --set=root e0a08d20-208f-444a-a6f0-281ffd8a1e1b
        fi
        echo 'Loading Snapshot: 2024-01-20 21:08:22 @/.snapshots/12/snapshot'
        echo 'Loading Kernel: vmlinuz-linux-clear ...'
        linux "/@/.snapshots/12/snapshot/boot/vmlinuz-linux-clear" root=UUID=e0a08d20-208f-444a-a6f0-281ffd8a1e1b  quiet console=tty0 console=ttyS0,115200n8 
cryptomgr.notests initcall_debug intel_iommu=igfx_off kvm-intel.nested=1 no_timer_check noreplace-smp page_alloc.shuffle=1 rcupdate.rcu_expedited=1 rootfstyp
e=btrfs tsc=reliable rw resume=UUID=1824b554-dd46-4e14-a85d-6aafd14791a7 loglevel=3 acpi_backlight=video nvidia-drm.modeset=1 ibt=off  rootflags=defaults,noa
time,compress=zstd,subvol="@/.snapshots/12/snapshot"
        echo 'Loading Microcode & Initramfs: intel-ucode.img initramfs-linux-clear-fallback.img ...'
        initrd "/@/.snapshots/12/snapshot/boot/intel-ucode.img" "/@/.snapshots/12/snapshot/boot/initramfs-linux-clear-fallback.img"
    }

as can be seen what’s being loaded is not a partition but a snapshot subvolume. The reason having a kernel different from what’s expected would be the API’s referenced by various modules and software running in your system. As the kernel develops it adds and drops a bunch of things. This might be fine if the kernel hasn’t changed anything drastic that causes issues with backwards compatibility but if it did…

1 Like

Yep.

I have seen some workarounds in the EOS forum, because systemd-boot has been available in the installer for a while now (systemd-boot uses the EFI partition for storing the kernels and images) and some folks want to shoehorn it into booting off snapshots like Grub.

For example, this person worked out some scripting to copy /efi on to the Btrfs partiton every time the kernel is updated: Btrfs snapshots and esp - Applications - EndeavourOS. I guess that still leaves the task of restoring it back to the /efi partition when needed, so not a complete solution in and of itself.

This person uses manual Btrfs snapshots (not Snapper) with some scripting to modify the snapshots themselves: SystemD boot + secure boot + TPM2 unlocking + UKI + Dual boot (windows) + Dracut + BTRFS + LUKS2 + boot from Snapshots - #6 by Svartis - EndeavourOS installation - EndeavourOS. A pretty neat solution, although very custom and of course they script their own snapshotting routine, etc.

I would say if you want to boot off of Btrfs snapshots, just keep the kernels and images on the Btrfs partition and use a bootloader like Grub which makes this process very easy.

I am not sure what you mean by this. I think having a Btrfs root partition is incredibly useful, whether or not you are storing the kernel and images there and booting off of snapshots or not.

Just to backtrack to the original topic for a moment: I’m not sure what any of this has to do with Limine, because it does not appear that storing the kernel and images on the EFI partition is a prerequisite for this bootloader. Here, it says you can specify the path for the kernel and images in the config: https://wiki.archlinux.org/title/Limine#UEFI_systems:

Configuration

limine does not ship a default configuration file, it is therefore necessary to create one. This file is necessary to teach Limine which operating systems are available for boot. The configuration file has a lot of options as Limine allows for a fair degree of customisation. A detailed documentation of the configuration file, its format, and its keys can be found here.

The configuration file, just like limine-bios.sys, needs to reside on either the root, a /boot, a /limine, or a /boot/limine directory of a partition on the drive on which Limine is deployed, as long as the file system of said partition is supported. The configuration file has to be named limine.cfg.

Note: In a Limine config, boot:/// represents the partition on which limine.cfg is located. In case there is no separate /boot partition, and limine.cfg resides on the root partition instead, then, in the following example, boot:/// should instead be boot:///boot/.

Here follows a simple example configuration that contains 1 boot menu entry that describes a typical Arch Linux kernel and initramfs:

limine.cfg
TIMEOUT=5 

:Arch Linux 
     PROTOCOL=linux 
     KERNEL_PATH=boot:///vmlinuz-linux 
     CMDLINE=root=UUID=*xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx* rw
     MODULE_PATH=boot:///initramfs-linux.img

where xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx is the root file system’s UUID.

Just leave the system configured as-is, with the EFI partition mounted at /boot/efi, and the kernel and images in /boot in the Btrfs partition, and point to them in their normal locations in the Limine config.

1 Like

Limine solely supports the CD format and FAT. Support for ext4 has recently been removed, for simplicity’s sake. You cannot take snapshots of FAT partitions, and Limine cannot read BTRFS partitions. So there is no common denominator to make this work.

This appears to be the overall least-hacky and reliable solution. Aw man, I was so happy when I found out about limine…

This topic was automatically closed 14 days after the last reply. New replies are no longer allowed.