Skip to content

Commit

Permalink
feat(user accounts): new ghaf user account setup
Browse files Browse the repository at this point in the history
  - introducing userborn
  - disabling mutable users
  - re-factoring ghaf account to admin account
  - introducing login user account with homed + auxiliary accounts

  - impermanence flake input pinned to userborn patch
  - /etc/machine-id (gui-vm) is currently hardcoded as login user identity file depends on it.
    It should be generated on first boot and persistet. Workaround is available upstream (after
    userborn patch) in impermanence but does not seem to work with our setup, investigation required
  - minor issues with login: wrong password results in multiple
    attempts, if fprint enabled user needs to first click login

Signed-off-by: Manuel Bluhm <[email protected]>
  • Loading branch information
mbssrc committed Dec 11, 2024
1 parent 7c10e3a commit bb60176
Show file tree
Hide file tree
Showing 39 changed files with 822 additions and 331 deletions.
7 changes: 4 additions & 3 deletions flake.lock

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

2 changes: 1 addition & 1 deletion flake.nix
Original file line number Diff line number Diff line change
Expand Up @@ -140,7 +140,7 @@
};

impermanence = {
url = "github:nix-community/impermanence";
url = "github:nix-community/impermanence/32b1094d28d5fbedcc85a403bc08c8877b396255";
};

givc = {
Expand Down
2 changes: 1 addition & 1 deletion modules/common/default.nix
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,7 @@
./firewall
./profiles
./security
./users/accounts.nix
./users
./version
./virtualization/docker.nix
./systemd
Expand Down
1 change: 0 additions & 1 deletion modules/common/profiles/debug.nix
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,6 @@ in
config = lib.mkIf cfg.enable {
# Enable default accounts and passwords
ghaf = {
users.accounts.enable = true;
# Enable development on target
development = {
nix-setup.enable = true;
Expand Down
2 changes: 1 addition & 1 deletion modules/common/profiles/release.nix
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,6 @@ in
# TODO this needs to be refined when we define a policy for the
# processes and the UID/groups that should be enabled by default
# if not already covered by systemd
ghaf.users.accounts.enable = true;
# ghaf.users.admin.enable = true;
};
}
7 changes: 0 additions & 7 deletions modules/common/services/audio.nix
Original file line number Diff line number Diff line change
Expand Up @@ -81,13 +81,6 @@ in
};
};

# Allow ghaf user to access pulseaudio and pipewire
users.extraUsers.ghaf.extraGroups = [
"audio"
"video"
"pipewire"
];

# Start pipewire on system boot
systemd.services.pipewire.wantedBy = [ "multi-user.target" ];

Expand Down
23 changes: 2 additions & 21 deletions modules/common/services/fprint.nix
Original file line number Diff line number Diff line change
Expand Up @@ -46,38 +46,19 @@ in
// Allow user to verify fingerprints
polkit.addRule(function(action, subject) {
if (action.id == "net.reactivated.fprint.device.verify" &&
subject.user == "ghaf") {
subject.isInGroup ("users")) {
return polkit.Result.YES;
}
});
// Allow user to enroll fingerprints
polkit.addRule(function(action, subject) {
if (action.id == "net.reactivated.fprint.device.enroll" &&
subject.user == "ghaf") {
subject.isInGroup ("users")) {
return polkit.Result.YES;
}
});
'';
};
# PAM rules for swaylock fingerprint reader
pam.services = {
swaylock.text = ''
# Account management.
account required pam_unix.so
# Authentication management.
auth sufficient pam_unix.so likeauth try_first_pass
auth sufficient ${pkgs.fprintd}/lib/security/pam_fprintd.so
auth required pam_deny.so
# Password management.
password sufficient pam_unix.so nullok sha512
# Session management.
session required pam_env.so conffile=/etc/pam/environment readenv=0
session required pam_unix.so
'';
};
};
};
}
4 changes: 1 addition & 3 deletions modules/common/services/xdgopener.nix
Original file line number Diff line number Diff line change
Expand Up @@ -22,6 +22,7 @@ let
# into all targets
ghaf-xdg-open = pkgs.callPackage ../../../packages/ghaf-xdg-open {
inherit (config.ghaf.security.sshKeys) sshKeyPath;
user = config.ghaf.users.appUser.name;
};
in
{
Expand Down Expand Up @@ -51,9 +52,6 @@ in
services."xdg@" = {
description = "XDG opener";
serviceConfig = {
# The user 'ghaf' is used here to access SSH keys for the scp command
# This is required to copy files to the zathuravm
User = "ghaf";
ExecStart = "${ghaf-xdg-open}/bin/ghaf-xdg-open";
StandardInput = "socket";
StandardOutput = "journal";
Expand Down
10 changes: 9 additions & 1 deletion modules/common/systemd/base.nix
Original file line number Diff line number Diff line change
Expand Up @@ -30,10 +30,11 @@ let
inherit (cfg) withAudit;
withCompression = true;
withCoredump = cfg.withDebug || cfg.withMachines;
inherit (cfg) withCryptsetup;
withCryptsetup = cfg.withCryptsetup || cfg.withHomed;
inherit (cfg) withEfi;
inherit (cfg) withBootloader;
inherit (cfg) withFido2;
inherit (cfg) withHomed;
inherit (cfg) withHostnamed;
withImportd = cfg.withMachines;
withKexectools = cfg.withDebug;
Expand All @@ -55,6 +56,7 @@ let
inherit (cfg) withTimesyncd;
inherit (cfg) withTpm2Tss;
inherit (cfg) withUkify;
withUserDb = cfg.withHomed;
withUtmp = cfg.withJournal || cfg.withAudit;
}
// lib.optionalAttrs (lib.strings.versionAtLeast pkgs.systemdMinimal.version "255.0") {
Expand Down Expand Up @@ -230,6 +232,12 @@ in
default = false;
};

withHomed = mkOption {
description = "Enable systemd homed for users home functionality.";
type = types.bool;
default = false;
};

withHostnamed = mkOption {
description = "Enable systemd hostname daemon.";
type = types.bool;
Expand Down
66 changes: 0 additions & 66 deletions modules/common/users/accounts.nix

This file was deleted.

100 changes: 100 additions & 0 deletions modules/common/users/admin.nix
Original file line number Diff line number Diff line change
@@ -0,0 +1,100 @@
# Copyright 2022-2024 TII (SSRC) and the Ghaf contributors
# SPDX-License-Identifier: Apache-2.0
{
config,
lib,
...
}:
let
cfg = config.ghaf.users.admin;
inherit (lib)
mkIf
types
mkOption
optionals
;
in
{
options.ghaf.users.admin = {
enable = mkOption {
description = "Enable the admin user account. Enabled by default.";
type = types.bool;
default = true;
};
name = mkOption {
description = "Admin account name. Defaults to 'ghaf'.";
type = types.str;
default = "ghaf";
};
initialPassword = mkOption {
description = "Default password for the admin user account.";
type = types.nullOr types.str;
default = "ghaf";
};
initialHashedPassword = mkOption {
description = "Initial hashed password for the admin user account.";
type = types.nullOr types.str;
default = null;
};
hashedPassword = mkOption {
description = "Hashed password for live updates.";
type = types.nullOr types.str;
default = null;
};
extraGroups = mkOption {
description = "Extra groups for the admin user.";
type = types.listOf types.str;
default = [ ];
};
};

config = mkIf cfg.enable {

# Assertions
assertions = [
{
assertion =
(cfg.initialPassword != null)
|| (cfg.initialHashedPassword != null)
|| (cfg.hashedPassword != null);
message = ''
No password set for the admin account. Please set one of the following options:
- initialPassword
- initialHashedPassword
- hashedPassword
to allow admin login.
'';
}
];

users = {
users = {
"${cfg.name}" = {
isNormalUser = true;
inherit (cfg) initialPassword;
inherit (cfg) initialHashedPassword;
inherit (cfg) hashedPassword;
createHome = false;
home = "/var/empty";
extraGroups =
[
"wheel"
"video"
]
++ cfg.extraGroups
++ optionals config.security.tpm2.enable [ "tss" ]
++ optionals config.ghaf.virtualization.docker.daemon.enable [ "docker" ];
};
};
groups = {
"${cfg.name}" = {
inherit (cfg) name;
members = [ cfg.name ];
};
};
};

# to build ghaf as admin with caches
nix.settings.trusted-users = mkIf config.ghaf.profiles.debug.enable [ cfg.name ];
};
}
25 changes: 25 additions & 0 deletions modules/common/users/common.nix
Original file line number Diff line number Diff line change
@@ -0,0 +1,25 @@
# Copyright 2022-2024 TII (SSRC) and the Ghaf contributors
# SPDX-License-Identifier: Apache-2.0
{
config,
lib,
...
}:
let
inherit (lib) mkDefault hasAttr;
hasStorageVm = (hasAttr "storagevm" config.ghaf) && config.ghaf.storagevm.enable;
in
{
# Common ghaf user settings
config = {

# Disable mutable users
users.mutableUsers = mkDefault false;

# Enable userborn
services.userborn = {
enable = mkDefault true;
passwordFilesLocation = if hasStorageVm then "/var/lib/nixos" else "/etc";
};
};
}
10 changes: 10 additions & 0 deletions modules/common/users/default.nix
Original file line number Diff line number Diff line change
@@ -0,0 +1,10 @@
# Copyright 2024 TII (SSRC) and the Ghaf contributors
# SPDX-License-Identifier: Apache-2.0
{
imports = [
./common.nix
./admin.nix
./desktop.nix
./managed.nix
];
}
Loading

0 comments on commit bb60176

Please sign in to comment.