diff --git a/nixos/modules/tasks/filesystems/overlayfs.nix b/nixos/modules/tasks/filesystems/overlayfs.nix index 0dde2fdc66b3e..8db2aeb90a30c 100644 --- a/nixos/modules/tasks/filesystems/overlayfs.nix +++ b/nixos/modules/tasks/filesystems/overlayfs.nix @@ -1,17 +1,29 @@ -{ config, lib, pkgs, utils, ... }: +{ + config, + lib, + pkgs, + utils, + ... +}: let # The scripted initrd contains some magic to add the prefix to the # paths just in time, so we don't add it here. - sysrootPrefix = fs: - if config.boot.initrd.systemd.enable && fs.overlay.underlyingDirectoriesOnRealRoot && (utils.fsNeededForBoot fs) then + sysrootPrefix = + fs: + if + config.boot.initrd.systemd.enable + && fs.overlay.underlyingDirectoriesOnRealRoot + && (utils.fsNeededForBoot fs) + then "/sysroot" else ""; # Returns a service that creates the required directories before the mount is # created. - preMountService = _name: fs: + preMountService = + _name: fs: let prefix = sysrootPrefix fs; @@ -21,106 +33,111 @@ let upperdir = prefix + fs.overlay.upperdir; workdir = prefix + fs.overlay.workdir; in - lib.mkIf (fs.overlay.upperdir != null) - { - "rw-${escapedMountpoint}" = { - requiredBy = [ mountUnit ]; - before = [ mountUnit ]; - unitConfig = { - DefaultDependencies = false; - RequiresMountsFor = "${upperdir} ${workdir}"; - }; - serviceConfig = { - Type = "oneshot"; - ExecStart = "${pkgs.coreutils}/bin/mkdir -p -m 0755 ${upperdir} ${workdir}"; - }; + lib.mkIf (fs.overlay.upperdir != null) { + "rw-${escapedMountpoint}" = { + requiredBy = [ mountUnit ]; + before = [ mountUnit ]; + unitConfig = { + DefaultDependencies = false; + RequiresMountsFor = "${upperdir} ${workdir}"; + }; + serviceConfig = { + Type = "oneshot"; + ExecStart = "${pkgs.coreutils}/bin/mkdir -p -m 0755 ${upperdir} ${workdir}"; }; }; + }; - overlayOpts = { config, ... }: { + overlayOpts = + { config, ... }: + { - options.overlay = { + options.overlay = { - lowerdir = lib.mkOption { - type = with lib.types; nullOr (nonEmptyListOf (either str pathInStore)); - default = null; - description = '' - The list of path(s) to the lowerdir(s). + lowerdir = lib.mkOption { + type = with lib.types; nullOr (nonEmptyListOf (either str pathInStore)); + default = null; + description = '' + The list of path(s) to the lowerdir(s). - To create a writable overlay, you MUST provide an `upperdir` and a - `workdir`. + To create a writable overlay, you MUST provide an `upperdir` and a + `workdir`. - You can create a read-only overlay when you provide multiple (at - least 2!) lowerdirs and neither an `upperdir` nor a `workdir`. - ''; - }; + You can create a read-only overlay when you provide multiple (at + least 2!) lowerdirs and neither an `upperdir` nor a `workdir`. + ''; + }; - upperdir = lib.mkOption { - type = lib.types.nullOr lib.types.str; - default = null; - description = '' - The path to the upperdir. + upperdir = lib.mkOption { + type = lib.types.nullOr lib.types.str; + default = null; + description = '' + The path to the upperdir. - If this is null, a read-only overlay is created using the lowerdir. + If this is null, a read-only overlay is created using the lowerdir. - If the filesystem is `neededForBoot`, this will be prefixed with `/sysroot`, - unless `underlyingDirectoriesOnRealRoot` is set to `true`. + If the filesystem is `neededForBoot`, this will be prefixed with `/sysroot`, + unless `underlyingDirectoriesOnRealRoot` is set to `true`. - If you set this to some value you MUST also set `workdir`. - ''; - }; + If you set this to some value you MUST also set `workdir`. + ''; + }; - workdir = lib.mkOption { - type = lib.types.nullOr lib.types.str; - default = null; - description = '' - The path to the workdir. + workdir = lib.mkOption { + type = lib.types.nullOr lib.types.str; + default = null; + description = '' + The path to the workdir. - If the filesystem is `neededForBoot`, this will be prefixed with `/sysroot`, - unless `underlyingDirectoriesOnRealRoot` is set to `true`. + If the filesystem is `neededForBoot`, this will be prefixed with `/sysroot`, + unless `underlyingDirectoriesOnRealRoot` is set to `true`. - This MUST be set if you set `upperdir`. - ''; - }; + This MUST be set if you set `upperdir`. + ''; + }; - underlyingDirectoriesOnRealRoot = lib.mkOption { - type = lib.types.bool; - default = false; - description = '' - If disabled, `lowerdir`, `upperdir` and `workdir` will be prefixed with `/sysroot`. + underlyingDirectoriesOnRealRoot = lib.mkOption { + type = lib.types.bool; + default = false; + description = '' + If disabled, `lowerdir`, `upperdir` and `workdir` will be prefixed with `/sysroot`. - Enabling this can be useful to create an overlay over directories which aren't on the real root. + Enabling this can be useful to create an overlay over directories which aren't on the real root. + + This does not work with the scripted (i.e. non-systemd) initrd. + ''; + }; + }; - This does not work with the scripted (i.e. non-systemd) initrd. - ''; + config = lib.mkIf (config.overlay.lowerdir != null) { + fsType = "overlay"; + device = lib.mkDefault "overlay"; + depends = map (x: "${x}") ( + config.overlay.lowerdir + ++ lib.optionals (config.overlay.upperdir != null) [ + config.overlay.upperdir + config.overlay.workdir + ] + ); + + options = + let + prefix = sysrootPrefix config; + + lowerdir = map (s: prefix + s) config.overlay.lowerdir; + upperdir = prefix + config.overlay.upperdir; + workdir = prefix + config.overlay.workdir; + in + [ + "lowerdir=${lib.concatStringsSep ":" lowerdir}" + ] + ++ lib.optionals (config.overlay.upperdir != null) [ + "upperdir=${upperdir}" + "workdir=${workdir}" + ]; }; - }; - config = lib.mkIf (config.overlay.lowerdir != null) { - fsType = "overlay"; - device = lib.mkDefault "overlay"; - depends = map (x: "${x}") (config.overlay.lowerdir ++ lib.optionals (config.overlay.upperdir != null) [ - config.overlay.upperdir - config.overlay.workdir - ]); - - options = - let - prefix = sysrootPrefix config; - - lowerdir = map (s: prefix + s) config.overlay.lowerdir; - upperdir = prefix + config.overlay.upperdir; - workdir = prefix + config.overlay.workdir; - in - [ - "lowerdir=${lib.concatStringsSep ":" lowerdir}" - ] ++ lib.optionals (config.overlay.upperdir != null) [ - "upperdir=${upperdir}" - "workdir=${workdir}" - ]; }; - - }; in {