{ config, pkgs, lib, flakeInputs, ... }: with lib; let cfg = config.nfsroot; in { imports = [ "${flakeInputs.nixpkgs.outPath}/nixos/modules/profiles/minimal.nix" "${flakeInputs.nixpkgs.outPath}/nixos/modules/profiles/all-hardware.nix" "${flakeInputs.nixpkgs.outPath}/nixos/modules/profiles/base.nix" "${flakeInputs.nixpkgs.outPath}/nixos/modules/profiles/installation-device.nix" ]; options = { nfsroot = { storeDevice = mkOption { type = types.str; }; }; }; config = { # Don't build the GRUB menu builder script, since we don't need it # here and it causes a cyclic dependency. boot.loader.grub.enable = false; # !!! Hack - attributes expected by other modules. environment.systemPackages = [ pkgs.grub2_efi ] ++ (if pkgs.stdenv.hostPlatform.system == "aarch64-linux" then [] else [ pkgs.grub2 pkgs.syslinux ]); fileSystems."/" = mkImageMediaOverride { fsType = "tmpfs"; options = [ "mode=0755" ]; }; # In stage 1, mount a tmpfs on top of /nix/store (the squashfs # image) to make this a live CD. fileSystems."/nix/.ro-store" = mkImageMediaOverride { fsType = "nfs4"; device = cfg.storeDevice; options = [ "ro" ]; neededForBoot = true; }; fileSystems."/nix/.rw-store" = mkImageMediaOverride { fsType = "tmpfs"; options = [ "mode=0755" ]; neededForBoot = true; }; fileSystems."/nix/store" = mkImageMediaOverride { fsType = "overlay"; device = "overlay"; options = [ "lowerdir=/nix/.ro-store" "upperdir=/nix/.rw-store/store" "workdir=/nix/.rw-store/work" ]; depends = [ "/nix/.ro-store" "/nix/.rw-store/store" "/nix/.rw-store/work" ]; }; boot.initrd.availableKernelModules = [ "nfs" "nfsv4" "overlay" ]; boot.initrd.supportedFilesystems = [ "nfs" "nfsv4" "overlay" ]; boot.initrd.network.enable = true; boot.initrd.network.flushBeforeStage2 = false; # otherwise nfs dosen't work networking.useDHCP = true; system.build.netbootIpxeScript = pkgs.writeTextDir "netboot.ipxe" '' #!ipxe # Use the cmdline variable to allow the user to specify custom kernel params # when chainloading this script from other iPXE scripts like netboot.xyz kernel ${pkgs.stdenv.hostPlatform.linux-kernel.target} init=${config.system.build.toplevel}/init initrd=initrd ${toString config.boot.kernelParams} ''${cmdline} initrd initrd boot ''; boot.postBootCommands = '' # nixos-rebuild also requires a "system" profile and an # /etc/NIXOS tag. touch /etc/NIXOS ${config.nix.package}/bin/nix-env -p /nix/var/nix/profiles/system --set /run/current-system ''; }; }