]> git.ipfire.org Git - thirdparty/bind9.git/commitdiff
Special case refresh stale ncache data
authorMatthijs Mekking <matthijs@isc.org>
Wed, 9 Jul 2025 12:21:44 +0000 (14:21 +0200)
committerMatthijs Mekking <matthijs@isc.org>
Wed, 23 Jul 2025 07:18:48 +0000 (07:18 +0000)
When refreshing stale ncache data, the qctx->rdataset is NULL and
requires special processing.

lib/dns/include/dns/rdataset.h
lib/ns/query.c

index 2632d3a643f839d88cf9bb9006d196b4f0be9859..7bf617058675fb8d28dd36de3a319f1c2024d145 100644 (file)
@@ -119,32 +119,32 @@ struct dns_rdataset {
 
        struct {
                bool question    : 1;
-               bool rendered    : 1;  /*%< message.c: was rendered */
-               bool answered    : 1;  /*%< server. */
-               bool cache       : 1;  /*%< resolver. */
-               bool answer      : 1;  /*%< resolver. */
-               bool answersig   : 1;  /*%< resolver. */
-               bool external    : 1;  /*%< resolver. */
-               bool ncache      : 1;  /*%< resolver. */
-               bool chaining    : 1;  /*%< resolver. */
-               bool ttladjusted : 1;  /*%< message.c: data had differing TTL
-                       values, and the rdataset->ttl holds the smallest */
-               bool chase        : 1; /*%< Used by resolver. */
-               bool nxdomain     : 1;
-               bool noqname      : 1;
-               bool checknames   : 1; /*%< Used by resolver. */
-               bool required     : 1;
-               bool resign       : 1;
-               bool closest      : 1;
-               bool optout       : 1; /*%< OPTOUT proof */
-               bool negative     : 1;
-               bool prefetch     : 1;
-               bool stale        : 1;
-               bool ancient      : 1;
-               bool stale_window : 1;
-               bool           keepcase   : 1;
-               bool           staticstub : 1;
-               dns_orderopt_t order      : 2;
+               bool rendered    : 1; /*%< message.c: was rendered */
+               bool answered    : 1; /*%< server. */
+               bool cache       : 1; /*%< resolver. */
+               bool answer      : 1; /*%< resolver. */
+               bool answersig   : 1; /*%< resolver. */
+               bool external    : 1; /*%< resolver. */
+               bool ncache      : 1; /*%< resolver. */
+               bool chaining    : 1; /*%< resolver. */
+               bool ttladjusted : 1; /*%< message.c: data had differing TTL
+                      values, and the rdataset->ttl holds the smallest */
+               bool           chase        : 1; /*%< Used by resolver. */
+               bool           nxdomain     : 1;
+               bool           noqname      : 1;
+               bool           checknames   : 1; /*%< Used by resolver. */
+               bool           required     : 1;
+               bool           resign       : 1;
+               bool           closest      : 1;
+               bool           optout       : 1; /*%< OPTOUT proof */
+               bool           negative     : 1;
+               bool           prefetch     : 1;
+               bool           stale        : 1;
+               bool           ancient      : 1;
+               bool           stale_window : 1;
+               bool           keepcase     : 1;
+               bool           staticstub   : 1;
+               dns_orderopt_t order        : 2;
        } attributes;
 
        /*%
index 9bca2446a41b8945c207e0be3b7797c1dbbab119..e751dca81a79d16186303f7916a2ec82de8bd8a6 100644 (file)
@@ -2813,12 +2813,19 @@ query_stale_refresh(ns_client_t *client, dns_name_t *qname,
                    dns_rdataset_t *rdataset) {
        CTRACE(ISC_LOG_DEBUG(3), "query_stale_refresh");
 
-       bool stale_refresh_window =
-               (STALE_WINDOW(rdataset) &&
-                (client->query.dboptions & DNS_DBFIND_STALEENABLED) != 0);
+       bool stale_refresh_window = false;
+       bool stale_rrset = true;
+
+       if (rdataset != NULL) {
+               stale_refresh_window = (STALE_WINDOW(rdataset) &&
+                                       (client->query.dboptions &
+                                        DNS_DBFIND_STALEENABLED) != 0);
+               stale_rrset = STALE(rdataset);
+       }
+
        if (FETCH_RECTYPE_STALE_REFRESH(client) != NULL ||
            (client->query.dboptions & DNS_DBFIND_STALETIMEOUT) == 0 ||
-           !STALE(rdataset) || stale_refresh_window)
+           !stale_rrset || stale_refresh_window)
        {
                return;
        }
@@ -2842,6 +2849,18 @@ query_stale_refresh(ns_client_t *client, dns_name_t *qname,
                         RECTYPE_STALE_REFRESH);
 }
 
+static void
+query_stale_refresh_ncache(ns_client_t *client) {
+       dns_name_t *qname;
+
+       if (client->query.origqname != NULL) {
+               qname = client->query.origqname;
+       } else {
+               qname = client->query.qname;
+       }
+       query_stale_refresh(client, qname, NULL);
+}
+
 static void
 query_prefetch(ns_client_t *client, dns_name_t *qname,
               dns_rdataset_t *rdataset) {
@@ -9965,7 +9984,7 @@ query_ncache(query_ctx_t *qctx, isc_result_t result) {
        }
 
        if (!qctx->is_zone && RECURSIONOK(qctx->client)) {
-               query_stale_refresh(qctx->client, qctx->fname, qctx->rdataset);
+               query_stale_refresh_ncache(qctx->client);
        }
 
        return query_nodata(qctx, result);