-
Notifications
You must be signed in to change notification settings - Fork 0
/
hardening.nix
68 lines (60 loc) · 2.25 KB
/
hardening.nix
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
{ config, pkgs, lib, ... }:
with lib;
let
optionsPerService = let
mkFlag = description: mkOption {
inherit description;
type = types.bool;
default = false;
};
in {
allowUnixDomainSockets = mkFlag "allow service to use AF_UNIX sockets";
allowInternetAccess = mkFlag "allow service to use AF_INET/AF_INET6 sockets";
allowWriteAccessTo = mkOption {
description = "List of paths that shall be mounted read-write (instead of read-only). If you use serviceConfig.{RuntimeDirectory,StateDirectory,CacheDirectory,LogsDirectory,ConfigurationDirectory}, those paths do not need to be mentioned again here.";
type = types.listOf types.str;
default = [];
};
};
toSystemdServiceConfig = serviceName: opts: {
serviceConfig = {
LockPersonality = true;
MemoryDenyWriteExecute = true;
NoNewPrivileges = true;
PrivateDevices = true;
PrivateTmp = true;
ProtectControlGroups = true;
ProtectHome = true;
ProtectHostname = true;
ProtectKernelLogs = true;
ProtectKernelModules = true;
ProtectKernelTunables = true;
ProtectSystem = "strict";
RemoveIPC = true;
ReadWritePaths = concatStringsSep " " opts.allowWriteAccessTo;
RestrictAddressFamilies = (
(optional opts.allowUnixDomainSockets "AF_UNIX")
++
(optional opts.allowInternetAccess "AF_INET")
++
(optional opts.allowInternetAccess "AF_INET6")
);
RestrictNamespaces = true;
RestrictRealtime = true;
RestrictSUIDSGID = true;
SystemCallArchitectures = "native";
SystemCallErrorNumber = "EPERM";
SystemCallFilter = "@system-service";
};
};
in {
options.my.hardening = mkOption {
description = "Which services to apply auto-hardening to. Each service mentioned in this attrset is, by default, restricted to a conservative set of syscalls (file IO, network IO, setuid/setgid etc.) that is useful for most network services, but does not allow tampering with the system configuration.";
example = {
gitea = { };
};
default = {};
type = with types; attrsOf (submodule { options = optionsPerService; });
};
config.systemd.services = mapAttrs toSystemdServiceConfig config.my.hardening;
}