Repository navigation
Build one initramfs, not two, in a Limine Mac's re-key - #17
joshuaswarren wants to merge 6 commits into
Conversation
maralcbr
left a comment
There was a problem hiding this comment.
Good catch on the wasted build. The staged key isn't embedded in the initramfs (rd.luks.key=…:UUID=<Boot>), so skipping /boot's image leaves no key material behind. Three changes before merge, all about proving the image that actually boots:
- Prove firmware ordering in every image a boot entry uses.
boot_image_orders_firmwarenow checks only the UKI on every Limine Mac, even whenapple_rekey_boothas just rebuilt/boot's image because GRUB is kept, and GRUB's entries boot that image. An M2+ booting a GRUB entry could then hit the disk prompt before the keyboard firmware, and nothing checks it before the staged key goes (provision_commit). Rule: on a Limine Mac, always check the UKI, and also/boot's image whenever retained GRUB entries use it. Test a good UKI with a bad GRUB image. - One GRUB decision.
grub_tools_present(-x $MAC_BOOT_ROOT/usr/bin/grub-probeandgrub-mkconfig) re-implements the decisionomarchy-mac-boot-updatemakes (omarchy-cmd-present grub-probe && … grub-mkconfig, plusOMARCHY_MAC_BOOT_UPDATE_GRUB). Two copies of one decision is exactly what cost #13 five rounds. Share one predicate. One caveat for (1):OMARCHY_MAC_BOOT_UPDATE_GRUBsuppresses regeneration, but that doesn't prove existing GRUB entries can't boot, so the firmware check should follow the boot images that are reachable, not that flag. provision_prepareuses the same rule. It still refuses oninitramfs_orders_firmware,/boot's image only, so a UKI-only Mac can be refused because of a stale image nothing boots. Prepare and commit should apply the same "images that boot" rule.
Please also post the first-boot timing once it's run with this change.
|
All three are in b5ad429:
The one-build goal holds: a Limine Mac without GRUB still runs Suites: |
The owner's re-key ran mkinitcpio -P before omarchy-mac-boot-update. On a Limine Mac without GRUB that builds /boot's GRUB image, which nothing boots, and then the UKI. On a 14-inch M2 Max (2026-10-06 first boot) each build took 8.6 to 10.0 s. Build only the UKI there, as omarchy-mac-encrypt already does; a Limine Mac that keeps GRUB still rebuilds its image. The commit then proves the firmware ordering in the image the Mac boots: the initramfs inside the UKI on a Limine Mac, not /boot's image.
The re-key proved the ordering in one image: the UKI on a Limine Mac, /boot's image elsewhere. A Limine Mac that keeps GRUB boots both. GRUB's retained entries boot /boot's image, so a build that left the vendor firmware out of it asked for the disk password before the keyboard firmware worked, and nothing checked it before provision-commit removed the staged key. provision-prepare refused a UKI-only Mac over a stale image nothing boots, and never read its UKI. Prepare and commit now prove the same images: the UKI on a Limine Mac, plus /boot's image wherever GRUB is kept. One decision names that GRUB is kept: grub_tools_present in lib/grub-keep.sh, which omarchy-mac-boot-update and lib/provision.sh both source. OMARCHY_MAC_BOOT_UPDATE_GRUB stays out of the check: it suppresses a rebuild, it does not stop GRUB from booting the image already there.
b5ad429 to
5f82570
Compare
|
Thanks @joshuaswarren. My three earlier points are addressed. Two small fixes needed before merge:
Optional: a test for an updater that fails after rewriting the command line (with a restore that also fails), and a missing-helper test. Please also post the first-boot timing when you have it. |
Without set -e, a missing grub-keep.sh left grub_tools_present returning 127, and the update carried on as if GRUB were absent.
…cpio On root's PATH, mkinitcpio resolves to the limine-mkinitcpio-hook wrapper in /usr/local/bin, which builds the real image and then the UKI and exits with the UKI's status. The keep-GRUB branch of a re-key therefore built extra images and hid a failed build of /boot's image. Call /usr/bin/mkinitcpio explicitly, and let the tests redirect it with OMARCHY_MKINITCPIO.
… a missing GRUB helper An updater that rewrites the command line and then fails, with a restore that fails too, still leaves the key on the boot partition and the restored command line in the boot files for the retry. A boot update whose GRUB helper does not load stops instead of carrying on without it.
|
The integration harness runs the staged provision in a fixture root where only PATH stubs exist, so the absolute /usr/bin/mkinitcpio failed there with No such file or directory and first-boot setup refused to finish. Resolve it as every other fixed path in provision.sh does, below MAC_BOOT_ROOT: empty on a live system, so production still calls /usr/bin/mkinitcpio past the wrapper on root's PATH, and a fixture root in tests, which now carries the stub. This replaces yesterday's OMARCHY_MKINITCPIO override, so the tests keep one convention.
scottjones
left a comment
There was a problem hiding this comment.
Thanks Joshua, this does what it says. A Limine Mac without GRUB now builds only the UKI during the re-key, and a Mac that keeps GRUB still rebuilds /boot's image. I checked Marcelo's points at 55d7eb1 and all five look resolved: the three from 10-07 (every boot image is proved, one grub_tools_present, prepare and commit use the same rule) and the two from 10-09 (/usr/bin/mkinitcpio past the wrapper, and the helper load failing closed). Thanks for working through them so carefully.
Three small things, all low and none blocking:
-
limine-update hides a failed UKI build. limine-mkinitcpio-install has
process_uki_kernel || return 0andprocess_kernel ... || true, in limine-mkinitcpio-hook 1.40.0-2 on edge (source) and in the 1.39.0-2 that release candidates pin (source). Solimine-updateexits 0 when the UKI build fails. On a Limine Mac without GRUB, commit then checks the old UKI's.initrd, which passes, and shreds the key, while the old UKI's.cmdlinestill namesrd.luks.key=. Reproduced in a fixture.- It's safe at boot: systemd-cryptsetup treats the missing key file as a cue to prompt for the password right away, and the next successful
limine-updatewrites a clean UKI. - Two options: refuse in commit when the UKI's
.cmdlinestill holdsrd.luks.key=, or, better since every caller is exposed, haveomarchy-mac-boot-updateconfirm the UKI was actually rebuilt. - Most of this is on main already. What's new is that main's
mkinitcpio -Pused to stop a re-key when the mkinitcpio config was broken.
- It's safe at boot: systemd-cryptsetup treats the missing key file as a cue to prompt for the password right away, and the next successful
-
Pre-existing:
boot_image_types_layout(omarchy-mac-boot/lib/provision.sh:176, Limine branch at :187) checks only the UKI, even on a Limine Mac that keeps GRUB. The new firmware check,boot_image_orders_firmware(:132), covers every image. -
Test gap: the
fail-mkinitcpiorow (omarchy-mac-boot/test/mac-provision-test.sh:408) passes only because the fixture image can't be extracted. Adding|| trueto themkinitcpio -Pcall at provision.sh:100 still passes the whole suite. A row where the/bootimage build really fails would pin that down.
None of these hold the merge from my side. Thanks again!
iconidentify
left a comment
There was a problem hiding this comment.
Validated 55d7eb1 and its conflict-free merge onto current main d8100ec. The full boot-package suite passes on both; provisioning integration also passes against Omarchy e1b0e5e after the merge retains main's updated platform fixtures.
The rekey path uses the shared GRUB predicate, checks UKI firmware contents and any retained GRUB image, and preserves the staged key on reported failures. No new high/medium finding in this change. Scott's three nonblocking follow-ups remain: a masked UKI build failure can leave the old cmdline, retained-GRUB keymap coverage is still UKI-only, and the mkinitcpio failure test needs a stronger negative control.
This review covers source and controlled tests. It does not supply new cold-boot evidence or first-boot timing.
On a Limine Mac without GRUB, the owner's re-key builds an initramfs image that nothing boots.
omarchy-provision-ownerre-keys the disk and then rebuilds the initramfs withmkinitcpio -Pbefore it callsomarchy-mac-boot-update. On a Limine Mac without GRUB,-Pbuilds/boot's GRUB image, which nothing boots, and then the UKI. On a 14-inch M2 Max's first boot (2026-10-06), each of those builds took 8.6 to 10.0 s. That first boot ran five full initramfs builds in about 46 s. This change removes the GRUB-image one from the re-key.Now a Limine Mac without GRUB builds only the UKI at that point, as
omarchy-mac-encryptalready does. A Limine Mac that keeps GRUB still rebuilds its image.The change also proves the firmware ordering in the image the Mac actually boots: the initramfs inside the UKI on a Limine Mac, not
/boot's image.test/mac-provision-test.shhas three new cases. A Limine Mac without GRUB tools runsomarchy-mac-boot-updateand nomkinitcpio -P. A Limine Mac that keeps GRUB still runsmkinitcpio -Pfirst. On a Limine Mac, the firmware ordering is checked in the UKI's initramfs.Checked at 4b463ef on main f47d3db (no newer upstream commits at the time), on a Debian host with the runtime CI pins (omacom/omarchy bf659459):
.github/scripts/check-scopeandcheck-architecture-gatesexit 0.mac-provision-test.shpasses, and so do the other 21 test files that pass on main. Three omarchy-mac-boot test files also fail on main here, so they are not caused by this change:apple-silicon-boot-check-test.sh(exit 127, a missing tool),mac-external-displays-test.shandupdate-m1n1-locale-test.sh(exit 1).shellcheck -S warningfinds nothing in the files this adds; the two warnings in changed test files are already on main. CI runs the full suites in the Arch container once this is open.Not measured yet: the first boot with this change. The saving is the one build's time (8.6 to 10.0 s), taken from the first boot above. There is a second, separate saving on the runtime side (a refresh that rebuilds the UKI again, 9 s on the same Mac), which is a separate PR to omacom/omarchy.