nixos/systemd-repart: enable running after initrd

This commit is contained in:
nikstur 2023-02-14 19:39:08 +01:00
parent 8422db6f0d
commit b1ff1e1658
2 changed files with 82 additions and 34 deletions

View File

@ -1,7 +1,8 @@
{ config, pkgs, lib, ... }: { config, pkgs, lib, ... }:
let let
cfg = config.boot.initrd.systemd.repart; cfg = config.systemd.repart;
initrdCfg = config.boot.initrd.systemd.repart;
writeDefinition = name: partitionConfig: pkgs.writeText writeDefinition = name: partitionConfig: pkgs.writeText
"${name}.conf" "${name}.conf"
@ -24,45 +25,59 @@ let
''; '';
in in
{ {
options.boot.initrd.systemd.repart = { options = {
enable = lib.mkEnableOption (lib.mdDoc "systemd-repart") // { boot.initrd.systemd.repart.enable = lib.mkEnableOption (lib.mdDoc "systemd-repart") // {
description = lib.mdDoc '' description = lib.mdDoc ''
Grow and add partitions to a partition table a boot time in the initrd. Grow and add partitions to a partition table at boot time in the initrd.
systemd-repart only works with GPT partition tables. systemd-repart only works with GPT partition tables.
To run systemd-repart after the initrd, see
`options.systemd.repart.enable`.
''; '';
}; };
partitions = lib.mkOption { systemd.repart = {
type = with lib.types; attrsOf (attrsOf (oneOf [ str int bool ])); enable = lib.mkEnableOption (lib.mdDoc "systemd-repart") // {
default = { }; description = lib.mdDoc ''
example = { Grow and add partitions to a partition table.
"10-root" = { systemd-repart only works with GPT partition tables.
Type = "root";
}; To run systemd-repart while in the initrd, see
"20-home" = { `options.boot.initrd.systemd.repart.enable`.
Type = "home"; '';
SizeMinBytes = "512M"; };
SizeMaxBytes = "2G";
}; partitions = lib.mkOption {
type = with lib.types; attrsOf (attrsOf (oneOf [ str int bool ]));
default = { };
example = {
"10-root" = {
Type = "root";
};
"20-home" = {
Type = "home";
SizeMinBytes = "512M";
SizeMaxBytes = "2G";
};
};
description = lib.mdDoc ''
Specify partitions as a set of the names of the definition files as the
key and the partition configuration as its value. The partition
configuration can use all upstream options. See <link
xlink:href="https://www.freedesktop.org/software/systemd/man/repart.d.html"/>
for all available options.
'';
}; };
description = lib.mdDoc ''
Specify partitions as a set of the names of the definition files as the
key and the partition configuration as its value. The partition
configuration can use all upstream options. See <link
xlink:href="https://www.freedesktop.org/software/systemd/man/repart.d.html"/>
for all available options.
'';
}; };
}; };
config = lib.mkIf cfg.enable { config = lib.mkIf (cfg.enable || initrdCfg.enable) {
# Link the definitions into /etc so that they are included in the # Always link the definitions into /etc so that they are also included in
# /nix/store of the sysroot. This also allows the user to run the # the /nix/store of the sysroot during early userspace (i.e. while in the
# systemd-repart binary after activation manually while automatically # initrd).
# picking up the definition files.
environment.etc."repart.d".source = definitionsDirectory; environment.etc."repart.d".source = definitionsDirectory;
boot.initrd.systemd = { boot.initrd.systemd = lib.mkIf initrdCfg.enable {
additionalUpstreamUnits = [ additionalUpstreamUnits = [
"systemd-repart.service" "systemd-repart.service"
]; ];
@ -73,7 +88,7 @@ in
# Override defaults in upstream unit. # Override defaults in upstream unit.
services.systemd-repart = { services.systemd-repart = {
# Unset the coniditions as they cannot be met before activation because # Unset the conditions as they cannot be met before activation because
# the definition files are not stored in the expected locations. # the definition files are not stored in the expected locations.
unitConfig.ConditionDirectoryNotEmpty = [ unitConfig.ConditionDirectoryNotEmpty = [
" " # required to unset the previous value. " " # required to unset the previous value.
@ -97,5 +112,12 @@ in
after = [ "sysroot.mount" ]; after = [ "sysroot.mount" ];
}; };
}; };
systemd = lib.mkIf cfg.enable {
additionalUpstreamSystemUnits = [
"systemd-repart.service"
];
};
}; };
} }

View File

@ -52,9 +52,6 @@ let
}; };
}; };
boot.initrd.systemd.enable = true;
boot.initrd.systemd.repart.enable = true;
# systemd-repart operates on disks with a partition table. The qemu module, # systemd-repart operates on disks with a partition table. The qemu module,
# however, creates separate filesystem images without a partition table, so # however, creates separate filesystem images without a partition table, so
# we have to create a disk image manually. # we have to create a disk image manually.
@ -88,7 +85,10 @@ in
nodes.machine = { config, pkgs, ... }: { nodes.machine = { config, pkgs, ... }: {
imports = [ common ]; imports = [ common ];
boot.initrd.systemd.repart.partitions = { boot.initrd.systemd.enable = true;
boot.initrd.systemd.repart.enable = true;
systemd.repart.partitions = {
"10-root" = { "10-root" = {
Type = "linux-generic"; Type = "linux-generic";
}; };
@ -105,4 +105,30 @@ in
assert "Growing existing partition 1." in systemd_repart_logs assert "Growing existing partition 1." in systemd_repart_logs
''; '';
}; };
after-initrd = makeTest {
name = "systemd-repart-after-initrd";
meta.maintainers = with maintainers; [ nikstur ];
nodes.machine = { config, pkgs, ... }: {
imports = [ common ];
systemd.repart.enable = true;
systemd.repart.partitions = {
"10-root" = {
Type = "linux-generic";
};
};
};
testScript = { nodes, ... }: ''
${useDiskImage nodes.machine}
machine.start()
machine.wait_for_unit("multi-user.target")
systemd_repart_logs = machine.succeed("journalctl --unit systemd-repart.service")
assert "Growing existing partition 1." in systemd_repart_logs
'';
};
} }