router: add sit tunnel option
This commit is contained in:
parent
0cc911f974
commit
d40bdb7415
|
@ -510,11 +510,11 @@
|
||||||
]
|
]
|
||||||
},
|
},
|
||||||
"locked": {
|
"locked": {
|
||||||
"lastModified": 1718217962,
|
"lastModified": 1720021052,
|
||||||
"narHash": "sha256-bVKwJdVeo6wMN6xMOFx3Um3x7ebijyCG5iGCIXAtDXA=",
|
"narHash": "sha256-tu8IQn8Kj7S0xRg0L2ej7S65FzXqSX7LI7M2pbLdQJU=",
|
||||||
"owner": "chayleaf",
|
"owner": "chayleaf",
|
||||||
"repo": "nixos-router",
|
"repo": "nixos-router",
|
||||||
"rev": "f25509e55a06f1dfa089556b28b9402c13e18aa4",
|
"rev": "4c132c4c5fc09b3c3317b960ec1533c4a5ebe41f",
|
||||||
"type": "github"
|
"type": "github"
|
||||||
},
|
},
|
||||||
"original": {
|
"original": {
|
||||||
|
|
|
@ -86,7 +86,7 @@
|
||||||
if dev.${name} or false then
|
if dev.${name} or false then
|
||||||
(if input._type or null == "flake"
|
(if input._type or null == "flake"
|
||||||
then let inputs = input.inputs // { self = (import /${devPath}/${name}/flake.nix).outputs inputs; };
|
then let inputs = input.inputs // { self = (import /${devPath}/${name}/flake.nix).outputs inputs; };
|
||||||
in { __toString = _: "/${devPath}/${name}"; } // inputs.self
|
in { __toString = _: "/${toString devPath}/${name}"; } // inputs.self
|
||||||
else /${devPath}/${name})
|
else /${devPath}/${name})
|
||||||
else input)
|
else input)
|
||||||
base-inputs;
|
base-inputs;
|
||||||
|
|
|
@ -414,6 +414,21 @@ in {
|
||||||
};
|
};
|
||||||
*/
|
*/
|
||||||
# ethernet wan
|
# ethernet wan
|
||||||
|
router.tunnels.sittun0 = lib.mkIf (cfg.vpn.tunnel.mode == "sit") {
|
||||||
|
mode = "sit";
|
||||||
|
remote = cfg.vpn.tunnel.ip;
|
||||||
|
local = cfg.vpn.tunnel.localIp;
|
||||||
|
ttl = 255;
|
||||||
|
};
|
||||||
|
router.interfaces.sittun0 = lib.mkIf (cfg.vpn.tunnel.mode == "sit") {
|
||||||
|
dependentServices = [
|
||||||
|
(lib.mkIf cfg.vpn.wireguard.enable { service = "wireguard-${vpn_iface}"; inNetns = false; })
|
||||||
|
(lib.mkIf cfg.vpn.openvpn.enable { service = "openvpn-client"; inNetns = false; })
|
||||||
|
];
|
||||||
|
ipv6.addresses = [ (router-lib.parseCidr cfg.vpn.tunnel.ifaceAddr) ];
|
||||||
|
ipv6.routes = [ { extraArgs = [ "::/0" "dev" "sittun0" ]; } ];
|
||||||
|
networkNamespace = "wan";
|
||||||
|
};
|
||||||
router.interfaces.wan = {
|
router.interfaces.wan = {
|
||||||
dependentServices = [
|
dependentServices = [
|
||||||
(lib.mkIf cfg.vpn.wireguard.enable { service = "wireguard-${vpn_iface}"; inNetns = false; })
|
(lib.mkIf cfg.vpn.wireguard.enable { service = "wireguard-${vpn_iface}"; inNetns = false; })
|
||||||
|
@ -703,11 +718,13 @@ in {
|
||||||
};
|
};
|
||||||
router.networkNamespaces.wan = {
|
router.networkNamespaces.wan = {
|
||||||
# this is the even more boring nftables config
|
# this is the even more boring nftables config
|
||||||
nftables.jsonRules = mkRules {
|
nftables.jsonRules = let
|
||||||
|
wans = [ "wan" ] ++ lib.optional (cfg.vpn.tunnel.mode == "sit") "sittun0";
|
||||||
|
in mkRules {
|
||||||
selfIp4 = netAddresses.netnsWan4;
|
selfIp4 = netAddresses.netnsWan4;
|
||||||
selfIp6 = netAddresses.netnsWan6;
|
selfIp6 = netAddresses.netnsWan6;
|
||||||
|
inherit wans;
|
||||||
lans = [ "veth-wan-b" ];
|
lans = [ "veth-wan-b" ];
|
||||||
wans = [ "wan" ];
|
|
||||||
netdevIngressWanRules = with notnft.dsl; with payload; [
|
netdevIngressWanRules = with notnft.dsl; with payload; [
|
||||||
[(is.eq (fib (f: with f; [ saddr mark iif ]) (f: f.oif)) missing) (log "wan oif missing ") drop]
|
[(is.eq (fib (f: with f; [ saddr mark iif ]) (f: f.oif)) missing) (log "wan oif missing ") drop]
|
||||||
];
|
];
|
||||||
|
@ -718,10 +735,10 @@ in {
|
||||||
rule4 = rule.target4; rule6 = rule.target6;
|
rule4 = rule.target4; rule6 = rule.target6;
|
||||||
in with notnft.dsl; with payload;
|
in with notnft.dsl; with payload;
|
||||||
lib.optionals (rule4 != null) [
|
lib.optionals (rule4 != null) [
|
||||||
[ (is.eq meta.iifname "wan") (is.eq ip.protocol protocols) (is.eq th.dport rule.port)
|
[ (is.eq meta.iifname (setIfNeeded wans)) (is.eq ip.protocol protocols) (is.eq th.dport rule.port)
|
||||||
(if rule4.port == null then dnat.ip rule4.address else dnat.ip rule4.address rule4.port) ]
|
(if rule4.port == null then dnat.ip rule4.address else dnat.ip rule4.address rule4.port) ]
|
||||||
] ++ lib.optionals (rule6 != null) [
|
] ++ lib.optionals (rule6 != null) [
|
||||||
[ (is.eq meta.iifname "wan") (is.eq ip6.nexthdr protocols) (is.eq th.dport rule.port)
|
[ (is.eq meta.iifname (setIfNeeded wans)) (is.eq ip6.nexthdr protocols) (is.eq th.dport rule.port)
|
||||||
(if rule6.port == null then dnat.ip6 rule6.address else dnat.ip6 rule6.address rule6.port) ]
|
(if rule6.port == null then dnat.ip6 rule6.address else dnat.ip6 rule6.address rule6.port) ]
|
||||||
])
|
])
|
||||||
(builtins.filter (x: !x.inVpn && (x.tcp || x.udp)) cfg.dnatRules));
|
(builtins.filter (x: !x.inVpn && (x.tcp || x.udp)) cfg.dnatRules));
|
||||||
|
@ -734,10 +751,10 @@ in {
|
||||||
rule4 = rule.target4; rule6 = rule.target6;
|
rule4 = rule.target4; rule6 = rule.target6;
|
||||||
in with notnft.dsl; with payload;
|
in with notnft.dsl; with payload;
|
||||||
lib.optionals (rule4 != null) [
|
lib.optionals (rule4 != null) [
|
||||||
[ (is.eq meta.iifname "wan") (is.eq meta.oifname "veth-wan-b") (is.eq ip.protocol protocols)
|
[ (is.eq meta.iifname (setIfNeeded wans)) (is.eq meta.oifname "veth-wan-b") (is.eq ip.protocol protocols)
|
||||||
(is.eq th.dport (if rule4.port != null then rule4.port else rule.port)) (is.eq ip.daddr rule4.address) masquerade ]
|
(is.eq th.dport (if rule4.port != null then rule4.port else rule.port)) (is.eq ip.daddr rule4.address) masquerade ]
|
||||||
] ++ lib.optionals (rule6 != null) [
|
] ++ lib.optionals (rule6 != null) [
|
||||||
[ (is.eq meta.iifname "wan") (is.eq meta.oifname "veth-wan-b") (is.eq ip6.nexthdr protocols)
|
[ (is.eq meta.iifname (setIfNeeded wans)) (is.eq meta.oifname "veth-wan-b") (is.eq ip6.nexthdr protocols)
|
||||||
(is.eq th.dport (if rule6.port != null then rule6.port else rule.port)) (is.eq ip6.daddr rule6.address) masquerade ]
|
(is.eq th.dport (if rule6.port != null then rule6.port else rule.port)) (is.eq ip6.daddr rule6.address) masquerade ]
|
||||||
])
|
])
|
||||||
(builtins.filter (x: !x.inVpn && (x.tcp || x.udp) && dnatRuleMode x == "snat") cfg.dnatRules));
|
(builtins.filter (x: !x.inVpn && (x.tcp || x.udp) && dnatRuleMode x == "snat") cfg.dnatRules));
|
||||||
|
@ -764,12 +781,13 @@ in {
|
||||||
|
|
||||||
# vpn socket is in wan namespace, meaning traffic gets sent through the wan namespace
|
# vpn socket is in wan namespace, meaning traffic gets sent through the wan namespace
|
||||||
# vpn interface is in default namespace, meaning it can be used in the default namespace
|
# vpn interface is in default namespace, meaning it can be used in the default namespace
|
||||||
# networking.wireguard.interfaces.${vpn_iface} = cfg.vpn.wireguard.config // {
|
networking.wireguard.interfaces.${vpn_iface} = lib.mkIf cfg.vpn.wireguard.enable
|
||||||
# socketNamespace = "wan";
|
(cfg.vpn.wireguard.config // {
|
||||||
# interfaceNamespace = "init";
|
socketNamespace = "wan";
|
||||||
# };
|
interfaceNamespace = "init";
|
||||||
|
});
|
||||||
|
|
||||||
systemd.services.vpn-tunnel = {
|
systemd.services.vpn-tunnel = lib.mkIf (cfg.vpn.tunnel.mode == "ssh") {
|
||||||
description = "VPN Tunnel";
|
description = "VPN Tunnel";
|
||||||
wantedBy = [
|
wantedBy = [
|
||||||
"multi-user.target"
|
"multi-user.target"
|
||||||
|
|
|
@ -7,7 +7,18 @@
|
||||||
options.router-settings = {
|
options.router-settings = {
|
||||||
vpn = {
|
vpn = {
|
||||||
tunnel = {
|
tunnel = {
|
||||||
enable = lib.mkEnableOption "VPN tunnel";
|
mode = lib.mkOption {
|
||||||
|
description = "tunnel mode";
|
||||||
|
type = with lib.types; nullOr (enum [ "ssh" "sit" ]);
|
||||||
|
};
|
||||||
|
ifaceAddr = lib.mkOption {
|
||||||
|
description = "interface cidr";
|
||||||
|
type = router-lib.types.cidr;
|
||||||
|
};
|
||||||
|
localIp = lib.mkOption {
|
||||||
|
description = "local ip";
|
||||||
|
type = router-lib.types.ip;
|
||||||
|
};
|
||||||
localPort = lib.mkOption {
|
localPort = lib.mkOption {
|
||||||
description = "local port";
|
description = "local port";
|
||||||
type = lib.types.port;
|
type = lib.types.port;
|
||||||
|
@ -18,7 +29,7 @@
|
||||||
};
|
};
|
||||||
ip = lib.mkOption {
|
ip = lib.mkOption {
|
||||||
description = "remote ip";
|
description = "remote ip";
|
||||||
type = router-lib.types.ipv4;
|
type = router-lib.types.ip;
|
||||||
};
|
};
|
||||||
port = lib.mkOption {
|
port = lib.mkOption {
|
||||||
description = "SSH port";
|
description = "SSH port";
|
||||||
|
|
Loading…
Reference in a new issue