]> git.ipfire.org Git - thirdparty/bind9.git/commitdiff
Dispatch async work jobs from the correct loop
authorOndřej Surý <ondrej@isc.org>
Tue, 10 Mar 2026 17:25:54 +0000 (18:25 +0100)
committerOndřej Surý <ondrej@sury.org>
Sat, 14 Mar 2026 05:32:54 +0000 (06:32 +0100)
Refactor dns_loadctx_t and dns_dumpctx_t to use standard
ISC_REFCOUNT_DECL and ISC_REFCOUNT_IMPL macros, retiring the
redundant manual attach and detach implementations.

Introduce dns_loadctx_enqueue() and dns_dumpctx_enqueue() to
ensure compliance with the new strict loop affinity in
isc_work_enqueue(). If the current loop does not match the
target loop, the enqueue operation is safely bounced to the
correct thread via isc_async_run().

lib/dns/master.c
lib/dns/masterdump.c

index ce2dca13d475931b798a61c2587784ce767f167d..4974999eeb66fe6541d330f780163068b9db5a80 100644 (file)
@@ -45,6 +45,8 @@
 #include <dns/time.h>
 #include <dns/ttl.h>
 
+#include "dns/types.h"
+
 /*!
  * Grow the number of dns_rdatalist_t (#RDLSZ) and dns_rdata_t (#RDSZ)
  * structures by these sizes when we need to.
@@ -387,29 +389,8 @@ gettoken(isc_lex_t *lex, unsigned int options, isc_token_t *token, bool eol,
        return ISC_R_SUCCESS;
 }
 
-void
-dns_loadctx_attach(dns_loadctx_t *source, dns_loadctx_t **target) {
-       REQUIRE(target != NULL && *target == NULL);
-       REQUIRE(DNS_LCTX_VALID(source));
-
-       isc_refcount_increment(&source->references);
-
-       *target = source;
-}
-
-void
-dns_loadctx_detach(dns_loadctx_t **lctxp) {
-       dns_loadctx_t *lctx;
-
-       REQUIRE(lctxp != NULL);
-       lctx = *lctxp;
-       *lctxp = NULL;
-       REQUIRE(DNS_LCTX_VALID(lctx));
-
-       if (isc_refcount_decrement(&lctx->references) == 1) {
-               loadctx_destroy(lctx);
-       }
-}
+ISC_REFCOUNT_DECL(dns_loadctx);
+ISC_REFCOUNT_IMPL(dns_loadctx, loadctx_destroy);
 
 static void
 incctx_destroy(isc_mem_t *mctx, dns_incctx_t *ictx) {
@@ -2621,6 +2602,21 @@ load_done(void *arg) {
        dns_loadctx_detach(&lctx);
 }
 
+static void
+load_enqueue(void *lctx) {
+       isc_work_enqueue(isc_loop(), load, load_done, lctx);
+}
+
+static void
+dns_loadctx_enqueue(isc_loop_t *loop, dns_loadctx_t *lctx) {
+       dns_loadctx_ref(lctx);
+       if (loop == isc_loop()) {
+               load_enqueue(lctx);
+       } else {
+               isc_async_run(loop, load_enqueue, lctx);
+       }
+}
+
 isc_result_t
 dns_master_loadfileasync(const char *master_file, dns_name_t *top,
                         dns_name_t *origin, dns_rdataclass_t zclass,
@@ -2649,8 +2645,8 @@ dns_master_loadfileasync(const char *master_file, dns_name_t *top,
                return result;
        }
 
-       dns_loadctx_attach(lctx, lctxp);
-       isc_work_enqueue(loop, load, load_done, lctx);
+       dns_loadctx_enqueue(loop, lctx);
+       *lctxp = lctx;
 
        return ISC_R_SUCCESS;
 }
index 07cd7c17621d5c679d017cc9a33e936592701561..e73f5d1b00cb6647ce9a817e42238275dd07c5cd 100644 (file)
@@ -1354,29 +1354,8 @@ dumpctx_destroy(dns_dumpctx_t *dctx) {
        isc_mem_putanddetach(&dctx->mctx, dctx, sizeof(*dctx));
 }
 
-void
-dns_dumpctx_attach(dns_dumpctx_t *source, dns_dumpctx_t **target) {
-       REQUIRE(DNS_DCTX_VALID(source));
-       REQUIRE(target != NULL && *target == NULL);
-
-       isc_refcount_increment(&source->references);
-
-       *target = source;
-}
-
-void
-dns_dumpctx_detach(dns_dumpctx_t **dctxp) {
-       dns_dumpctx_t *dctx;
-
-       REQUIRE(dctxp != NULL);
-       dctx = *dctxp;
-       *dctxp = NULL;
-       REQUIRE(DNS_DCTX_VALID(dctx));
-
-       if (isc_refcount_decrement(&dctx->references) == 1) {
-               dumpctx_destroy(dctx);
-       }
-}
+ISC_REFCOUNT_DECL(dns_dumpctx);
+ISC_REFCOUNT_IMPL(dns_dumpctx, dumpctx_destroy);
 
 isc_result_t
 dns_dumpctx_serial(dns_dumpctx_t *dctx, uint32_t *serial) {
@@ -1728,6 +1707,21 @@ cleanup:
        return result;
 }
 
+static void
+master_dump_enqueue(void *dctx) {
+       isc_work_enqueue(isc_loop(), master_dump_cb, master_dump_done_cb, dctx);
+}
+
+static void
+dns_dumpctx_enqueue(isc_loop_t *loop, dns_dumpctx_t *dctx) {
+       dns_dumpctx_ref(dctx);
+       if (loop == isc_loop()) {
+               master_dump_enqueue(dctx);
+       } else {
+               isc_async_run(loop, master_dump_enqueue, dctx);
+       }
+}
+
 isc_result_t
 dns_master_dumptostreamasync(isc_mem_t *mctx, dns_db_t *db,
                             dns_dbversion_t *version,
@@ -1745,8 +1739,8 @@ dns_master_dumptostreamasync(isc_mem_t *mctx, dns_db_t *db,
        dctx->done = done;
        dctx->done_arg = done_arg;
 
-       dns_dumpctx_attach(dctx, dctxp);
-       isc_work_enqueue(loop, master_dump_cb, master_dump_done_cb, dctx);
+       dns_dumpctx_enqueue(loop, dctx);
+       *dctxp = dctx;
 
        return ISC_R_SUCCESS;
 }
@@ -1834,8 +1828,8 @@ dns_master_dumpasync(isc_mem_t *mctx, dns_db_t *db, dns_dbversion_t *version,
        dctx->file = file;
        dctx->tmpfile = tempname;
 
-       dns_dumpctx_attach(dctx, dctxp);
-       isc_work_enqueue(loop, master_dump_cb, master_dump_done_cb, dctx);
+       dns_dumpctx_enqueue(loop, dctx);
+       *dctxp = dctx;
 
        return ISC_R_SUCCESS;