## Firewall ## ======== ## ## Provides a service to create an nftables ruleset based on ## configuration supplied to it. { lib, pkgs, config, ...}: let inherit (lib) mkOption types; inherit (pkgs) liminix; inherit (pkgs.liminix.services) oneshot; kconf = isModule : # setting isModule false is utterly untested and mostly # unimplemented: I say this to preempt any "how on earth is this # even supposed to work?" questions let yes = if isModule then "m" else "y"; in { NFT_FIB_IPV4 = yes; NFT_FIB_IPV6 = yes; NF_TABLES = yes; NF_CT_PROTO_DCCP = "y"; NF_CT_PROTO_SCTP = "y"; NF_CT_PROTO_UDPLITE = "y"; # NF_CONNTRACK_FTP = yes; NFT_CT = yes; }; kmodules = pkgs.kernel-modules.override { kernelSrc = config.system.outputs.kernel.src; modulesupport = config.system.outputs.kernel.modulesupport; targets = [ "nft_fib_ipv4" "nft_fib_ipv6" ]; kconfig = kconf true; }; loadModules = oneshot { name = "firewall-modules"; up = "sh ${kmodules}/load.sh"; down = "sh ${kmodules}/unload.sh"; }; in { options = { system.service.firewall = mkOption { type = liminix.lib.types.serviceDefn; }; }; config = { system.service.firewall = let svc = liminix.callService ./service.nix { ruleset = mkOption { type = types.attrsOf types.attrs; # we could usefully tighten this a bit :-) description = "firewall ruleset"; }; }; in svc // { build = args : (svc.build args) // { dependencies = [ loadModules ] ++ (svc.dependencies or []); }; }; # For historical reasons the kernel config is split between # monolithic options and modules. TODO: go through this list # and see what can be moved into the "kconf" definiton above kernel.config = { NETFILTER_XT_MATCH_CONNTRACK = "y"; IP6_NF_IPTABLES= "y"; IP_NF_IPTABLES= "y"; IP_NF_NAT = "y"; IP_NF_TARGET_MASQUERADE = "y"; NETFILTER = "y"; NETFILTER_ADVANCED = "y"; NETFILTER_XTABLES = "y"; NFT_COMPAT = "y"; NFT_CT = "y"; NFT_LOG = "y"; NFT_MASQ = "y"; NFT_NAT = "y"; NFT_REJECT = "y"; NFT_REJECT_INET = "y"; NF_CONNTRACK = "y"; NF_NAT = "y"; NF_NAT_MASQUERADE = "y"; NF_TABLES= "y"; NF_TABLES_INET = "y"; NF_TABLES_IPV4 = "y"; NF_TABLES_IPV6 = "y"; }; }; }