Commit graph

45976 commits

Author SHA1 Message Date
Colin Vidal
f52fe46dec fix: usr: Fix recursion loop in case of badly behaving forwarders
When forwarding DNS queries, the CD bit is cleared on the first query, and the CD bit is only used as a fallback if the first query fails. However, due to a logic bug this could lead to an unbounded loop re-sending the same message, until the maximum query count is hit. This has been fixed.

Closes #5804

Merge branch '5804-resend-loop-forwarder-cd' into 'main'

See merge request isc-projects/bind9!12133
2026-06-18 09:21:26 +02:00
Colin Vidal
4b55bfe626 Avoid resend loop when forwarder SERVFAILs with both CD=0 and CD=1
Commit `36cf1c6a5bf943ad718ddba9fbe6ea97810e3bc2` introduces the
`DNS_FETCHOPT_TRYCD` flag which enables, when sending a query to a
forwarder, the forwarder to validate the answer (CD=0). The crux is
that if for some reason the forwarder returns SERVFAIL, we can retry the
same query and disable the forwarder validation (CD=1) so the resolver
can attempt validation itself (or detect it's bogus).

The logic was to first set `DNS_FETCHOPT_TRYCD` to the query options but
not on the message (so CD=0), and, when getting a SERVFAIL answer, if
the option `DNS_FETCHOPT_TRYCD` was set, to also set it into the
message. However, there was no way to know if this was the first (or
second) query because the original message is discarded when getting the
answer. This can lead to an unbounded loop re-sending the same message
again and again (until the global query count stops it).

This is fixed by using two separate flags `DNS_FETCHOPT_TRYNOCD`, set on
the query options for the very first query, then, if it SERVFAIL,
check if `DNS_FETCHOPT_TRYNOCD` is set but `DNS_FETCHOPT_TRYCD` is not.
In this case, we know we're about to send the second query. If it also
fails, `DNS_FETCHOPT_TRYCD` will be set anyway, so there is no point
retrying. This breaks the unbounded loop.
2026-06-18 08:49:23 +02:00
Matthijs Mekking
4c22fa0d56 Reproducer forwarder resend loop
Run malicious server: resend_loop/ans2/ans.py

Start BIND: ns1

Send single query to test.com

OBSERVED BEHAVIOR
The malicious server receives tens of thousands of resend packets
within seconds. CPU usage of the named worker thread remains elevated
(50–100% of one core) until the default fetch timeout (~10 seconds)
terminates the request. Instrumentation during testing confirmed that
isc_counter_used(fctx->qc) remains constant (value 1) throughout the
entire resend loop.
2026-06-18 08:49:23 +02:00
Colin Vidal
e0a74bf3cb fix: usr: Cache glue only for enabled address families
When caching delegation NS data, only use A/AAAA glue records if the resolver has the corresponding IPv4/IPv6 dispatcher configured. If IPv4 or IPv6 is disabled, ignore glue for that family and fall back to caching the nameserver name if there is no glue from the other supported family.

Merge branch 'colin/glues-supported-stack' into 'main'

See merge request isc-projects/bind9!11889
2026-06-18 08:48:29 +02:00
Colin Vidal
7a27fdf3be Cache glue only for enabled address families
When caching delegation NS data, only use A/AAAA glue records if the
resolver has the corresponding IPv4/IPv6 dispatcher configured. If IPv4
or IPv6 is disabled, ignore glue for that family and fall back to
caching the nameserver name if there is no glue from the other supported
family.

The new `cache_delegns` system test is covering delegation NS caching
with dual-stack resolver, IPv4-only, IPv6-only configurations. It also
set up an authoritative sever with zones with A-only, AAAA-only, and
dual-stack glue, which are all queried, and checks the delegation
database dump to confirm that the cached delegation data correspond to
the resolver configuration.
2026-06-18 08:48:20 +02:00
Colin Vidal
8a890e10cb rem: usr: Remove GeoIP2 metro and metrocode
The `geoip metro` and `geoip metrocode` configuration options has been
removed as metro code are deprecated from MaxMind library.

Merge branch 'colin/remove-geoip-metro' into 'main'

See merge request isc-projects/bind9!12217
2026-06-18 07:56:59 +02:00
Colin Vidal
6645371566 remove GeoIP2 metro and metrocode
The `geoip metro` and `geoip metrocode` configuration options has been
removed as metro code are deprecated from MaxMind library.
2026-06-18 07:23:31 +02:00
Ondřej Surý
e18cbe6c5d fix: dev: Fix invalid pointer release in JSON statistics-channel response
Each response served on a JSON statistics endpoint released the wrong
pointer to the JSON library after the response was sent: the response
body string instead of the JSON document.  With the current responses
this does not crash named in practice, but the call is incorrect and
can in principle corrupt memory.  XML responses are not affected.

Closes #6024

Merge branch '6024-statschannel-json-response-invalid-free' into 'main'

See merge request isc-projects/bind9!12068
2026-06-18 07:13:42 +02:00
Ondřej Surý
f39089576a Fix invalid free in statistics-channel JSON renderer
wrap_jsonfree() called json_object_put() on the response-body buffer
base, which is the JSON string returned by
json_object_to_json_string_ext(), not a struct json_object.  The root
object is already passed in as the callback argument; release only
that.
2026-06-18 07:10:01 +02:00
Ondřej Surý
9608158d73 Add regression test for statistics-channel JSON free bug
Hit every JSON statistics endpoint several times.  The current code
calls json_object_put() on the response-body string pointer, which
doesn't crash just by accident - the memory position contains large
value from static string.
2026-06-18 07:10:01 +02:00
Ondřej Surý
0b13a184fc chg: dev: Sync picohttpparser.c with upstream commit a875a01
Synced with the h2o/picohttpparser upstream repository up to commit
f4d94b48b31e0abae029ebeafcfd9ca0680ede58.

This commit is just hygiene and consistency by keeping the vendored copy
current.

Merge branch 'mnowak/picohttpparser-sync-a875a01' into 'main'

See merge request isc-projects/bind9!12159
2026-06-18 06:26:43 +02:00
Ondřej Surý
5b34773627 Re-apply the picohttpparser.c patch
This:
- makes sure all variables are initialized
- adds missing curly braces for single line statements
- use proper comment for fallthrough case statements
2026-06-18 06:26:07 +02:00
Michal Nowak
cfd7fd867b Sync picohttpparser.c with upstream commit a875a01
Pull in upstream commit a875a01 from h2o/picohttpparser: enforce use of
CRLF in chunk headers, by rejecting bare CR / LF. Replaces the lenient
CHUNKED_IN_CHUNK_CRLF state with strict CHUNKED_IN_CHUNK_HEADER_EXPECT_LF,
CHUNKED_IN_CHUNK_DATA_EXPECT_CR and CHUNKED_IN_CHUNK_DATA_EXPECT_LF states.

Synced with the h2o/picohttpparser upstream repository up to commit
f4d94b48b31e0abae029ebeafcfd9ca0680ede58.

This commit is just hygiene and consistency by keeping the vendored copy
current.

Assisted-by: Claude:claude-opus-4-7
2026-06-18 06:26:07 +02:00
Ondřej Surý
88701b9112 fix: nil: Allocate work threads from their owning loop's memory context
The per-loop worker threads allocated their state from the loop manager's
memory context instead of the per-loop context that owns them. Allocate
from the owning loop's context and hold a reference to that loop for the
thread's lifetime, matching the context handling already used on the
work-enqueue and completion paths.

Already changed as part of 9.20 backport.

Merge branch 'ondrej/rewrite-threadpool-fixups' into 'main'

See merge request isc-projects/bind9!12268
2026-06-17 22:30:13 +02:00
Ondřej Surý
17b8942efa Run the work asynchronously when shutting down
Instead of running the work directly, run it asynchronously to prevent
dead-locks when then isc_work is scheduled from inside a lock and the
job itself is using locking.
2026-06-17 22:29:51 +02:00
Ondřej Surý
72ff42d2bf Allocate work threads from their owning loop's memory context
A per-loop work thread referenced the loop manager's memory context,
which is not the context that backs the loop the thread serves. Pass
the owning loop instead and allocate from loop->mctx, keeping a loop
reference for the thread's lifetime. This matches how isc_work_enqueue
and work_done already obtain the context from the loop, and the
teardown uses loop->mctx before dropping the reference.
2026-06-17 22:29:51 +02:00
Štěpán Balážik
9b3a86bb84 chg: test: Reimplement the formerr system test in Python
Replace the shell and Perl based FORMERR system test with a Python
test that constructs the malformed DNS packets directly and checks
the responses.

Remove the legacy shell and Perl test script and the intermediate
packet files in hex, leaving the packet construction inline in
tests_formerr.py.

Merge branch 'stepan/formerr-system-test-python' into 'main'

See merge request isc-projects/bind9!11898
2026-06-17 20:01:06 +00:00
Štěpán Balážik
62a3804a4c Simplify the packets in the formerr system test
Normalize the message ID to 0 and the TTL of records to 1 unless
required (OPT and UPDATE records require TTL=0).

Rename the questionclass test case to twoquestionclasses for
consistency.
2026-06-17 20:08:48 +02:00
Štěpán Balážik
151b2d6045 Reimplement the FORMERR system test in Python
Replace the shell and Perl based FORMERR system test with a Python
test that constructs the malformed DNS packets directly and checks
the responses.

Remove the legacy shell and Perl test script and the intermediate
packet files in hex, leaving the packet construction inline in
tests_formerr.py.

Preserve the same wire for all packets sent to the server, but
construct them in a more explicit and readable way.
2026-06-17 20:08:48 +02:00
Ondřej Surý
0eb657c45b chg: dev: Rework isc_work as per-loop, per-lane cancelable worker threads
Fold the libuv thread pool and the per-loop isc_helper threads into a single
isc_work pool. Each (loop, lane) gets its own SPSC queue and worker, which drops
the shared-queue contention, and the FAST/SLOW lanes keep short crypto tasks off
the long blocking ones (zone dump/load, xfrin). isc_work jobs are now cancelable:
isc_work_cancel() tombstones a still-queued job and its after_cb fires with
ISC_R_CANCELED, so abandoned work can be dropped instead of run to completion.

Merge branch 'ondrej/rewrite-threadpool' into 'main'

See merge request isc-projects/bind9!12226
2026-06-17 19:07:21 +02:00
Ondřej Surý
a5f13b3410 Replace the shared work pool with per-loop, per-lane worker threads
Offloaded work used two different mechanisms: a per-loop isc_helper
thread for CPU-bound crypto (DNSSEC validation, message signature
checks) and the process-global libuv thread pool for blocking I/O (zone
load and dump, inbound transfer apply). Neither could cancel a queued
task, and the two disagreed about exclusive mode — the helper paused
with its loop under isc_loopmgr_pause() but the libuv pool did not, so
blocking offloaded work kept running while a loop held the exclusive
lock.

Unify both behind isc_work: each loop gets its own worker thread per
lane — FAST for short, bounded tasks and SLOW for long, blocking ones —
fed by a private queue. Separate lanes keep a short crypto task off the
path of a multi-second zone dump once both run on per-loop workers;
every lane parks with isc_loopmgr_pause() so exclusive mode now quiesces
offloaded work too; and a still-queued task can be canceled before it
starts (isc_work_cancel). isc_helper is removed and its callers select a
lane.
2026-06-17 19:07:08 +02:00
Nicki Křížek
37b13e955e chg: ci: Adjust allow_failure in cross-version-config tests
The failures caused by #6007 are longer happening.

However, in the mean time, other tests have begun to fail due to https://gitlab.isc.org/isc-projects/bind9/-/merge_requests/12163/diffs?commit_id=9771df0aca5ce399ad0535f656c403a58d674606

Merge branch 'nicki/revert-allow-failure-after-9.21.23' into 'main'

See merge request isc-projects/bind9!12264
2026-06-17 17:42:35 +02:00
Nicki Křížek
d3345763cb Add allow_failure to cross-version-config tests
Due to a recent change which dropped the non-IN-class in views, the
following tests are failing in cross-version-config-tests:

auth
catz
class
resolver
unknown

This can be reverted once the July releases are public.
2026-06-17 17:25:40 +02:00
Nicki Křížek
fb47203570 Revert "Make cross-version-config-tests allow_failure: true"
This reverts commit 86b0615aea.
2026-06-17 16:31:43 +02:00
Nicki Křížek (GitLab job 7567049)
46feca4e4a Merge tag 'v9.21.23' 2026-06-17 13:48:49 +00:00
Alessio Podda
2b3911290f fix: usr: Only print per zone glue stats when query statistics is full
The code printing query statistics was ignoring the zone-statistics
option. This has been fixed.

Closes #6164

Merge branch '6164-no-per-zone-glue-stats' into 'main'

See merge request isc-projects/bind9!12262
2026-06-17 12:40:55 +00:00
Alessio Podda
e1cb775e95 Add test for query statistics
Ensure that no per-zone glue statistic is printed unless
zone-statistics is set to full.
2026-06-17 14:06:12 +02:00
Alessio Podda
f655b6af84 Only print per zone glue cache stats when zone-statistics is full
The code printing glue cache statistics was ignoring the
zone-statistics option. This has been fixed.
2026-06-17 14:06:12 +02:00
Colin Vidal
e0e1208dbb fix: usr: Fix CNAME resolution failure caused by a cached SERVFAIL response
Under certain circumstances, a cached SERVFAIL response could incorrectly prevent successful resolution of a CNAME target. This could cause resolution failures to persist until the cached SERVFAIL entry expired, even when the CNAME target itself was otherwise resolvable. This issue has been fixed.

Closes #5983

Merge branch '5983-servfail-cache-cname' into 'main'

See merge request isc-projects/bind9!12158
2026-06-17 11:24:32 +02:00
Colin Vidal
66af5b464d Use original query name when caching SERVFAIL
Instead of using `client->query.qname` when caching a SERVFAIL answer,
use `client->query.origqname` when available.

This avoids caching a SERVFAIL against a CNAME target when the failure
occurs while the resolver is following the CNAME chain. This is
problematic, for instance, when the SERVFAIL is triggered by the
`max-query-count` threshold being reached, which would incorrectly
prevent legitimate resolution of the CNAME target while in the SERVFAIL
cache.

Note that if the SERVFAIL genuinely originated from resolving the CNAME
target, that specific failure will no longer be cached, and a direct
query for the CNAME target will trigger a fresh (likely failing)
resolution attempt. However, this is still preferable to the previous
behaviour, which would wrongly prevent resolving the CNAME target if it
was cached for other reasons (like the example above).
2026-06-17 09:32:19 +02:00
Colin Vidal
d238b8eece
System test covering SERVFAIL cache and CNAME
Add a system test for the case where resolution SERVFAILs because the
fetch context reaches the `max-query-count` threshold while following a
CNAME.

Resolving the CNAME target independently should still work, because the
SERVFAIL cache stores the original query name rather than the target.
2026-06-17 06:42:16 +02:00
Evan Hunt
1fe179973e rem: usr: remove the secondary validator in query.c
Previously, when the additional section of a response was being
populated, if cached data was found with pending trust, it would be
opportunistically validated. The code implementing this validation was
not quite formally correct. Rather than fixing it, the code has been
removed: RRsets with pending trust are now omitted from responses.

Closes #5966

Closes #5968

Closes #5972

Merge branch 'each-remove-lightweight-validator' into 'main'

See merge request isc-projects/bind9!12236
2026-06-17 02:42:40 +00:00
Nicki Křížek
72bda8335f Don't run vulture on ansX system test dirs
Exclude ansX directories from vulture, as splitting up the handlers into
multiple files gets flagged as unused code.
2026-06-16 19:07:06 -07:00
Evan Hunt
05691b53da Merge DNSSEC wildcard tests
Merge the tests for #5966 (F-043) and #5972 (F-045), previously called
dnssec_wildcard_additional and dnssec_replayed_parent_wildcard, into a
single directory with two modules.
2026-06-16 19:07:06 -07:00
Alessio Podda
99377e9fdd Reproducer for #5968 parent RRSIG in additional
Add a new "dnssec_parent_rrsig" system test.

Co-Authored-By: Matthijs Mekking <matthijs@isc.org>
2026-06-16 19:07:06 -07:00
Alessio Podda
4466bbcb4a Reproducer for #5972 DNS_R_FROMWILDCARD accepted
Add a new "dnssec_wildcard_additional" system test.

Co-Authored-By: Evan Hunt <each@isc.org>
2026-06-16 19:07:06 -07:00
Alessio Podda
1d4d3e09ad Reproducer for #5966 replay parent wildcard
Add a new "dnssec_replayed_parent_wildcard" system test.

Co-Authored-By: Matthijs Mekking <matthijs@isc.org>
2026-06-16 19:07:06 -07:00
Evan Hunt
6e44151466 add isctest.mark method for ecdsa_deterinistic
This checks support for ECDSA deterministic mode in the cryptography
library.
2026-06-16 19:07:06 -07:00
Matthijs Mekking
f678d03a67 Add isctest.check methods for AA flag
Similar to checking AD flag, add methods to see if the AA flag is
present or absent.
2026-06-16 14:45:49 -07:00
Evan Hunt
7ec85b4bd2 Remove the secondary validator in query.c
Previously, when the additional section of a response was being
populated, if cached data was found with pending trust, it would be
opportunistically validated. The code implementing this validation was
not quite formally correct; rather than fixing it, the code has been
removed; RRsets with pending trust are now omitted from responses.

Fixes: isc-projects/bind9#5966
Fixes: isc-projects/bind9#5968
Fixes: isc-projects/bind9#5972
2026-06-16 10:11:16 -07:00
Vicky Risk
499da939f8 fix: doc: Edit SECURITY.md to remove references to bind-security@isc.org
We no longer want to encourage people to open new issues via email because we are getting too many spammy reports generated by LLM. By requiring people actually login to Gitlab to make their report, they will (hopefully) see our reporting template, and think at least a little bit about whether they are making a well-considered, valid report.

Merge branch 'vicky-main-patch-01884' into 'main'

See merge request isc-projects/bind9!12248
2026-06-16 11:26:01 -04:00
Vicky Risk
ce17ffcb48 Edit SECURITY.md to remove references to bind-security@isc.org 2026-06-16 15:32:52 +02:00
Ondřej Surý
1d6b19549c chg: dev: Use SIEVE for TSIG generated-key LRU
Replace the list-based LRU for TSIG KEYs with SIEVE-based LRU.

Merge branch 'ondrej/use-sieve-for-tsigkey-lru' into 'main'

See merge request isc-projects/bind9!12043
2026-06-16 15:13:30 +02:00
Ondřej Surý
bb353200da
Use SIEVE for TSIG generated-key LRU
The generated-key cache used a strict LRU: every lookup hit promoted
the key to the tail of the list under the write lock, even when the
caller arrived holding only the read lock.  That promotion was both
a lock upgrade and a list reshuffle on the hot path.

Replace the LRU with the SIEVE eviction policy.  Lookups now do a
lock-free atomic mark of the visited bit; eviction work moves to
insertion time, which already holds the write lock.
2026-06-16 14:40:49 +02:00
Ondřej Surý
bfb61e1dbc fix: test: Fix the rpz servfail-until-ready test when zone updates run serially
The rpz servfail-until-ready test assumed a particular policy zone always
finished loading last, which only holds when zone updates run in parallel;
on a single CPU (or with serialized offload) it could fail spuriously. It now
polls until RPZ reports ready instead.

Merge branch 'ondrej/fix-rpz-system-test-on-single-cpu' into 'main'

See merge request isc-projects/bind9!12251
2026-06-16 14:01:33 +02:00
Ondřej Surý
153c9d3509 Poll for RPZ readiness in the servfail-until-ready test
RPZ is ready only once every policy zone has completed its first update,
and the zones do not finish in a fixed order, so whenever the updates
run serially (per-loop offload, or any single-CPU run): 'slow-rpz' zone
can finish before the others and the query still gets SERVFAIL.  Poll
the query until it returns NOERROR instead.

Assisted-by: Claude:claude-opus-4-8
2026-06-16 14:01:13 +02:00
Alessio Podda
074efb5768 fix: dev: Keep RRL ncache fixed name alive
Move the fixed name storage out of the NCACHE branch so the name passed to dns_rrl() remains valid for cached NXDOMAIN responses.

Closes #6029

Merge branch '6029-fixedname-fix' into 'main'

See merge request isc-projects/bind9!12096
2026-06-16 11:01:52 +00:00
Alessio Podda
aa022f7ea2 Keep RRL ncache fixed name alive
Move the fixed name storage out of the NCACHE branch so the name passed to
dns_rrl() remains valid for cached NXDOMAIN responses.
2026-06-16 11:56:59 +02:00
Alessio Podda
c2ebd1f66e Add RRL cached NXDOMAIN system test
Add a Python system test that primes ns2's negative cache, queries the
cached NXDOMAIN through RRL, and verifies named remains responsive.
2026-06-16 11:47:09 +02:00
Nicki Křížek
139b0fc48e new: test: Add AnsInstance as the ans counterpart of NamedInstance
Tests interacting with mock ans servers had to hardcode their IP
addresses and open ans.run directly, while named instances already
had the NamedInstance abstraction with `.ip`, `.log` and the
watch_log_*() helpers.  Factor the parts of NamedInstance that are
not named-specific into a ServerInstance base class and add an
AnsInstance subclass for ans servers, exposed through the `servers`
fixture and new ans1-ans11 convenience fixtures.

Assisted-by: Claude:claude-fable-5

Merge branch 'nicki/pytest-ans-instance' into 'main'

See merge request isc-projects/bind9!12241
2026-06-16 10:28:36 +02:00