at 23.05-pre 5.4 kB view raw
1{ config, lib, pkgs, ... }: 2 3with lib; 4let 5 cfg = config.services.lvm; 6in { 7 options.services.lvm = { 8 package = mkOption { 9 type = types.package; 10 default = pkgs.lvm2; 11 internal = true; 12 defaultText = literalExpression "pkgs.lvm2"; 13 description = lib.mdDoc '' 14 This option allows you to override the LVM package that's used on the system 15 (udev rules, tmpfiles, systemd services). 16 Defaults to pkgs.lvm2, pkgs.lvm2_dmeventd if dmeventd or pkgs.lvm2_vdo if vdo is enabled. 17 ''; 18 }; 19 dmeventd.enable = mkEnableOption (lib.mdDoc "the LVM dmevent daemon"); 20 boot.thin.enable = mkEnableOption (lib.mdDoc "support for booting from ThinLVs"); 21 boot.vdo.enable = mkEnableOption (lib.mdDoc "support for booting from VDOLVs"); 22 }; 23 24 options.boot.initrd.services.lvm.enable = (mkEnableOption (lib.mdDoc "enable booting from LVM2 in the initrd")) // { 25 visible = false; 26 }; 27 28 config = mkMerge [ 29 ({ 30 # minimal configuration file to make lvmconfig/lvm2-activation-generator happy 31 environment.etc."lvm/lvm.conf".text = "config {}"; 32 }) 33 (mkIf (!config.boot.isContainer) { 34 systemd.tmpfiles.packages = [ cfg.package.out ]; 35 environment.systemPackages = [ cfg.package ]; 36 systemd.packages = [ cfg.package ]; 37 38 services.udev.packages = [ cfg.package.out ]; 39 40 # We need lvm2 for the device-mapper rules 41 boot.initrd.services.udev.packages = lib.mkIf config.boot.initrd.services.lvm.enable [ cfg.package ]; 42 # The device-mapper rules want to call tools from lvm2 43 boot.initrd.systemd.initrdBin = lib.mkIf config.boot.initrd.services.lvm.enable [ cfg.package ]; 44 boot.initrd.services.udev.binPackages = lib.mkIf config.boot.initrd.services.lvm.enable [ cfg.package ]; 45 }) 46 (mkIf cfg.dmeventd.enable { 47 systemd.sockets."dm-event".wantedBy = [ "sockets.target" ]; 48 systemd.services."lvm2-monitor".wantedBy = [ "sysinit.target" ]; 49 50 environment.etc."lvm/lvm.conf".text = '' 51 dmeventd/executable = "${cfg.package}/bin/dmeventd" 52 ''; 53 services.lvm.package = mkDefault pkgs.lvm2_dmeventd; 54 }) 55 (mkIf cfg.boot.thin.enable { 56 boot.initrd = { 57 kernelModules = [ "dm-snapshot" "dm-thin-pool" ]; 58 59 systemd.initrdBin = lib.mkIf config.boot.initrd.services.lvm.enable [ pkgs.thin-provisioning-tools ]; 60 61 extraUtilsCommands = mkIf (!config.boot.initrd.systemd.enable) '' 62 for BIN in ${pkgs.thin-provisioning-tools}/bin/*; do 63 copy_bin_and_libs $BIN 64 done 65 ''; 66 67 extraUtilsCommandsTest = mkIf (!config.boot.initrd.systemd.enable) '' 68 ls ${pkgs.thin-provisioning-tools}/bin/ | grep -v pdata_tools | while read BIN; do 69 $out/bin/$(basename $BIN) --help > /dev/null 70 done 71 ''; 72 }; 73 74 environment.etc."lvm/lvm.conf".text = concatMapStringsSep "\n" 75 (bin: "global/${bin}_executable = ${pkgs.thin-provisioning-tools}/bin/${bin}") 76 [ "thin_check" "thin_dump" "thin_repair" "cache_check" "cache_dump" "cache_repair" ]; 77 78 environment.systemPackages = [ pkgs.thin-provisioning-tools ]; 79 }) 80 (mkIf cfg.boot.vdo.enable { 81 boot = { 82 initrd = { 83 kernelModules = [ "kvdo" ]; 84 85 systemd.initrdBin = lib.mkIf config.boot.initrd.services.lvm.enable [ pkgs.vdo ]; 86 87 extraUtilsCommands = mkIf (!config.boot.initrd.systemd.enable)'' 88 ls ${pkgs.vdo}/bin/ | while read BIN; do 89 copy_bin_and_libs ${pkgs.vdo}/bin/$BIN 90 done 91 substituteInPlace $out/bin/vdorecover --replace "${pkgs.bash}/bin/bash" "/bin/sh" 92 substituteInPlace $out/bin/adaptLVMVDO.sh --replace "${pkgs.bash}/bin/bash" "/bin/sh" 93 ''; 94 95 extraUtilsCommandsTest = mkIf (!config.boot.initrd.systemd.enable)'' 96 ls ${pkgs.vdo}/bin/ | grep -vE '(adaptLVMVDO|vdorecover)' | while read BIN; do 97 $out/bin/$(basename $BIN) --help > /dev/null 98 done 99 ''; 100 }; 101 extraModulePackages = [ config.boot.kernelPackages.kvdo ]; 102 }; 103 104 services.lvm.package = mkOverride 999 pkgs.lvm2_vdo; # this overrides mkDefault 105 106 environment.systemPackages = [ pkgs.vdo ]; 107 }) 108 (mkIf (cfg.dmeventd.enable || cfg.boot.thin.enable) { 109 boot.initrd.systemd.contents."/etc/lvm/lvm.conf".text = optionalString (config.boot.initrd.services.lvm.enable && cfg.boot.thin.enable) (concatMapStringsSep "\n" 110 (bin: "global/${bin}_executable = /bin/${bin}") 111 [ "thin_check" "thin_dump" "thin_repair" "cache_check" "cache_dump" "cache_repair" ] 112 ) + "\n" + optionalString cfg.dmeventd.enable '' 113 dmeventd/executable = /bin/false 114 activation/monitoring = 0 115 ''; 116 117 boot.initrd.preLVMCommands = mkIf (!config.boot.initrd.systemd.enable) '' 118 mkdir -p /etc/lvm 119 cat << EOF >> /etc/lvm/lvm.conf 120 ${optionalString cfg.boot.thin.enable ( 121 concatMapStringsSep "\n" 122 (bin: "global/${bin}_executable = $(command -v ${bin})") 123 [ "thin_check" "thin_dump" "thin_repair" "cache_check" "cache_dump" "cache_repair" ] 124 ) 125 } 126 ${optionalString cfg.dmeventd.enable '' 127 dmeventd/executable = "$(command -v false)" 128 activation/monitoring = 0 129 ''} 130 EOF 131 ''; 132 }) 133 ]; 134 135}