]> git.ipfire.org Git - thirdparty/bind9.git/commitdiff
Parse "parental-agents" configuration
authorMatthijs Mekking <matthijs@isc.org>
Tue, 11 May 2021 12:46:38 +0000 (14:46 +0200)
committerMatthijs Mekking <matthijs@isc.org>
Wed, 30 Jun 2021 15:28:48 +0000 (17:28 +0200)
Parse the new "parental-agents" configuration and store it in the zone
structure.

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

index 9956e351fa86ed6e0455e52b6151ab5b71f89d24..873da2784933cf3e48bcffff78ba3d45232305c2 100644 (file)
@@ -1710,6 +1710,28 @@ named_zone_configure(const cfg_obj_t *config, const cfg_obj_t *vconfig,
                                          dns_zone_clearforwardacl));
        }
 
+       /*%
+        * Configure parental agents, applies to primary and secondary zones.
+        */
+       if (ztype == dns_zone_master || ztype == dns_zone_slave) {
+               obj = NULL;
+               (void)cfg_map_get(zoptions, "parental-agents", &obj);
+               if (obj != NULL) {
+                       dns_ipkeylist_t ipkl;
+                       dns_ipkeylist_init(&ipkl);
+                       RETERR(named_config_getipandkeylist(
+                               config, "parental-agents", obj, mctx, &ipkl));
+                       result = dns_zone_setparentals(zone, ipkl.addrs,
+                                                      ipkl.keys, ipkl.tlss,
+                                                      ipkl.count);
+                       dns_ipkeylist_clear(mctx, &ipkl);
+                       RETERR(result);
+               } else {
+                       RETERR(dns_zone_setparentals(zone, NULL, NULL, NULL,
+                                                    0));
+               }
+       }
+
        /*%
         * Primary master functionality.
         */
index a981f0dd231f58909bbb9f37547d15e8b303dc03..dc8350c6e36a866e21d27f2a6c66be21d02d7b0e 100644 (file)
@@ -642,12 +642,30 @@ dns_zone_setprimaries(dns_zone_t *zone, const isc_sockaddr_t *primaries,
  *\li  'zone' to be a valid zone.
  *\li  'primaries' array of isc_sockaddr_t with port set or NULL.
  *\li  'count' the number of primaries.
- *\li      'keynames' array of dns_name_t's for tsig keys or NULL.
+ *\li  'keynames' array of dns_name_t's for tsig keys or NULL.
  *
- *  \li    dns_zone_setprimaries() is just a wrapper to setprimarieswithkeys(),
- *      passing NULL in the keynames field.
+ *\li  If 'primaries' is NULL then 'count' must be zero.
  *
- * \li If 'primaries' is NULL then 'count' must be zero.
+ * Returns:
+ *\li  #ISC_R_SUCCESS
+ *\li  #ISC_R_NOMEMORY
+ *\li      Any result dns_name_dup() can return, if keynames!=NULL
+ */
+
+isc_result_t
+dns_zone_setparentals(dns_zone_t *zone, const isc_sockaddr_t *parentals,
+                     dns_name_t **keynames, dns_name_t **tlsnames,
+                     uint32_t count);
+/*%<
+ *     Set the list of parental agents for the zone.
+ *
+ * Require:
+ *\li  'zone' to be a valid zone.
+ *\li  'parentals' array of isc_sockaddr_t with port set or NULL.
+ *\li  'count' the number of primaries.
+ *\li  'keynames' array of dns_name_t's for tsig keys or NULL.
+ *
+ *\li  If 'parentals' is NULL then 'count' must be zero.
  *
  * Returns:
  *\li  #ISC_R_SUCCESS
index 46a0aff8f94e6528fee23fcba5355d705649c158..3211c54de85755cf1c05890d50e3fa4dd8159145 100644 (file)
@@ -281,6 +281,15 @@ struct dns_zone {
        unsigned int masterscnt;
        unsigned int curmaster;
        isc_sockaddr_t masteraddr;
+
+       isc_sockaddr_t *parentals;
+       isc_dscp_t *parentaldscps;
+       dns_name_t **parentalkeynames;
+       dns_name_t **parentaltlsnames;
+       dns_dnsseckeylist_t checkds_ok;
+       unsigned int parentalscnt;
+       isc_sockaddr_t parentaladdr;
+
        dns_notifytype_t notifytype;
        isc_sockaddr_t *notify;
        dns_name_t **notifykeynames;
@@ -1129,6 +1138,16 @@ free_refs:
        return (result);
 }
 
+static void
+clear_keylist(dns_dnsseckeylist_t *list, isc_mem_t *mctx) {
+       dns_dnsseckey_t *key;
+       while (!ISC_LIST_EMPTY(*list)) {
+               key = ISC_LIST_HEAD(*list);
+               ISC_LIST_UNLINK(*list, key, link);
+               dns_dnsseckey_destroy(mctx, &key);
+       }
+}
+
 /*
  * Free a zone.  Because we require that there be no more
  * outstanding events or references, no locking is necessary.
@@ -1222,6 +1241,10 @@ zone_free(dns_zone_t *zone) {
        if (zone->kasp != NULL) {
                dns_kasp_detach(&zone->kasp);
        }
+       if (!ISC_LIST_EMPTY(zone->checkds_ok)) {
+               clear_keylist(&zone->checkds_ok, zone->mctx);
+       }
+
        zone->journalsize = -1;
        if (zone->journal != NULL) {
                isc_mem_free(zone->mctx, zone->journal);
@@ -1251,6 +1274,8 @@ zone_free(dns_zone_t *zone) {
                dns_catz_catzs_detach(&zone->catzs);
        }
        zone_freedbargs(zone);
+       RUNTIME_CHECK(dns_zone_setparentals(zone, NULL, NULL, NULL, 0) ==
+                     ISC_R_SUCCESS);
        RUNTIME_CHECK(dns_zone_setprimaries(zone, NULL, NULL, NULL, 0) ==
                      ISC_R_SUCCESS);
        RUNTIME_CHECK(dns_zone_setalsonotify(zone, NULL, NULL, NULL, NULL, 0) ==
@@ -6305,6 +6330,62 @@ unlock:
        return (result);
 }
 
+isc_result_t
+dns_zone_setparentals(dns_zone_t *zone, const isc_sockaddr_t *parentals,
+                     dns_name_t **keynames, dns_name_t **tlsnames,
+                     uint32_t count) {
+       isc_result_t result = ISC_R_SUCCESS;
+       isc_sockaddr_t *newaddrs = NULL;
+       isc_dscp_t *newdscps = NULL;
+       dns_name_t **newkeynames = NULL;
+       dns_name_t **newtlsnames = NULL;
+
+       REQUIRE(DNS_ZONE_VALID(zone));
+       REQUIRE(count == 0 || parentals != NULL);
+       if (keynames != NULL || tlsnames != NULL) {
+               REQUIRE(count != 0);
+       }
+
+       LOCK_ZONE(zone);
+
+       clear_serverslist(&zone->parentals, &zone->parentaldscps,
+                         &zone->parentalkeynames, &zone->parentaltlsnames,
+                         &zone->parentalscnt, zone->mctx);
+       /*
+        * If count == 0, don't allocate any space for parentals, or keynames
+        * so internally, those pointers are NULL if count == 0
+        */
+       if (count == 0) {
+               goto unlock;
+       }
+
+       /*
+        * Now set up the parentals and parental key lists
+        */
+       result = set_serverslist(count, parentals, &newaddrs, NULL, &newdscps,
+                                keynames, &newkeynames, tlsnames, &newtlsnames,
+                                zone->mctx);
+       INSIST(newdscps == NULL);
+       if (result != ISC_R_SUCCESS) {
+               goto unlock;
+       }
+
+       /*
+        * Everything is ok so attach to the zone.
+        */
+       zone->parentals = newaddrs;
+       zone->parentaldscps = newdscps;
+       zone->parentalkeynames = newkeynames;
+       zone->parentaltlsnames = newtlsnames;
+       zone->parentalscnt = count;
+
+       dns_zone_log(zone, ISC_LOG_NOTICE, "checkds: set %u parentals", count);
+
+unlock:
+       UNLOCK_ZONE(zone);
+       return (result);
+}
+
 isc_result_t
 dns_zone_getdb(dns_zone_t *zone, dns_db_t **dpb) {
        isc_result_t result = ISC_R_SUCCESS;
@@ -19617,16 +19698,6 @@ cleanup:
        return (result);
 }
 
-static void
-clear_keylist(dns_dnsseckeylist_t *list, isc_mem_t *mctx) {
-       dns_dnsseckey_t *key;
-       while (!ISC_LIST_EMPTY(*list)) {
-               key = ISC_LIST_HEAD(*list);
-               ISC_LIST_UNLINK(*list, key, link);
-               dns_dnsseckey_destroy(mctx, &key);
-       }
-}
-
 /* Called once; *timep should be set to the current time. */
 static isc_result_t
 next_keyevent(dst_key_t *key, isc_stdtime_t *timep) {