]> git.ipfire.org Git - thirdparty/bind9.git/commitdiff
store the zone configuration object in the zone
authorEvan Hunt <each@isc.org>
Wed, 22 Oct 2025 05:56:27 +0000 (22:56 -0700)
committerEvan Hunt <each@isc.org>
Thu, 23 Oct 2025 20:01:06 +0000 (13:01 -0700)
when configuring a zone, we can now save the zone's configuration
object in the zone itself by calling dns_zone_setcfg().  this can
then be used by "rndc showzone" to print the zone's configuration,
which is simpler than searching for it using the new-zones
configuration, and allows it to work even if "allow-new-zones"
is disabled.

bin/named/server.c
bin/named/zoneconf.c
lib/dns/include/dns/zone.h
lib/dns/zone.c

index 936d3979754cad20fc1b2b523e0bd760e94af5d5..5fdfedd08298c520a82e02a090299cfc70435381 100644 (file)
@@ -7546,7 +7546,7 @@ cleanup:
        return result;
 }
 
-#else /* HAVE_LMDB */
+#else  /* HAVE_LMDB */
 
 static isc_result_t
 data_to_cfg(dns_view_t *view, MDB_val *key, MDB_val *data, isc_buffer_t **text,
@@ -7786,70 +7786,6 @@ configure_newzones(dns_view_t *view, cfg_obj_t *config, cfg_obj_t *vconfig,
 
        return result;
 }
-
-static isc_result_t
-get_newzone_config(dns_view_t *view, const char *zonename,
-                  cfg_obj_t **zoneconfig) {
-       isc_result_t result;
-       int status;
-       cfg_obj_t *zoneconf = NULL;
-       isc_buffer_t *text = NULL;
-       MDB_txn *txn = NULL;
-       MDB_dbi dbi;
-       MDB_val key, data;
-       char zname[DNS_NAME_FORMATSIZE];
-       dns_fixedname_t fname;
-       dns_name_t *name;
-       isc_buffer_t b;
-
-       INSIST(zoneconfig != NULL && *zoneconfig == NULL);
-
-       LOCK(&view->new_zone_lock);
-
-       CHECK(nzd_open(view, MDB_RDONLY, &txn, &dbi));
-
-       isc_log_write(NAMED_LOGCATEGORY_GENERAL, NAMED_LOGMODULE_SERVER,
-                     ISC_LOG_INFO,
-                     "loading NZD config from '%s' "
-                     "for zone '%s'",
-                     view->new_zone_db, zonename);
-
-       /* Normalize zone name */
-       isc_buffer_constinit(&b, zonename, strlen(zonename));
-       isc_buffer_add(&b, strlen(zonename));
-       name = dns_fixedname_initname(&fname);
-       CHECK(dns_name_fromtext(name, &b, dns_rootname, DNS_NAME_DOWNCASE));
-       dns_name_format(name, zname, sizeof(zname));
-
-       key.mv_data = zname;
-       key.mv_size = strlen(zname);
-
-       status = mdb_get(txn, dbi, &key, &data);
-       if (status != MDB_SUCCESS) {
-               CHECK(ISC_R_FAILURE);
-       }
-
-       CHECK(data_to_cfg(view, &key, &data, &text, &zoneconf));
-
-       *zoneconfig = zoneconf;
-       zoneconf = NULL;
-       result = ISC_R_SUCCESS;
-
-cleanup:
-       (void)nzd_close(&txn, false);
-
-       UNLOCK(&view->new_zone_lock);
-
-       if (zoneconf != NULL) {
-               cfg_obj_detach(&zoneconf);
-       }
-       if (text != NULL) {
-               isc_buffer_free(&text);
-       }
-
-       return result;
-}
-
 #endif /* HAVE_LMDB */
 
 #define APPLY_CONFIGURATION_SUBROUTINE_LOG                               \
@@ -14045,72 +13981,6 @@ cleanup:
        return result;
 }
 
-static const cfg_obj_t *
-find_name_in_list_from_map(const cfg_obj_t *config,
-                          const char *map_key_for_list, const char *name,
-                          bool redirect) {
-       const cfg_obj_t *list = NULL;
-       const cfg_obj_t *obj = NULL;
-       dns_fixedname_t fixed1, fixed2;
-       dns_name_t *name1 = NULL, *name2 = NULL;
-       isc_result_t result;
-
-       if (strcmp(map_key_for_list, "zone") == 0) {
-               name1 = dns_fixedname_initname(&fixed1);
-               name2 = dns_fixedname_initname(&fixed2);
-               result = dns_name_fromstring(name1, name, dns_rootname, 0,
-                                            NULL);
-               RUNTIME_CHECK(result == ISC_R_SUCCESS);
-       }
-
-       cfg_map_get(config, map_key_for_list, &list);
-       CFG_LIST_FOREACH(list, element) {
-               const char *vname = NULL;
-
-               obj = cfg_listelt_value(element);
-               INSIST(obj != NULL);
-               vname = cfg_obj_asstring(cfg_tuple_get(obj, "name"));
-               if (vname == NULL) {
-                       obj = NULL;
-                       continue;
-               }
-
-               if (name1 != NULL) {
-                       result = dns_name_fromstring(name2, vname, dns_rootname,
-                                                    0, NULL);
-                       if (result == ISC_R_SUCCESS &&
-                           dns_name_equal(name1, name2))
-                       {
-                               const cfg_obj_t *zoptions =
-                                       cfg_tuple_get(obj, "options");
-                               const cfg_obj_t *typeobj = NULL;
-
-                               if (zoptions != NULL) {
-                                       const cfg_obj_t *toptions =
-                                               named_zone_templateopts(
-                                                       config, zoptions);
-                                       named_config_findopt(zoptions, toptions,
-                                                            "type", &typeobj);
-                               }
-                               if (redirect && typeobj != NULL &&
-                                   strcasecmp(cfg_obj_asstring(typeobj),
-                                              "redirect") == 0)
-                               {
-                                       break;
-                               } else if (!redirect) {
-                                       break;
-                               }
-                       }
-               } else if (strcasecmp(vname, name) == 0) {
-                       break;
-               }
-
-               obj = NULL;
-       }
-
-       return obj;
-}
-
 static void
 emitzone(void *arg, const char *buf, int len) {
        ns_dzarg_t *dzarg = arg;
@@ -14130,16 +14000,9 @@ isc_result_t
 named_server_showzone(named_server_t *server, isc_lex_t *lex,
                      isc_buffer_t **text) {
        isc_result_t result;
-       const cfg_obj_t *vconfig = NULL, *zconfig = NULL;
+       const cfg_obj_t *zconfig = NULL;
        char zonename[DNS_NAME_FORMATSIZE];
-       const cfg_obj_t *map;
-       dns_view_t *view = NULL;
        dns_zone_t *zone = NULL;
-       ns_cfgctx_t *cfg = NULL;
-#ifdef HAVE_LMDB
-       cfg_obj_t *nzconfig = NULL;
-#endif /* HAVE_LMDB */
-       bool added, redirect;
        ns_dzarg_t dzarg;
 
        REQUIRE(text != NULL);
@@ -14151,51 +14014,9 @@ named_server_showzone(named_server_t *server, isc_lex_t *lex,
                goto cleanup;
        }
 
-       redirect = dns_zone_gettype(zone) == dns_zone_redirect;
-       added = dns_zone_getadded(zone);
-       view = dns_zone_getview(zone);
+       zconfig = dns_zone_getcfg(zone);
        dns_zone_detach(&zone);
 
-       cfg = (ns_cfgctx_t *)view->new_zone_config;
-       if (cfg == NULL) {
-               result = ISC_R_FAILURE;
-               goto cleanup;
-       }
-
-       if (!added) {
-               /* Find the view statement */
-               vconfig = find_name_in_list_from_map(cfg->config, "view",
-                                                    view->name, false);
-
-               /* Find the zone statement */
-               if (vconfig != NULL) {
-                       map = cfg_tuple_get(vconfig, "options");
-               } else {
-                       map = cfg->config;
-               }
-
-               zconfig = find_name_in_list_from_map(map, "zone", zonename,
-                                                    redirect);
-       }
-
-#ifndef HAVE_LMDB
-       if (zconfig == NULL && cfg->nzf_config != NULL) {
-               zconfig = find_name_in_list_from_map(cfg->nzf_config, "zone",
-                                                    zonename, redirect);
-       }
-#else  /* HAVE_LMDB */
-       if (zconfig == NULL) {
-               const cfg_obj_t *zlist = NULL;
-               CHECK(get_newzone_config(view, zonename, &nzconfig));
-               CHECK(cfg_map_get(nzconfig, "zone", &zlist));
-               if (!cfg_obj_islist(zlist)) {
-                       CHECK(ISC_R_FAILURE);
-               }
-
-               zconfig = cfg_listelt_value(cfg_list_first(zlist));
-       }
-#endif /* HAVE_LMDB */
-
        if (zconfig == NULL) {
                CHECK(ISC_R_NOTFOUND);
        }
@@ -14212,11 +14033,6 @@ named_server_showzone(named_server_t *server, isc_lex_t *lex,
        result = ISC_R_SUCCESS;
 
 cleanup:
-#ifdef HAVE_LMDB
-       if (nzconfig != NULL) {
-               cfg_obj_detach(&nzconfig);
-       }
-#endif /* HAVE_LMDB */
        if (isc_buffer_usedlength(*text) > 0) {
                (void)putnull(text);
        }
index ae3d95bda1466faf9aeb97160aad843ef56f0c54..ae82d76feb8a7ea8793635d7f5ca8999838d4b5a 100644 (file)
@@ -869,6 +869,12 @@ process_notifytype(dns_notifytype_t ntype, dns_zonetype_t ztype,
        return dns_notifytype_explicit;
 }
 
+static void
+detach_cfg(void *arg) {
+       cfg_obj_t *cfg = (cfg_obj_t *)arg;
+       cfg_obj_detach(&cfg);
+}
+
 isc_result_t
 named_zone_configure(const cfg_obj_t *config, const cfg_obj_t *vconfig,
                     const cfg_obj_t *zconfig, cfg_aclconfctx_t *aclctx,
@@ -1908,6 +1914,11 @@ named_zone_configure(const cfg_obj_t *config, const cfg_obj_t *vconfig,
                break;
        }
 
+       /* Save the configuration for later use */
+       cfg_obj_t *cfg = UNCONST(zconfig);
+       cfg_obj_ref(cfg);
+       dns_zone_setcfg(zone, (void *)cfg, detach_cfg);
+
        result = ISC_R_SUCCESS;
 
 cleanup:
index 24cd59fd166058a53a470bbd30ca708a6938003e..7a7a8325cf894ab54a3afd31dd5a5bc90b013eb2 100644 (file)
@@ -2777,6 +2777,25 @@ dns_zone_unloadplugins(dns_zone_t *zone);
  * \li 'zone' to be a valid zone.
  */
 
+void
+dns_zone_setcfg(dns_zone_t *zone, void *cfg, void (*cfg_detach)(void *));
+/*%<
+ * Set a pointer to the configuration object for 'zone', which can be
+ * used later to dump the configuration status.
+ *
+ * Requires:
+ * \li 'zone' to be a valid zone.
+ */
+void *
+dns_zone_getcfg(dns_zone_t *zone);
+/*%<
+ * Return a pointer to the configuration object for 'zone', that was
+ * previously set using _setcfg().
+ *
+ * Requires:
+ * \li 'zone' to be a valid zone.
+ */
+
 #if DNS_ZONE_TRACE
 #define dns_zone_ref(ptr)   dns_zone__ref(ptr, __func__, __FILE__, __LINE__)
 #define dns_zone_unref(ptr) dns_zone__unref(ptr, __func__, __FILE__, __LINE__)
index b14b7fffb48ea92b6abce4bda1fccc1a9855628d..d4275f24d361860280b75f5ac1308a5a5fc82744 100644 (file)
@@ -538,6 +538,10 @@ struct dns_zone {
        void (*plugins_free)(isc_mem_t *, void **);
        void *hooktable;
        void (*hooktable_free)(isc_mem_t *, void **);
+
+       /* Configuration object */
+       void *cfg;
+       void (*cfg_detach)(void *);
 };
 
 #define zonediff_init(z, d)                \
@@ -15343,6 +15347,9 @@ zone_shutdown(void *arg) {
                dns_zonemgr_releasezone(zone->zmgr, zone);
        }
 
+       /* Detach the zone configuration pointer */
+       dns_zone_setcfg(zone, NULL, NULL);
+
        LOCK_ZONE(zone);
        INSIST(zone != zone->raw);
 
@@ -24908,3 +24915,22 @@ dns_zone_unloadplugins(dns_zone_t *zone) {
                zone->plugins_free = NULL;
        }
 }
+
+void
+dns_zone_setcfg(dns_zone_t *zone, void *cfg, void (*cfg_detach)(void *)) {
+       REQUIRE(DNS_ZONE_VALID(zone));
+
+       if (zone->cfg != NULL && zone->cfg_detach != NULL) {
+               zone->cfg_detach(zone->cfg);
+               zone->cfg = NULL;
+       }
+       zone->cfg = cfg;
+       zone->cfg_detach = cfg_detach;
+}
+
+void *
+dns_zone_getcfg(dns_zone_t *zone) {
+       REQUIRE(DNS_ZONE_VALID(zone));
+
+       return zone->cfg;
+}