From f3648de497a8dd75b83988cd3009e4e8e64e6db4 Mon Sep 17 00:00:00 2001 From: Philip Taron Date: Wed, 1 Apr 2026 13:51:33 -0700 Subject: [PATCH] polkit: fix polkit-agent-helper@ sandbox for pam_u2f polkit 127 switched to socket activation with a systemd unit for polkit-agent-helper that uses PrivateDevices=yes and ProtectHome=yes. This breaks pam_u2f (and potentially other PAM modules that interact with hardware), because: - PrivateDevices=yes creates a private /dev without hidraw devices, so FIDO tokens are inaccessible - ProtectHome=yes blocks reading ~/.config/Yubico/u2f_keys - StandardError=inherit causes polkit agents to misinterpret PAM diagnostic output as protocol errors, resulting in tight re-execution loops Fix by overriding these properties in the polkit module: - StandardError=journal unconditionally (benefits all PAM modules) - PrivateDevices/DeviceAllow/ProtectHome when pam_u2f is enabled Co-authored-by: Victor Luft --- nixos/modules/security/polkit.nix | 22 ++++++++++++++++++++++ 1 file changed, 22 insertions(+) diff --git a/nixos/modules/security/polkit.nix b/nixos/modules/security/polkit.nix index ca0a88246528..d4a99ba8a7b6 100644 --- a/nixos/modules/security/polkit.nix +++ b/nixos/modules/security/polkit.nix @@ -80,6 +80,28 @@ in systemd.sockets."polkit-agent-helper".wantedBy = [ "sockets.target" ]; + systemd.services."polkit-agent-helper@".serviceConfig = lib.mkMerge [ + # The upstream unit inherits stderr to the polkit agent, which causes + # agent processes to misinterpret diagnostic output from PAM modules + # as protocol errors, resulting in tight re-execution loops. + { StandardError = "journal"; } + + # The upstream unit uses PrivateDevices=yes and ProtectHome=yes, + # which prevents PAM modules from accessing hardware (e.g. FIDO + # tokens via /dev/hidraw*) or reading key files from home directories. + (lib.mkIf config.security.pam.u2f.enable { + # Override upstream PrivateDevices=yes to allow access to /dev/hidraw* + PrivateDevices = false; + DeviceAllow = [ + "/dev/urandom r" + "char-hidraw rw" + ]; + # Override upstream ProtectHome=yes so pam_u2f can read + # ~/.config/Yubico/u2f_keys (the default key file location) + ProtectHome = "read-only"; + }) + ]; + # The polkit daemon reads action/rule files environment.pathsToLink = [ "/share/polkit-1" ];