feat: merge bootloader related features

This commit is contained in:
2026-05-26 21:11:59 +02:00
parent db1e9c15ac
commit a9378ca8b5
7 changed files with 129 additions and 132 deletions

View File

@@ -3,11 +3,23 @@
{ {
config, config,
lib, lib,
pkgs,
inputs, inputs,
... ...
}: }:
let let
cfg = config.features.bootloader; cfg = config.features.bootloader;
keyDir = "/etc/secrets/initrd";
mkIpString =
{
address,
gateway,
netmask,
interface,
...
}:
"${address}::${gateway}:${netmask}::${interface}:none";
in in
{ {
imports = [ inputs.lanzaboote.nixosModules.lanzaboote ]; imports = [ inputs.lanzaboote.nixosModules.lanzaboote ];
@@ -23,15 +35,88 @@
default = "systemd-boot"; default = "systemd-boot";
}; };
plymouth.enable = lib.mkEnableOption "plymouth boot splash"; configurationLimit = lib.mkOption {
type = lib.types.int;
default = 10;
};
consoleFont = lib.mkOption {
type = lib.types.str;
default = "ter-v32n";
};
resumeDevice = lib.mkOption {
type = lib.types.nullOr lib.types.str;
default = null;
};
initrdSsh = {
enable = lib.mkEnableOption "remote LUKS unlock via ssh in initrd";
networkModule = lib.mkOption {
type = lib.types.str;
};
ip = {
enable = lib.mkEnableOption "static IP for initrd (otherwise DHCP)";
address = lib.mkOption {
type = lib.types.str;
};
gateway = lib.mkOption {
type = lib.types.str;
};
netmask = lib.mkOption {
type = lib.types.str;
default = "255.255.255.0";
};
interface = lib.mkOption {
type = lib.types.str;
};
};
authorizedKeys = lib.mkOption {
type = lib.types.listOf lib.types.str;
default = [ ];
};
};
}; };
config = lib.mkIf cfg.enable ( config = lib.mkIf cfg.enable (
lib.mkMerge [ lib.mkMerge [
{ {
boot.loader.efi.canTouchEfiVariables = true; boot.loader.efi.canTouchEfiVariables = true;
# request the largest framebuffer uefi offers; plymouth inherits it
boot.loader.systemd-boot.consoleMode = "max"; # lanzaboote inherits editor + configurationLimit from systemd-boot.*
boot.loader.systemd-boot = {
editor = false;
inherit (cfg) configurationLimit;
};
boot.initrd.systemd.enable = true;
# block simpledrm so fbcon defers until the gpu driver binds; avoids
# the simpledrm -> real-driver fbcon transition that mangles console
# text and leaves the luks prompt typing offset from the visible
# surface. hosts must put the gpu driver in initrd (nixos-hardware
# does this for amd; manual hardware.amdgpu.initrd.enable on others)
boot.kernelParams = [ "initcall_blacklist=simpledrm_platform_driver_init" ];
# verbose boot: kernel messages and systemd unit lines visible end
# to end. trade-off: the luks prompt will be interleaved with the
# last few "Starting/Started ..." lines (no upstream fix exists
# without plymouth). boot.initrd.verbose is a no-op under
# systemd-initrd, so not set here.
# readable luks prompt at panel-native dpi
console = {
earlySetup = true;
font = cfg.consoleFont;
packages = [ pkgs.terminus_font ];
};
} }
(lib.mkIf (cfg.mode == "systemd-boot") { (lib.mkIf (cfg.mode == "systemd-boot") {
@@ -46,26 +131,41 @@
}; };
}) })
(lib.mkIf cfg.plymouth.enable { (lib.mkIf (cfg.resumeDevice != null) {
# plymouth needs systemd-initrd to render the luks prompt cleanly boot.resumeDevice = cfg.resumeDevice;
boot.initrd.systemd.enable = true; })
# host is responsible for early-KMS so plymouth lands on the gpu driver, (lib.mkIf cfg.initrdSsh.enable {
# not simpledrm (e.g. hardware.amdgpu.initrd.enable on amd hosts) boot.initrd.systemd.settings.Manager.DefaultDeviceTimeoutSec = "infinity";
boot.plymouth.enable = true;
stylix.targets.plymouth.logoAnimated = false;
boot.kernelParams = [ boot.initrd.availableKernelModules = [ cfg.initrdSsh.networkModule ];
"quiet"
"splash" boot.kernelParams = lib.mkIf cfg.initrdSsh.ip.enable [
"loglevel=3" "ip=${mkIpString cfg.initrdSsh.ip}"
"rd.systemd.show_status=false"
"rd.udev.log_level=3"
"udev.log_priority=3"
"plymouth.force-scale=1"
]; ];
boot.consoleLogLevel = 0;
boot.initrd.verbose = false; boot.initrd.network = {
enable = true;
ssh = {
enable = true;
port = 22;
hostKeys = [
"${keyDir}/ssh_host_rsa_key"
"${keyDir}/ssh_host_ed25519_key"
];
inherit (cfg.initrdSsh) authorizedKeys;
};
};
# forward LUKS password prompt to the ssh session (systemd-initrd idiom)
boot.initrd.systemd.users.root.shell = "/bin/systemd-tty-ask-password-agent";
boot.initrd.systemd.network.networks = lib.mkIf (!cfg.initrdSsh.ip.enable) {
"10-initrd" = {
matchConfig.Driver = cfg.initrdSsh.networkModule;
networkConfig.DHCP = "yes";
};
};
}) })
] ]
); );

View File

@@ -1,90 +0,0 @@
{
nixos =
{ lib, config, ... }:
let
cfg = config.features.initrd-ssh;
keyDir = "/etc/secrets/initrd";
mkIpString =
{
address,
gateway,
netmask,
interface,
...
}:
"${address}::${gateway}:${netmask}::${interface}:none";
in
{
options.features.initrd-ssh = {
enable = lib.mkEnableOption "initrd ssh";
ip = {
enable = lib.mkEnableOption "static IP for initrd (otherwise DHCP)";
address = lib.mkOption {
type = lib.types.str;
};
gateway = lib.mkOption {
type = lib.types.str;
};
netmask = lib.mkOption {
type = lib.types.str;
default = "255.255.255.0";
};
interface = lib.mkOption {
type = lib.types.str;
};
};
authorizedKeys = lib.mkOption {
type = lib.types.listOf lib.types.str;
default = [ ];
};
networkModule = lib.mkOption {
type = lib.types.str;
};
};
config = lib.mkIf cfg.enable {
boot.initrd.availableKernelModules = [ cfg.networkModule ];
boot.initrd.kernelModules = [ cfg.networkModule ];
boot.kernelParams = lib.mkIf cfg.ip.enable [
"ip=${mkIpString cfg.ip}"
];
boot.initrd.systemd.enable = true;
# remote unlock may take a while; don't let device units give up
boot.initrd.systemd.settings.Manager.DefaultDeviceTimeoutSec = "infinity";
boot.initrd.network = {
enable = true;
ssh = {
enable = true;
port = 22;
hostKeys = [
"${keyDir}/ssh_host_rsa_key"
"${keyDir}/ssh_host_ed25519_key"
];
inherit (cfg) authorizedKeys;
};
};
# systemd-networkd retries DHCP indefinitely, unlike udhcpc
boot.initrd.systemd.network.networks = lib.mkIf (!cfg.ip.enable) {
"10-initrd" = {
matchConfig.Driver = cfg.networkModule;
networkConfig.DHCP = "yes";
};
};
# forward LUKS password prompt to the SSH session
boot.initrd.systemd.users.root.shell = "/bin/systemd-tty-ask-password-agent";
};
};
}

View File

@@ -8,11 +8,6 @@
options.features.power = { options.features.power = {
enable = lib.mkEnableOption "laptop power management"; enable = lib.mkEnableOption "laptop power management";
resumeDevice = lib.mkOption {
type = lib.types.nullOr lib.types.str;
default = null;
};
lidSwitch = lib.mkOption { lidSwitch = lib.mkOption {
type = lib.types.str; type = lib.types.str;
default = "suspend-then-hibernate"; default = "suspend-then-hibernate";
@@ -40,8 +35,6 @@
}; };
config = lib.mkIf cfg.enable { config = lib.mkIf cfg.enable {
boot.resumeDevice = lib.mkIf (cfg.resumeDevice != null) cfg.resumeDevice;
services.logind.settings.Login = { services.logind.settings.Login = {
HandleLidSwitch = cfg.lidSwitch; HandleLidSwitch = cfg.lidSwitch;
HandlePowerKey = cfg.powerKey; HandlePowerKey = cfg.powerKey;

View File

@@ -55,7 +55,6 @@ in
"git" "git"
"gnupg" "gnupg"
"harmonia" "harmonia"
"initrd-ssh"
"localisation" "localisation"
"neovim" "neovim"
"networkmanager" "networkmanager"

View File

@@ -10,16 +10,13 @@
inputs.nixos-hardware.nixosModules.framework-16-amd-ai-300-series inputs.nixos-hardware.nixosModules.framework-16-amd-ai-300-series
]; ];
features.bootloader.plymouth.enable = true; features.bootloader.resumeDevice = "/dev/mapper/vg0-swap";
features.desktop.bluetooth.enable = true; features.desktop.bluetooth.enable = true;
features.gnupg.yubikey.enable = true; features.gnupg.yubikey.enable = true;
features.udev = { features.udev = {
ledger.enable = true; ledger.enable = true;
keyboard-zsa.enable = true; keyboard-zsa.enable = true;
}; };
features.power.resumeDevice = "/dev/disk/by-uuid/ff4750e7-3a9f-42c2-bb68-c458a6560540";
boot.kernelParams = [ "pcie_aspm.policy=powersupersave" ];
programs.nix-ld.libraries = options.programs.nix-ld.libraries.default; programs.nix-ld.libraries = options.programs.nix-ld.libraries.default;

View File

@@ -37,10 +37,7 @@
fileSystems."/boot" = { fileSystems."/boot" = {
device = "/dev/disk/by-uuid/42D9-FAFD"; device = "/dev/disk/by-uuid/42D9-FAFD";
fsType = "vfat"; fsType = "vfat";
options = [ options = [ "umask=0077" ];
"fmask=0022"
"dmask=0022"
];
}; };
swapDevices = [ swapDevices = [

View File

@@ -8,7 +8,11 @@
features.nix-settings.towerCache.enable = false; features.nix-settings.towerCache.enable = false;
features.bootloader = { features.bootloader = {
mode = "lanzaboote"; mode = "lanzaboote";
plymouth.enable = true; initrdSsh = {
enable = true;
networkModule = "r8169";
authorizedKeys = userKeys.sshAuthorizedKeys;
};
}; };
features.desktop.bluetooth.enable = true; features.desktop.bluetooth.enable = true;
features.gnupg.yubikey.enable = true; features.gnupg.yubikey.enable = true;
@@ -16,17 +20,14 @@
ledger.enable = true; ledger.enable = true;
keyboard-zsa.enable = true; keyboard-zsa.enable = true;
}; };
features.initrd-ssh = {
networkModule = "r8169";
authorizedKeys = userKeys.sshAuthorizedKeys;
};
# nix store signing # nix store signing
sops.secrets.nix-signing-key.sopsFile = ../../secrets/tower.yaml; sops.secrets.nix-signing-key.sopsFile = ../../secrets/tower.yaml;
nix.settings.secret-key-files = [ config.sops.secrets.nix-signing-key.path ]; nix.settings.secret-key-files = [ config.sops.secrets.nix-signing-key.path ];
boot.kernelParams = [ "btusb.reset=1" ]; boot.kernelParams = [ "btusb.reset=1" ];
# early kms so plymouth lands on amdgpu, not simpledrm # pairs with bootloader's simpledrm initcall blacklist: amdgpu owns fbcon
# from the start, no driver-swap mode-set
hardware.amdgpu.initrd.enable = true; hardware.amdgpu.initrd.enable = true;
services.udisks2.enable = true; services.udisks2.enable = true;