diff --git a/conf.c b/conf.c index d347f1d..dcba9ae 100644 --- a/conf.c +++ b/conf.c @@ -600,6 +600,7 @@ static void usage(const char *name) info( " --no-ndp Disable NDP responses"); info( " --no-dhcpv6 Disable DHCPv6 server"); info( " --no-ra Disable router advertisements"); + info( " --no-map-gw Don't map gateway address to host"); info( " -4, --ipv4-only Enable IPv4 operation only"); info( " -6, --ipv6-only Enable IPv6 operation only"); @@ -776,6 +777,7 @@ void conf(struct ctx *c, int argc, char **argv) {"no-dhcpv6", no_argument, &c->no_dhcpv6, 1 }, {"no-ndp", no_argument, &c->no_ndp, 1 }, {"no-ra", no_argument, &c->no_ra, 1 }, + {"no-map-gw", no_argument, &c->no_map_gw, 1 }, {"ipv4-only", no_argument, &c->v4, '4' }, {"ipv6-only", no_argument, &c->v6, '6' }, {"tcp-ports", required_argument, NULL, 't' }, diff --git a/passt.1 b/passt.1 index bf8228d..3355bff 100644 --- a/passt.1 +++ b/passt.1 @@ -207,6 +207,11 @@ namespace will be silently dropped. Disable Router Advertisements. Router Solicitations coming from guest or target namespace will be ignored. +.TP +.BR \-\-no-map-gw +Don't remap TCP connections and untracked UDP traffic, with the gateway address +as destination, to the host. + .TP .BR \-4 ", " \-\-ipv4-only Enable IPv4-only operation. IPv6 traffic will be ignored. @@ -635,7 +640,7 @@ address corresponding to the default gateway will have their destination address translated to a loopback address, if and only if a packet, in the opposite direction, with a loopback destination or source address, port-wise matching for UDP, or connection-wise for TCP, has been recently forwarded to guest or -namespace. +namespace. This behaviour can be disabled with \-\-no\-map\-gw. .SS Handling of local traffic in pasta diff --git a/passt.h b/passt.h index 50e33a3..e2bfe9d 100644 --- a/passt.h +++ b/passt.h @@ -130,6 +130,7 @@ enum passt_modes { * @no_dhcpv6: Disable DHCPv6 server * @no_ndp: Disable NDP handler altogether * @no_ra: Disable router advertisements + * @no_map_gw: Don't map connections, untracked UDP to gateway to host * @low_wmem: Low probed net.core.wmem_max * @low_rmem: Low probed net.core.rmem_max */ @@ -188,6 +189,7 @@ struct ctx { int no_dhcpv6; int no_ndp; int no_ra; + int no_map_gw; int low_wmem; int low_rmem; diff --git a/tcp.c b/tcp.c index 05382f7..011710e 100644 --- a/tcp.c +++ b/tcp.c @@ -1845,9 +1845,10 @@ static void tcp_conn_from_tap(struct ctx *c, int af, void *addr, tcp_sock_set_bufsize(c, s); - if (af == AF_INET && addr4.sin_addr.s_addr == c->gw4) + if (af == AF_INET && addr4.sin_addr.s_addr == c->gw4 && !c->no_map_gw) addr4.sin_addr.s_addr = htonl(INADDR_LOOPBACK); - else if (af == AF_INET6 && !memcmp(addr, &c->gw6, sizeof(c->gw6))) + else if (af == AF_INET6 && !memcmp(addr, &c->gw6, sizeof(c->gw6)) && + !c->no_map_gw) addr6.sin6_addr = in6addr_loopback; if (af == AF_INET6 && IN6_IS_ADDR_LINKLOCAL(&addr6.sin6_addr)) { diff --git a/udp.c b/udp.c index e77345f..148b06a 100644 --- a/udp.c +++ b/udp.c @@ -933,7 +933,7 @@ int udp_tap_handler(struct ctx *c, int af, void *addr, udp_tap_map[V4][src].ts = now->tv_sec; - if (s_in.sin_addr.s_addr == c->gw4) { + if (s_in.sin_addr.s_addr == c->gw4 && !c->no_map_gw) { if (!udp_tap_map[V4][dst].ts_local || udp_tap_map[V4][dst].loopback) s_in.sin_addr.s_addr = htonl(INADDR_LOOPBACK); @@ -951,7 +951,7 @@ int udp_tap_handler(struct ctx *c, int af, void *addr, sa = (struct sockaddr *)&s_in6; sl = sizeof(s_in6); - if (!memcmp(addr, &c->gw6, sizeof(c->gw6))) { + if (!memcmp(addr, &c->gw6, sizeof(c->gw6)) && !c->no_map_gw) { if (!udp_tap_map[V6][dst].ts_local || udp_tap_map[V6][dst].loopback) s_in6.sin6_addr = in6addr_loopback;