NLnetLabs / unbound

Unbound is a validating, recursive, and caching DNS resolver.
https://nlnetlabs.nl/unbound
BSD 3-Clause "New" or "Revised" License
3.14k stars 358 forks source link

Unbound fails to resolve DNS if the system has IPv6 enabled but IPv6 connectivity is broken #908

Open adrelanos opened 1 year ago

adrelanos commented 1 year ago

Describe the bug

Unbound fails to resolve DNS if the system has IPv6 enabled but IPv6 connectivity is broken.

Does unbound attempt to fallback on IPv4 in case IPv6 is broken?

To reproduce

Steps to reproduce the behavior:

  1. Debian bookworm
  2. Install dnssec-trigger
  3. nslookup

Expected behavior

Functional DNS.

System:

Configure line: --build=x86_64-linux-gnu --prefix=/usr --includedir=${prefix}/include --mandir=${prefix}/share/man --infodir=${prefix}/share/info --sysconfdir=/etc --localstatedir=/var --disable-option-checking --disable-silent-rules --libdir=${prefix}/lib/x86_64-linux-gnu --runstatedir=/run --disable-maintainer-mode --disable-dependency-tracking --with-pythonmodule --with-pyunbound --enable-subnet --enable-dnstap --enable-systemd --with-libnghttp2 --with-chroot-dir= --with-dnstap-socket-path=/run/dnstap.sock --disable-rpath --with-pidfile=/run/unbound.pid --with-libevent --enable-tfo-client --with-rootkey-file=/usr/share/dns/root.key --enable-tfo-server Linked libs: libevent 2.1.12-stable (it uses epoll), OpenSSL 3.0.9 30 May 2023 Linked modules: dns64 python subnetcache respip validator iterator TCP Fastopen feature available

BSD licensed, see LICENSE in source package for details. Report bugs to unbound-bugs@nlnetlabs.nl or https://github.com/NLnetLabs/unbound/issues

adrelanos commented 1 year ago

debug log: https://nopaste.net/TY3I8Ee9gO

adrelanos commented 1 year ago

I think this should be considered a bug in unbound. Because with the default /etc/resolv.conf, DNS was functional.

But after using dnssec-trigger, DNS was broken. Connectivity got broken instead of more secure.

gthess commented 1 year ago

Hi, I don't think this is a bug. What I see from the logs is Unbound trying both IPv4 and IPv6 addresses. The IPv6 packets cannot be routed so that gives an error. (do-ip6: no could help if IPv6 connectivity is always broken). The IPv4 replies are categorized as "lame" by Unbound with the following log output:

info: query response REC_LAME: recursive but not authoritative server
info: mark as REC_LAME

This is because the servers there are not giving authoritative answers (probably your DNS traffic (port 53) is intercepted by a forwarder in your network). Unbound then tries other addresses in order to find an acceptable answer. By doing so it reaches the limit of allowed send packets for a single query:

debug: request has exceeded the maximum number of sends with 33
debug: return error response SERVFAIL

Now those IPv4 "lame" answers would be accepted by Unbound as a last resort but only after all possible servers were (re)tried; the retrying part is for IPv6 in this case. This doesn't happen for this domain (.) given the number of available nameservers.

One possible solution would be do-ip6: no. It will get the IPv6 addresses out of the equation and "the maximum number of sends" could be avoided allowing for the last resort to take place. Bringing down outbound-msg-retry from the default 5 and bringing up max-sent-count from the default 32 could work but it is not advisable. This is still not ideal though since it seems you are behind a forwarder and that means that possibly all your queries would have to deal with the same last resort logic, rendering DNS resolution slow.

A better approach then would be to forward your DNS traffic to a (open) resolver you trust preferable over DoT (https://unbound.docs.nlnetlabs.nl/en/latest/manpages/unbound.conf.html#forward-zone-options).

For a list of public resolvers that support DoT: https://dnsprivacy.org/public_resolvers/#dns-over-tls-dot.

Although if destination port 53 is intercepted I would not be suprised if destination port 853 is blocked.