Skip to content

Commit d99143c

Browse files
authored
Merge pull request #1007 from DaanDeMeyer/always-initrd
Rework initramfs generation (again)
2 parents b2472e2 + f09e056 commit d99143c

File tree

1 file changed

+58
-38
lines changed

1 file changed

+58
-38
lines changed

mkosi/__init__.py

+58-38
Original file line numberDiff line numberDiff line change
@@ -1816,6 +1816,11 @@ def prepare_tree(args: MkosiArgs, root: Path, do_run_build_script: bool, cached:
18161816
else:
18171817
# If this is not enabled, let's create an empty directory on /boot
18181818
root.joinpath("boot").mkdir(mode=0o700)
1819+
# Make sure kernel-install actually runs when needed by creating the machine-id subdirectory
1820+
# under /boot. For "bios" on Debian/Ubuntu, it's required for grub to pick up the generated
1821+
# initrd.
1822+
if args.distribution in (Distribution.debian, Distribution.ubuntu) and "bios" in args.boot_protocols:
1823+
root.joinpath("boot", args.machine_id).mkdir(mode=0o700)
18191824

18201825
if args.get_partition(PartitionIdentifier.esp):
18211826
root.joinpath("efi/EFI").mkdir(mode=0o700)
@@ -2117,7 +2122,7 @@ def invoke_dnf(
21172122
cmdline += [command, *sort_packages(packages)]
21182123

21192124
with mount_api_vfs(args, root):
2120-
run(cmdline)
2125+
run(cmdline, env=dict(KERNEL_INSTALL_BYPASS="1"))
21212126

21222127
distribution, release = detect_distribution()
21232128
if distribution not in (Distribution.debian, Distribution.ubuntu):
@@ -2378,7 +2383,7 @@ def install_fedora(args: MkosiArgs, root: Path, do_run_build_script: bool) -> No
23782383
add_packages(args, packages, "glibc-minimal-langpack", conditional="glibc")
23792384

23802385
if not do_run_build_script and args.bootable:
2381-
add_packages(args, packages, "kernel-core", "kernel-modules", "dracut", "binutils")
2386+
add_packages(args, packages, "kernel-core", "kernel-modules", "dracut")
23822387
add_packages(args, packages, "systemd-udev", conditional="systemd")
23832388
configure_dracut(args, packages, root)
23842389
if do_run_build_script:
@@ -2413,7 +2418,7 @@ def install_mageia(args: MkosiArgs, root: Path, do_run_build_script: bool) -> No
24132418
packages = {*args.packages}
24142419
add_packages(args, packages, "basesystem-minimal")
24152420
if not do_run_build_script and args.bootable:
2416-
add_packages(args, packages, "kernel-server-latest", "dracut", "binutils")
2421+
add_packages(args, packages, "kernel-server-latest", "dracut")
24172422
configure_dracut(args, packages, root)
24182423
# Mageia ships /etc/50-mageia.conf that omits systemd from the initramfs and disables hostonly.
24192424
# We override that again so our defaults get applied correctly on Mageia as well.
@@ -2462,7 +2467,7 @@ def install_openmandriva(args: MkosiArgs, root: Path, do_run_build_script: bool)
24622467
add_packages(args, packages, "basesystem-minimal", "systemd")
24632468
if not do_run_build_script and args.bootable:
24642469
add_packages(args, packages, "systemd-boot", "systemd-cryptsetup", conditional="systemd")
2465-
add_packages(args, packages, "kernel-release-server", "dracut", "binutils", "timezone")
2470+
add_packages(args, packages, "kernel-release-server", "dracut", "timezone")
24662471
configure_dracut(args, packages, root)
24672472
if args.netdev:
24682473
add_packages(args, packages, "systemd-networkd", conditional="systemd")
@@ -2684,7 +2689,7 @@ def install_centos(args: MkosiArgs, root: Path, do_run_build_script: bool) -> No
26842689
packages = {*args.packages}
26852690
add_packages(args, packages, "centos-release", "systemd")
26862691
if not do_run_build_script and args.bootable:
2687-
add_packages(args, packages, "kernel", "dracut", "binutils")
2692+
add_packages(args, packages, "kernel", "dracut")
26882693
configure_dracut(args, packages, root)
26892694
if epel_release <= 7:
26902695
add_packages(
@@ -2736,7 +2741,7 @@ def install_rocky(args: MkosiArgs, root: Path, do_run_build_script: bool) -> Non
27362741
packages = {*args.packages}
27372742
add_packages(args, packages, "rocky-release", "systemd")
27382743
if not do_run_build_script and args.bootable:
2739-
add_packages(args, packages, "kernel", "dracut", "binutils")
2744+
add_packages(args, packages, "kernel", "dracut")
27402745
configure_dracut(args, packages, root)
27412746
add_packages(args, packages, "systemd-udev", conditional="systemd")
27422747

@@ -2768,7 +2773,7 @@ def install_alma(args: MkosiArgs, root: Path, do_run_build_script: bool) -> None
27682773
packages = {*args.packages}
27692774
add_packages(args, packages, "almalinux-release", "systemd")
27702775
if not do_run_build_script and args.bootable:
2771-
add_packages(args, packages, "kernel", "dracut", "binutils")
2776+
add_packages(args, packages, "kernel", "dracut")
27722777
configure_dracut(args, packages, root)
27732778
add_packages(args, packages, "systemd-udev", conditional="systemd")
27742779

@@ -2800,10 +2805,11 @@ def invoke_apt(
28002805
) -> None:
28012806

28022807
cmdline = ["/usr/bin/apt-get", "--assume-yes", command, *extra]
2803-
env = {
2804-
"DEBIAN_FRONTEND": "noninteractive",
2805-
"DEBCONF_NONINTERACTIVE_SEEN": "true",
2806-
}
2808+
env = dict(
2809+
DEBIAN_FRONTEND="noninteractive",
2810+
DEBCONF_NONINTERACTIVE_SEEN="true",
2811+
INITRD="No",
2812+
)
28072813

28082814
run_workspace_command(args, root, cmdline, network=True, env=env)
28092815

@@ -2853,7 +2859,7 @@ def install_debian_or_ubuntu(args: MkosiArgs, root: Path, *, do_run_build_script
28532859
extra_packages.update(args.build_packages)
28542860

28552861
if not do_run_build_script and args.bootable:
2856-
add_packages(args, extra_packages, "dracut", "binutils")
2862+
add_packages(args, extra_packages, "dracut")
28572863
configure_dracut(args, extra_packages, root)
28582864

28592865
if args.distribution == Distribution.ubuntu:
@@ -2944,10 +2950,6 @@ def install_debian_or_ubuntu(args: MkosiArgs, root: Path, *, do_run_build_script
29442950
root.joinpath("etc/resolv.conf").symlink_to("../run/systemd/resolve/resolv.conf")
29452951
run(["systemctl", "--root", root, "enable", "systemd-resolved"])
29462952

2947-
if args.bootable and not do_run_build_script and "uefi" in args.boot_protocols:
2948-
for kver, kimg in gen_kernel_images(args, root):
2949-
run_workspace_command(args, root, ["kernel-install", "add", kver, Path("/") / kimg])
2950-
29512953

29522954
@complete_step("Installing Debian…")
29532955
def install_debian(args: MkosiArgs, root: Path, do_run_build_script: bool) -> None:
@@ -2959,8 +2961,8 @@ def install_ubuntu(args: MkosiArgs, root: Path, do_run_build_script: bool) -> No
29592961
install_debian_or_ubuntu(args, root, do_run_build_script=do_run_build_script)
29602962

29612963

2962-
def run_pacman(root: Path, pacman_conf: Path, packages: Set[str]) -> None:
2963-
run(["pacman", "--config", pacman_conf, "--noconfirm", "-Sy", *sort_packages(packages)])
2964+
def invoke_pacman(root: Path, pacman_conf: Path, packages: Set[str]) -> None:
2965+
run(["pacman", "--config", pacman_conf, "--noconfirm", "-Sy", *sort_packages(packages)], env=dict(KERNEL_INSTALL_BYPASS="1"))
29642966

29652967

29662968
@complete_step("Installing Arch Linux…")
@@ -3103,7 +3105,7 @@ def install_arch(args: MkosiArgs, root: Path, do_run_build_script: bool) -> None
31033105
if args.get_partition(PartitionIdentifier.bios):
31043106
add_packages(args, packages, "grub")
31053107

3106-
add_packages(args, packages, "dracut", "binutils")
3108+
add_packages(args, packages, "dracut")
31073109
configure_dracut(args, packages, root)
31083110

31093111
packages.update(args.packages)
@@ -3127,7 +3129,7 @@ def install_arch(args: MkosiArgs, root: Path, do_run_build_script: bool) -> None
31273129
add_packages(args, packages, "openssh")
31283130

31293131
with mount_api_vfs(args, root):
3130-
run_pacman(root, pacman_conf, packages)
3132+
invoke_pacman(root, pacman_conf, packages)
31313133

31323134
# Arch still uses pam_securetty which prevents root login into
31333135
# systemd-nspawn containers. See https://bugs.archlinux.org/task/45903.
@@ -3173,7 +3175,7 @@ def install_opensuse(args: MkosiArgs, root: Path, do_run_build_script: bool) ->
31733175
add_packages(args, packages, "patterns-base-minimal_base")
31743176

31753177
if not do_run_build_script and args.bootable:
3176-
add_packages(args, packages, "kernel-default", "dracut", "binutils")
3178+
add_packages(args, packages, "kernel-default", "dracut")
31773179
configure_dracut(args, packages, root)
31783180

31793181
if args.get_partition(PartitionIdentifier.bios):
@@ -3224,11 +3226,6 @@ def jj(line: str) -> str:
32243226
# copy now, patch later (in set_autologin())
32253227
shutil.copy2(root / "usr/etc/pam.d/login", root / "etc/pam.d/login")
32263228

3227-
# Zypper doesn't run dracut automatically so we have to do it manually.
3228-
if args.bootable and not do_run_build_script and "uefi" in args.boot_protocols:
3229-
for kver, kimg in gen_kernel_images(args, root):
3230-
run_workspace_command(args, root, ["kernel-install", "add", kver, Path("/") / kimg])
3231-
32323229

32333230
@complete_step("Installing Gentoo…")
32343231
def install_gentoo(
@@ -4261,7 +4258,7 @@ def extract_partition(
42614258
def gen_kernel_images(args: MkosiArgs, root: Path) -> Iterator[Tuple[str, Path]]:
42624259
# Apparently openmandriva hasn't yet completed its usrmerge so we use lib here instead of usr/lib.
42634260
for kver in root.joinpath("lib/modules").iterdir():
4264-
if not (kver.is_dir() and os.path.isfile(os.path.join(kver, "modules.dep"))): # type: ignore
4261+
if not kver.is_dir():
42654262
continue
42664263

42674264
if args.distribution == Distribution.gentoo:
@@ -4333,11 +4330,11 @@ def install_unified_kernel(
43334330
partlabel = None
43344331

43354332
if args.image_version:
4336-
boot_binary = Path(prefix) / f"EFI/Linux/{image_id}_{args.image_version}.efi"
4333+
boot_binary = root / prefix / f"EFI/Linux/{image_id}_{args.image_version}.efi"
43374334
elif root_hash:
4338-
boot_binary = Path(prefix) / f"EFI/Linux/{image_id}-{kver}-{root_hash}.efi"
4335+
boot_binary = root / prefix / f"EFI/Linux/{image_id}-{kver}-{root_hash}.efi"
43394336
else:
4340-
boot_binary = Path(prefix) / f"EFI/Linux/{image_id}-{kver}.efi"
4337+
boot_binary = root / prefix / f"EFI/Linux/{image_id}-{kver}.efi"
43414338

43424339
if root.joinpath("etc/kernel/cmdline").exists():
43434340
boot_options = root.joinpath("etc/kernel/cmdline").read_text().strip()
@@ -4352,17 +4349,24 @@ def install_unified_kernel(
43524349
elif partlabel:
43534350
boot_options = f"{boot_options} root=PARTLABEL={partlabel}"
43544351

4352+
osrelease = root / "usr/lib/os-release"
4353+
cmdline = workspace(root) / "cmdline"
4354+
cmdline.write_text(boot_options)
4355+
initrd = root / prefix / args.machine_id / kver / "initrd"
4356+
43554357
cmd: Sequence[PathString] = [
4356-
"dracut",
4357-
"--uefi",
4358-
"--kver", kver,
4359-
"--kernel-image", Path("/") / kimg,
4360-
"--kernel-cmdline", boot_options,
4361-
"--force",
4358+
"objcopy",
4359+
"--add-section", f".osrel={osrelease}", "--change-section-vma", ".osrel=0x20000",
4360+
"--add-section", f".cmdline={cmdline}", "--change-section-vma", ".cmdline=0x30000",
4361+
"--add-section", f".linux={root / kimg}", "--change-section-vma", ".linux=0x2000000",
4362+
"--add-section", f".initrd={initrd}", "--change-section-vma", ".initrd=0x3000000",
4363+
root / "lib/systemd/boot/efi/linuxx64.efi.stub",
43624364
boot_binary,
43634365
]
43644366

4365-
run_workspace_command(args, root, cmd)
4367+
run(cmd)
4368+
4369+
cmdline.unlink()
43664370

43674371

43684372
def secure_boot_sign(
@@ -7277,6 +7281,21 @@ def setup_netdev(args: MkosiArgs, root: Path, do_run_build_script: bool, cached:
72777281
run(["systemctl", "--root", root, "enable", "systemd-networkd"])
72787282

72797283

7284+
def run_kernel_install(args: MkosiArgs, root: Path, do_run_build_script: bool, for_cache: bool) -> None:
7285+
if not args.bootable or do_run_build_script or for_cache:
7286+
return
7287+
7288+
with complete_step("Generating initramfs images…"):
7289+
# Running kernel-install on Debian/Ubuntu doesn't regenerate the initramfs. Instead, we can trigger
7290+
# regeneration of the initramfs via "dpkg-reconfigure dracut". kernel-install can then be called to put
7291+
# the generated initrds in the right place.
7292+
if args.distribution in (Distribution.debian, Distribution.ubuntu):
7293+
run_workspace_command(args, root, ["dpkg-reconfigure", "dracut"])
7294+
7295+
for kver, kimg in gen_kernel_images(args, root):
7296+
run_workspace_command(args, root, ["kernel-install", "add", kver, Path("/") / kimg])
7297+
7298+
72807299
@dataclasses.dataclass
72817300
class BuildOutput:
72827301
raw: Optional[BinaryIO]
@@ -7368,11 +7387,12 @@ def build_image(
73687387
install_distribution(args, root, do_run_build_script, cached_tree)
73697388
install_etc_locale(args, root, cached_tree)
73707389
install_etc_hostname(args, root, cached_tree)
7371-
install_boot_loader(args, root, loopdev, do_run_build_script, cached_tree)
73727390
run_prepare_script(args, root, do_run_build_script, cached_tree)
73737391
install_build_src(args, root, do_run_build_script, for_cache)
73747392
install_build_dest(args, root, do_run_build_script, for_cache)
73757393
install_extra_trees(args, root, for_cache)
7394+
run_kernel_install(args, root, do_run_build_script, for_cache)
7395+
install_boot_loader(args, root, loopdev, do_run_build_script, cached_tree)
73767396
set_root_password(args, root, do_run_build_script, cached_tree)
73777397
set_serial_terminal(args, root, do_run_build_script, cached_tree)
73787398
set_autologin(args, root, do_run_build_script, cached_tree)

0 commit comments

Comments
 (0)