Files
nix-dotfiles-v2/developmentlog.md
T

4.4 KiB

Development log

legolas: NVMe (Corsair MP600 ELITE / Phison E21) suspend/resume crashes

The drive hung on resume from S3 (deep) suspend — boot logs ended at PM: suspend entry (deep) with no resume, followed by a hard reboot. The Phison E21 can't recover from the D3 transition that S3 forces.

Investigation also found two existing workarounds were doing nothing:

  • The udev rule ATTR{d3cold_allowed}="0" was a no-op — that sysfs attribute doesn't exist on this Phison endpoint or its parent root port (0000:00:1d.0).
  • The nvme-resume-fix service was broken: ExecStart used > redirection without a shell, so echo just printed the string and never wrote to the rescan sysfs file. It never actually rescanned.

Changes (hosts/legolas/hardware-configuration.nix):

  • Switched mem_sleep_default from deep (S3) to s2idle (modern standby). s2idle avoids the deep D3 path that hangs the drive.
  • Removed the no-op d3cold_allowed rule and the broken rescan service.
  • Added a correct runtime-PM-off udev rule on both the NVMe endpoint (0000:6e:00.0) and its parent root port (0000:00:1d.0), keeping the PCIe wakeup disable.

Note: runtime PM was already off on the endpoint (power/control=on); that alone never fixed the crash because system suspend uses a separate code path. Verify after rebuild that the cmdline has mem_sleep_default=s2idle (the running generation showed a stale duplicate deep).

Headless home-manager configs (galadriel, elros, elrond)

Added minimal home-manager configs for gunalx and root on headless hosts. These skip all GUI/desktop modules (niri, stylix, foot, noctalia, etc.) and keep only CLI tools: bash (with sops AI keys), git, nixvim (full config reused), opencode, atuin, sshconfig, sops.

Files:

  • home/gunalx-headless.nix — gunalx's minimal config, same module set as gunalx.nix minus all GUI imports.
  • home/root.nix — identical CLI stack, explicitly sets home.username/home.homeDirectory to root.
  • home/sops.nix — parameterized age key paths to use config.home.homeDirectory so both users work without duplication.
  • home/sshconfig.nix — removed ssh-askpass-fullscreen (unwired GUI dependency, was dead weight).
  • flake.nix — added headlessHmModules let binding (shared by all three hosts) wiring home-manager.users.gunalx + home-manager.users.root.

Manual step: root needs the sops age key at /root/.config/sops/age/key.txt (or SSH key at /root/.ssh/nixos) to decrypt AI API secrets. age.generateKey = true will create a new key, but it won't match the encrypted secrets — copy gunalx's age key to root's path, or re-encrypt the secrets with root's age public key.

galadriel: kernel 7.0 EOL

Linux 7.0 was removed from nixpkgs (EOL). pkgs.zfs (stable) is now 2.4.2, same version previously pulled from unstable. Switched boot.kernelPackages to the default (6.18) and boot.zfs.package to pkgs.zfs. No pool compatibility concern since ZFS version is unchanged.

legolas: lid-close still killing the NVMe — stale deep + logind suspend

Root cause of the recurring "SSD dies when lid closed": the booted generation carried a duplicate mem_sleep_default=deep after mem_sleep_default=s2idle (last wins), so /sys/power/mem_sleep was s2idle [deep] — every suspend went to S3. The source config only had s2idle; the stale param lived in the old generation. ACPI advertises S3 (supports S0 S3 S4 S5) but S3 is broken for the Phison E21 on this Skylake-era Intel platform, so only s0/s2idle is reliable. Separately, HandleLidSwitch was unset → defaulted to suspend, which was the actual lid-close trigger.

Changes (hosts/legolas/hardware-configuration.nix):

  • services.logind.lidSwitch/lidSwitchExternalPower/lidSwitchDocked = ignore. Lid close no longer suspends; niri's switch-events still locks via noctalia, so the laptop stays on (RAM powered) but can't enter the S3 path.
  • systemd.services.force-s2idle writes s2idle to /sys/power/mem_sleep at boot — guarantees the active mode is s2idle even if a future cmdline carries a stray deep.
  • Suspend (s2idle) remains available via systemctl suspend; hibernation stays disabled.

Also fixed home/niri.nix lid-close command from the undocumented lockScreen lock to the v5-canonical session lock (matching the Mod+M binding).

Verify after rebuild+reboot: /proc/cmdline has no deep, and /sys/power/mem_sleep shows [s2idle] deep.