nixos-config/machines/shinobu/services/router/rules.nft

128 lines
3.8 KiB
Plaintext

define NAT_LAN_IFACES = { "br-lan" }
define NAT_WAN_IFACES = { "wg-upstream" }
define PHYSICAL_WAN = "enp1s0"
define MASQUERADE_IFACES = { $NAT_WAN_IFACES, $PHYSICAL_WAN }
define VUEKO_V4 = 168.119.176.53
define VUEKO_V6 = 2a01:4f8:c012:2f4::1
define VUEKO_PORT = 51820
define WG_UPSTREAM_ENDPOINT = $CFG_wg-upstream_endpoint_address
define PLASTIC_ROUTER_V4 = 192.168.0.1
define VPN_BYPASS_MARK = $CFG_vpnBypassFwMark
table inet filter {
chain forward {
type filter hook forward priority filter; policy drop
# Use MSS clamping
# to avoid too large packets from client on the lan
# not going through the tunnel.
iifname wg-upstream tcp flags syn / syn,rst tcp option maxseg size set rt mtu
oifname wg-upstream tcp flags syn / syn,rst tcp option maxseg size set rt mtu
# allow traffic between lan and wan
iifname $NAT_LAN_IFACES oifname $NAT_WAN_IFACES counter accept
iifname $NAT_WAN_IFACES oifname $NAT_LAN_IFACES ct state established,related counter accept
# accept responses on physical wan
iifname $PHYSICAL_WAN oifname $NAT_LAN_IFACES ct state established,related counter accept
# allow selected destinations via physical wan
# plastic router
iifname $NAT_LAN_IFACES oifname $PHYSICAL_WAN ip daddr $PLASTIC_ROUTER_V4 counter accept
# all destinations configured via policy based routing
oifname $PHYSICAL_WAN mark $VPN_BYPASS_MARK counter accept
}
}
table inet nat {
chain postrouting {
type nat hook postrouting priority filter; policy accept
oifname $MASQUERADE_IFACES masquerade
}
}
# Bypass VPN by setting mark.
# This acts in two places that are handled separatly by nftables:
# Packets from the local host (output hook) and forwared packets (prerouting hook).
# To simplify the handling,
# there is a single chain that handles both,
# which is jumped to from the specific chains.
table inet vpn-bypass {
# This must be of type route, otherwise no route lookup will be performed
chain output {
type route hook output priority mangle
jump common
}
# This does not need to be of type route
chain prerouting {
type filter hook prerouting priority mangle
jump common
}
chain common {
ip daddr $VUEKO_V4 udp dport $VUEKO_PORT mark set $VPN_BYPASS_MARK counter
ip6 daddr $VUEKO_V6 udp dport $VUEKO_PORT mark set $VPN_BYPASS_MARK counter
}
}
# Only allow select connections from and to (physical) wan,
# overriding NixOS firewall in some cases.
table inet restrict-wan {
# Priorities must be higher than filter (0),
# which the NixOS firewall uses.
chain input {
type filter hook input priority -50; policy accept
# accept responses
iifname $PHYSICAL_WAN ct state established,related counter accept
# accept icmpv6
iifname $PHYSICAL_WAN icmpv6 type { nd-neighbor-solicit, nd-router-advert, nd-neighbor-advert } accept
# drop everything else
iifname $PHYSICAL_WAN counter drop
}
# This handles all packets (local and forwarded)
chain postrouting {
type filter hook postrouting priority 0; policy accept
# accept connections to plastic router
oifname $PHYSICAL_WAN ip daddr $PLASTIC_ROUTER_V4 counter accept
# accept icmpv6
oifname $PHYSICAL_WAN icmpv6 type { nd-neighbor-solicit, nd-router-advert, nd-neighbor-advert } accept
# accept connections to selected endpoints
# VPN (wg-upstream)
oifname $PHYSICAL_WAN ip daddr $WG_UPSTREAM_ENDPOINT counter accept # only this is used
# destinations configured in VPN bypass
oifname $PHYSICAL_WAN mark $VPN_BYPASS_MARK counter accept
# drop all other packets
oifname $PHYSICAL_WAN counter drop
}
}
# Tracing infrastructure, can be used for debugging (nft monitor trace)
table inet trace {
chain prerouting {
type filter hook prerouting priority raw - 1
jump common
}
chain output {
type filter hook output priority raw - 1
jump common
}
chain common {
# Add tracing rule here
# … meta nftrace set 1
# DO NOT COMMIT ANY TRACING RULES
}
}