]> git.ipfire.org Git - thirdparty/bind9.git/commitdiff
Skip non-existent qpcache headers in iterators
authorOndřej Surý <ondrej@sury.org>
Sun, 12 Jul 2026 05:00:31 +0000 (07:00 +0200)
committerOndřej Surý <ondrej@sury.org>
Sun, 12 Jul 2026 05:06:42 +0000 (07:06 +0200)
The cache rdataset iterator must never bind delete tombstones, even
when expired cache entries are requested for dumpdb. Treat non-existent
slab headers as inactive so expired dumps cannot expose headers without
a backing rdataslab.

Assisted-by: Codex:GPT-5
lib/dns/qpcache.c

index 72ad867e3c1a26d1ac1f61ac1255dfd2fe7bcb3d..ad0768d36f9480ad78ec64754ddb2a34833f99e9 100644 (file)
@@ -2101,7 +2101,9 @@ qpcache_createiterator(dns_db_t *db, unsigned int options ISC_ATTR_UNUSED,
 static bool
 iterator_active(qpcache_t *qpdb, qpc_rditer_t *iterator,
                dns_slabheader_t *header) {
-       dns_ttl_t stale_ttl = header->expire + STALE_TTL(header, qpdb);
+       if (!EXISTS(header)) {
+               return false;
+       }
 
        /*
         * If this header is still active then return it.
@@ -2110,6 +2112,8 @@ iterator_active(qpcache_t *qpdb, qpc_rditer_t *iterator,
                return true;
        }
 
+       dns_ttl_t stale_ttl = header->expire + STALE_TTL(header, qpdb);
+
        /*
         * If we are not returning stale records or the rdataset is
         * too old don't return it.
@@ -2150,6 +2154,9 @@ qpcache_allrdatasets(dns_db_t *db, dns_dbnode_t *node, dns_dbversion_t *version,
        NODE_RDLOCK(nlock, &nlocktype);
 
        DNS_SLABHEADER_FOREACH(header, &qpnode->headers) {
+               if (!EXISTS(header)) {
+                       continue;
+               }
                if (EXPIREDOK(iterator) ||
                    iterator_active(qpdb, iterator, header))
                {