]> git.ipfire.org Git - thirdparty/bind9.git/commit
Remove duplicate addresses from the resolver SLIST
authorColin Vidal <colin@isc.org>
Wed, 4 Feb 2026 09:18:42 +0000 (10:18 +0100)
committerColin Vidal <colin@isc.org>
Thu, 30 Apr 2026 16:38:35 +0000 (18:38 +0200)
commit5d7f468c7784d8806e230b784f5e63cb4c6c76ce
tree20f2f800554ab98d00b0caed4f0b98b678c25c4b
parent20d79632c20ba81e66dec9a9e158ac17909ede1a
Remove duplicate addresses from the resolver SLIST

The SLIST (essentially `fctx->finds`, forwarders and dual-stack
alternatives aside) can have duplicate server addresses when multiple
in-domain nameservers share the same IP addresses:

  sub.example.          NS      ns1.sub.example.
  sub.example.          NS      ns2.sub.example.
  ns1.sub.example.      A       1.2.3.4
  ns1.sub.example.      A       5.6.7.8
  ns2.sub.example.      A       1.2.3.4
  ns2.sub.example.      A       5.6.7.8

If both 1.2.3.4 and 5.6.7.8 fail to return a valid answer, the resolver
would query each address twice.

The problem is fixed by replacing the two-phase server selection (sort
each find list by SRTT, sort finds by head SRTT) with a single linear
scan in nextaddress() that finds the lowest-SRTT unmarked, non-duplicate
address across all find lists.

The old approach had a correctness bug: after sorting, the resolver
picked the next address from the "current" find list rather than
globally.  For example, with find lists [1, 15, 26] and [3, 4, 5], the
second pick would be SRTT 15 instead of the correct SRTT 3.

The new approach is both simpler and correct: each call to nextaddress()
walks all addresses, skips marked and duplicate entries, and returns the
one with the lowest SRTT.  While this walk is repeated for each server
attempt, it operates on a small bounded list and is negligible compared
to the network I/O of querying the server.

(cherry picked from commit ced6b66fafa1badfd044d569a6d3cfbdb600f5a7)
lib/dns/resolver.c