conf: Add --dns-host option to configure host side nameserver

When redirecting DNS queries with the --dns-forward option, passt/pasta
needs a host side nameserver to redirect the queries to.  This is
controlled by the c->ip[46].dns_host variables.  This is set to the first
first nameserver listed in the host's /etc/resolv.conf, and there isn't
currently a way to override it from the command line.

Prior to 0b25cac9 ("conf: Treat --dns addresses as guest visible
addresses") it was possible to alter this with the -D/--dns option.
However, doing so was confusing and had some nonsensical edge cases because
-D generally takes guest side addresses, rather than host side addresses.

Add a new --dns-host option to restore this functionality in a more
sensible way.

Link: https://bugs.passt.top/show_bug.cgi?id=102
Signed-off-by: David Gibson <david@gibson.dropbear.id.au>
Signed-off-by: Stefano Brivio <sbrivio@redhat.com>
This commit is contained in:
David Gibson 2024-10-03 15:14:02 +10:00 committed by Stefano Brivio
parent 9d66df9a9a
commit ff63ac922a
2 changed files with 29 additions and 4 deletions

16
conf.c
View file

@ -829,6 +829,9 @@ static void usage(const char *name, FILE *f, int status)
" --dns-forward ADDR Forward DNS queries sent to ADDR\n" " --dns-forward ADDR Forward DNS queries sent to ADDR\n"
" can be specified zero to two times (for IPv4 and IPv6)\n" " can be specified zero to two times (for IPv4 and IPv6)\n"
" default: don't forward DNS queries\n" " default: don't forward DNS queries\n"
" --dns-host ADDR Host nameserver to direct queries to\n"
" can be specified zero to two times (for IPv4 and IPv6)\n"
" default: first nameserver from host's /etc/resolv.conf\n"
" --no-tcp Disable TCP protocol handler\n" " --no-tcp Disable TCP protocol handler\n"
" --no-udp Disable UDP protocol handler\n" " --no-udp Disable UDP protocol handler\n"
" --no-icmp Disable ICMP/ICMPv6 protocol handler\n" " --no-icmp Disable ICMP/ICMPv6 protocol handler\n"
@ -1286,6 +1289,7 @@ void conf(struct ctx *c, int argc, char **argv)
{"netns-only", no_argument, NULL, 20 }, {"netns-only", no_argument, NULL, 20 },
{"map-host-loopback", required_argument, NULL, 21 }, {"map-host-loopback", required_argument, NULL, 21 },
{"map-guest-addr", required_argument, NULL, 22 }, {"map-guest-addr", required_argument, NULL, 22 },
{"dns-host", required_argument, NULL, 24 },
{ 0 }, { 0 },
}; };
const char *logname = (c->mode == MODE_PASTA) ? "pasta" : "passt"; const char *logname = (c->mode == MODE_PASTA) ? "pasta" : "passt";
@ -1463,6 +1467,18 @@ void conf(struct ctx *c, int argc, char **argv)
conf_nat(optarg, &c->ip4.map_guest_addr, conf_nat(optarg, &c->ip4.map_guest_addr,
&c->ip6.map_guest_addr, NULL); &c->ip6.map_guest_addr, NULL);
break; break;
case 24:
if (inet_pton(AF_INET6, optarg, &c->ip6.dns_host) &&
!IN6_IS_ADDR_UNSPECIFIED(&c->ip6.dns_host))
break;
if (inet_pton(AF_INET, optarg, &c->ip4.dns_host) &&
!IN4_IS_ADDR_UNSPECIFIED(&c->ip4.dns_host) &&
!IN4_IS_ADDR_BROADCAST(&c->ip4.dns_host))
break;
die("Invalid host nameserver address: %s", optarg);
break;
case 'd': case 'd':
c->debug = 1; c->debug = 1;
c->quiet = 0; c->quiet = 0;

17
passt.1
View file

@ -249,10 +249,19 @@ the host.
.TP .TP
.BR \-\-dns-forward " " \fIaddr .BR \-\-dns-forward " " \fIaddr
Map \fIaddr\fR (IPv4 or IPv6) as seen from guest or namespace to the Map \fIaddr\fR (IPv4 or IPv6) as seen from guest or namespace to the
first configured DNS resolver (with corresponding IP version). Maps nameserver (with corresponding IP version) specified by the
only UDP and TCP traffic to port 53 or port 853. Replies are \fB\-\-dns-host\fR option. Maps only UDP and TCP traffic to port 53 or
translated back with a reverse mapping. This option can be specified port 853. Replies are translated back with a reverse mapping. This
zero to two times (once for IPv4, once for IPv6). option can be specified zero to two times (once for IPv4, once for
IPv6).
.TP
.BR \-\-dns-host " " \fIaddr
Configure the host nameserver which guest or namespace queries to the
\fB\-\-dns-forward\fR address will be redirected to. This option can
be specified zero to two times (once for IPv4, once for IPv6).
By default, the first nameserver from the host's
\fI/etc/resolv.conf\fR.
.TP .TP
.BR \-S ", " \-\-search " " \fIlist .BR \-S ", " \-\-search " " \fIlist