nix: get nftables from correct parent attr

nix: what do you mean `baseNameOf` is not in lib

nix: `pkgs.system` -> `pkgs.hostPlatform.system`

nix: include contrib in pacakge source

nix: fix types
This commit is contained in:
raf 2025-05-01 06:07:09 +03:00
commit bc21bfc506
Signed by: NotAShelf
GPG key ID: 29D95B64378DB4BF
2 changed files with 46 additions and 57 deletions

View file

@ -5,6 +5,7 @@ self: {
pkgs, pkgs,
... ...
}: let }: let
inherit (builtins) toJSON toString;
inherit (lib.modules) mkIf; inherit (lib.modules) mkIf;
inherit (lib.options) mkOption mkEnableOption literalExpression; inherit (lib.options) mkOption mkEnableOption literalExpression;
inherit (lib.types) package str port int listOf enum bool attrsOf path; inherit (lib.types) package str port int listOf enum bool attrsOf path;
@ -13,7 +14,7 @@ self: {
cfg = config.services.eris; cfg = config.services.eris;
# Generate the config.json content # Generate the config.json content
erisConfigFile = pkgs.writeText "eris-config.json" (builtins.toJSON { erisConfigFile = pkgs.writeText "eris-config.json" (toJSON {
listen_addr = cfg.listenAddress; listen_addr = cfg.listenAddress;
metrics_port = cfg.metricsPort; metrics_port = cfg.metricsPort;
backend_addr = cfg.backendAddress; backend_addr = cfg.backendAddress;
@ -37,8 +38,8 @@ in {
package = mkOption { package = mkOption {
type = package; type = package;
default = self.packages.${pkgs.system}.eris; default = self.packages.${pkgs.stdenv.system}.eris;
defaultText = literalExpression "pkgs.eris"; defaultText = literalExpression "self.packages.\${pkgs.stdenv.system}.eris";
description = "The Eris package to use."; description = "The Eris package to use.";
}; };
@ -52,6 +53,7 @@ in {
metricsPort = mkOption { metricsPort = mkOption {
type = port; type = port;
default = 9100; default = 9100;
example = 9110;
description = "The port for the Prometheus metrics endpoint."; description = "The port for the Prometheus metrics endpoint.";
}; };
@ -65,13 +67,13 @@ in {
minDelay = mkOption { minDelay = mkOption {
type = int; type = int;
default = 1000; default = 1000;
description = "Minimum delay (in milliseconds) between sending characters in tarpit mode."; description = "Minimum delay (in ms) between sending characters in tarpit mode.";
}; };
maxDelay = mkOption { maxDelay = mkOption {
type = int; type = int;
default = 15000; default = 15000;
description = "Maximum delay (in milliseconds) between sending characters in tarpit mode."; description = "Maximum delay (in ms) between sending characters in tarpit mode.";
}; };
maxTarpitTime = mkOption { maxTarpitTime = mkOption {
@ -153,7 +155,7 @@ in {
dataDir = mkOption { dataDir = mkOption {
# This derives from stateDir by default to keep persistent data together # This derives from stateDir by default to keep persistent data together
type = path; type = path;
default = "${cfg.stateDir}/data"; default = "/var/lib/eris/data";
description = "Directory containing `corpora` and `scripts` subdirectories."; description = "Directory containing `corpora` and `scripts` subdirectories.";
}; };
@ -179,7 +181,7 @@ in {
An attribute set where keys are Lua script filenames (e.g., "`my_script.lua`") An attribute set where keys are Lua script filenames (e.g., "`my_script.lua`")
and values are paths to the script files. These will be placed in {path}`''${cfg.dataDir}/scripts`. and values are paths to the script files. These will be placed in {path}`''${cfg.dataDir}/scripts`.
''; '';
example = lib.literalExpression '' example = literalExpression ''
{ {
"custom_tokens.lua" = ./custom_tokens.lua; "custom_tokens.lua" = ./custom_tokens.lua;
} }
@ -216,7 +218,7 @@ in {
}; };
config = mkIf cfg.enable { config = mkIf cfg.enable {
services.nftables = { networking.nftables = {
enable = mkIf cfg.nftablesIntegration cfg.nftablesIntegration; enable = mkIf cfg.nftablesIntegration cfg.nftablesIntegration;
ruleset = mkIf cfg.nftablesIntegration '' ruleset = mkIf cfg.nftablesIntegration ''
table inet filter { table inet filter {
@ -224,7 +226,7 @@ in {
type ipv4_addr; flags interval; comment "Managed by Eris NixOS module"; type ipv4_addr; flags interval; comment "Managed by Eris NixOS module";
} }
chain input { chain INPUT {
${lib.optionalString cfg.nftablesDropRule '' ${lib.optionalString cfg.nftablesDropRule ''
ip saddr @eris_blacklist counter drop comment "Drop traffic from Eris blacklist"; ip saddr @eris_blacklist counter drop comment "Drop traffic from Eris blacklist";
''} ''}
@ -248,8 +250,8 @@ in {
systemd.services.eris = { systemd.services.eris = {
description = "Eris Tarpit Service"; description = "Eris Tarpit Service";
wantedBy = ["multi-user.target"]; wantedBy = ["multi-user.target"];
after = ["network.target"] ++ optionals cfg.nftablesIntegration "nftables.service"; after = ["network.target"] ++ (optionals cfg.nftablesIntegration ["nftables.service"]);
requires = optionals cfg.nftablesIntegration "nftables.service"; requires = optionals cfg.nftablesIntegration ["nftables.service"];
serviceConfig = { serviceConfig = {
# User and Group configuration # User and Group configuration
@ -258,7 +260,7 @@ in {
# Process management # Process management
ExecStart = '' ExecStart = ''
${cfg.package}/bin/eris \ ${lib.getExe cfg.package} \
--config-file ${erisConfigFile} \ --config-file ${erisConfigFile} \
--log-level ${cfg.logLevel} --log-level ${cfg.logLevel}
''; '';
@ -274,27 +276,29 @@ in {
# Deny privilege escalation # Deny privilege escalation
NoNewPrivileges = true; NoNewPrivileges = true;
# FIXME: this breaks everything.
# Filesystem access control # Filesystem access control
ProtectSystem = "strict"; # Mount /usr, /boot, /etc read-only # ProtectSystem = "strict"; # Mount /usr, /boot, /etc read-only
ProtectHome = true; # Make /home, /root inaccessible # ProtectHome = true; # Make /home, /root inaccessible
#
# Explicitly allow writes to state/cache/data dirs # # Explicitly allow writes to state/cache/data dirs
ReadWritePaths = [ # ReadWritePaths = [
cfg.stateDir # "/var/lib/eris"
cfg.cacheDir # "${cfg.stateDir}"
cfg.dataDir # "${cfg.cacheDir}"
]; # "${cfg.dataDir}"
# ];
# Allow reads from config file path #
ReadOnlyPaths = [erisConfigFile]; # # Allow reads from config file path
# ReadOnlyPaths = ["${erisConfigFile}"];
# Explicitly deny access to sensitive paths #
InaccessiblePaths = [ # # Explicitly deny access to sensitive paths
"/boot" # InaccessiblePaths = [
"/root" # "/boot"
"/home" # "/root"
"/srv" # Add others as needed # "/home"
]; # "/srv"
# ];
PrivateTmp = true; # Use private /tmp and /var/tmp PrivateTmp = true; # Use private /tmp and /var/tmp
PrivateDevices = true; # Restrict device access (/dev) PrivateDevices = true; # Restrict device access (/dev)
@ -306,17 +310,14 @@ in {
ProtectControlGroups = true; # Make Control Group hierarchies read-only ProtectControlGroups = true; # Make Control Group hierarchies read-only
# Network access control # Network access control
RestrictAddressFamilies = ["AF_INET" "AF_INET6"]; # Allow only standard IP protocols RestrictAddressFamilies = ["AF_INET" "AF_INET6"];
CapabilityBoundingSet = ["CAP_NET_BIND_SERVICE"]; # Allow binding to ports < 1024 if needed
CapabilityBoundingSet = ["CAP_NET_BIND_SERVICE"];
AmbientCapabilities = ["CAP_NET_BIND_SERVICE"]; AmbientCapabilities = ["CAP_NET_BIND_SERVICE"];
# System call filtering (adjust based on Eris's needs)
# Start with a reasonable baseline for network services # Start with a reasonable baseline for network services
SystemCallFilter = ["@system-service" "@network-io" "@file-system"]; SystemCallFilter = ["@system-service" "@network-io" "@file-system"];
# TODO: Consider adding more specific filters or removing groups if issues arise
# e.g., SystemCallArchitectures=native. This probably will not be enough
# Other hardening # Other hardening
RestrictNamespaces = true; # Prevent creation of new namespaces RestrictNamespaces = true; # Prevent creation of new namespaces
LockPersonality = true; # Lock down legacy personality settings LockPersonality = true; # Lock down legacy personality settings
@ -326,8 +327,8 @@ in {
RestrictSUIDSGID = true; # Ignore SUID/SGID bits on execution RestrictSUIDSGID = true; # Ignore SUID/SGID bits on execution
# Directories managed by systemd # Directories managed by systemd
StateDirectory = lib.baseNameOf cfg.stateDir; # e.g., "eris" StateDirectory = "eris";
CacheDirectory = lib.baseNameOf cfg.cacheDir; # e.g., "eris" CacheDirectory = "eris";
StateDirectoryMode = "0750"; StateDirectoryMode = "0750";
CacheDirectoryMode = "0750"; CacheDirectoryMode = "0750";
@ -340,13 +341,11 @@ in {
preStart = let preStart = let
corporaDir = "${cfg.dataDir}/corpora"; corporaDir = "${cfg.dataDir}/corpora";
scriptsDir = "${cfg.dataDir}/scripts"; scriptsDir = "${cfg.dataDir}/scripts";
chownCmd = "${pkgs.coreutils}/bin/chown ${cfg.user}:${cfg.group}";
# Create commands to copy corpora files # Create commands to copy corpora files
copyCorporaCmds = copyCorporaCmds =
lib.mapAttrsToList (name: path: '' lib.mapAttrsToList (name: path: ''
cp -vf ${path} ${corporaDir}/${name} cp -vf ${path} ${corporaDir}/${name}
${chownCmd} ${corporaDir}/${name}
'') '')
cfg.corpora; cfg.corpora;
@ -354,23 +353,12 @@ in {
copyLuaScriptCmds = copyLuaScriptCmds =
lib.mapAttrsToList (name: path: '' lib.mapAttrsToList (name: path: ''
cp -vf ${path} ${scriptsDir}/${name} cp -vf ${path} ${scriptsDir}/${name}
${chownCmd} ${scriptsDir}/${name}
'') '')
cfg.luaScripts; cfg.luaScripts;
in '' in ''
# Systemd creates StateDirectory and CacheDirectory, but we need subdirs
mkdir -p ${cfg.stateDir}/conf ${cfg.dataDir} ${corporaDir} ${scriptsDir}
# Ensure ownership is correct for all relevant dirs managed by systemd or created here
${chownCmd} /var/lib/${lib.baseNameOf cfg.stateDir} \
/var/cache/${lib.baseNameOf cfg.cacheDir} \
${cfg.stateDir}/conf \
${cfg.dataDir} \
${corporaDir} \
${scriptsDir}
# Copy declarative files # Copy declarative files
${lib.toString copyCorporaCmds} ${lib.optionalString (cfg.corpora != {}) (toString copyCorporaCmds)}
${lib.toString copyLuaScriptCmds} ${lib.optionalString (cfg.luaScripts != {}) (toString copyLuaScriptCmds)}
''; '';
}; };
}; };

View file

@ -18,6 +18,7 @@ in
root = s; root = s;
fileset = fs.unions [ fileset = fs.unions [
(fs.fileFilter (file: builtins.any file.hasExt ["rs"]) (s + /src)) (fs.fileFilter (file: builtins.any file.hasExt ["rs"]) (s + /src))
(s + /contrib)
lockfile lockfile
cargoToml cargoToml
]; ];
@ -25,8 +26,8 @@ in
postInstall = '' postInstall = ''
mkdir -p $out/share/contrib mkdir -p $out/share/contrib
cp -r ${../contrib}/corpus $out/share/contrib/ cp -rv $src/contrib/corpus $out/share/contrib
cp -r ${../contrib}/lua $out/share/contrib/ cp -rv $src/contrib/lua $out/share/contrib
''; '';
cargoLock.lockFile = lockfile; cargoLock.lockFile = lockfile;