]> git.ipfire.org Git - thirdparty/bind9.git/commitdiff
Fix a bug in dns_zone_getprimaryaddr()
authorAram Sargsyan <aram@isc.org>
Thu, 27 Feb 2025 11:52:30 +0000 (11:52 +0000)
committerArаm Sаrgsyаn <aram@isc.org>
Fri, 28 Feb 2025 15:33:37 +0000 (15:33 +0000)
When all the addresses were already iterated over, the
dns_remote_curraddr() function asserts. So before calling it,
dns_zone_getprimaryaddr() now checks the address list using the
dns_remote_done() function. This also means that instead of
returning 'isc_sockaddr_t' it now returns 'isc_result_t' and
writes the primary's address into the provided pointer only when
returning success.

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

index 4df131de2f939215ea8072ebfb1a43f8b5453d82..e872d492b35879ad83652bfe3cd5d5a27c8bf231 100644 (file)
@@ -1617,9 +1617,13 @@ xfrin_xmlrender(dns_zone_t *zone, void *arg) {
                isc_sockaddr_format(addrp, addr_buf, sizeof(addr_buf));
                TRY0(xmlTextWriterWriteString(writer, ISC_XMLCHAR addr_buf));
        } else if (is_presoa) {
-               addr = dns_zone_getprimaryaddr(zone);
-               isc_sockaddr_format(&addr, addr_buf, sizeof(addr_buf));
-               TRY0(xmlTextWriterWriteString(writer, ISC_XMLCHAR addr_buf));
+               if (dns_zone_getprimaryaddr(zone, &addr) == ISC_R_SUCCESS) {
+                       isc_sockaddr_format(&addr, addr_buf, sizeof(addr_buf));
+                       TRY0(xmlTextWriterWriteString(writer,
+                                                     ISC_XMLCHAR addr_buf));
+               } else {
+                       TRY0(xmlTextWriterWriteString(writer, ISC_XMLCHAR "-"));
+               }
        } else {
                TRY0(xmlTextWriterWriteString(writer, ISC_XMLCHAR "-"));
        }
@@ -2671,10 +2675,15 @@ xfrin_jsonrender(dns_zone_t *zone, void *arg) {
                json_object_object_add(xfrinobj, "remoteaddr",
                                       json_object_new_string(addr_buf));
        } else if (is_presoa) {
-               addr = dns_zone_getprimaryaddr(zone);
-               isc_sockaddr_format(&addr, addr_buf, sizeof(addr_buf));
-               json_object_object_add(xfrinobj, "remoteaddr",
-                                      json_object_new_string(addr_buf));
+               if (dns_zone_getprimaryaddr(zone, &addr) == ISC_R_SUCCESS) {
+                       isc_sockaddr_format(&addr, addr_buf, sizeof(addr_buf));
+                       json_object_object_add(
+                               xfrinobj, "remoteaddr",
+                               json_object_new_string(addr_buf));
+               } else {
+                       json_object_object_add(xfrinobj, "remoteaddr",
+                                              json_object_new_string("-"));
+               }
        } else {
                json_object_object_add(xfrinobj, "remoteaddr",
                                       json_object_new_string("-"));
index 63b39eb1b87e5bf72cd7d9f951e6255c60e26854..02ae1e99d5ed5c35969fedc767e148718fb9d493 100644 (file)
@@ -1539,14 +1539,19 @@ dns_zone_getsourceaddr(dns_zone_t *zone);
  * \li 'zone' has a non-empty primaries list.
  */
 
-isc_sockaddr_t
-dns_zone_getprimaryaddr(dns_zone_t *zone);
+isc_result_t
+dns_zone_getprimaryaddr(dns_zone_t *zone, isc_sockaddr_t *dest);
 /*%<
- * Get the zone's current primary server.
+ * Get the zone's current primary server into '*dest'.
  *
  * Requires:
  * \li 'zone' to be a valid zone.
  * \li 'zone' has a non-empty primaries list.
+ * \li 'dest' != NULL.
+ *
+ * Returns:
+ *\li  #ISC_R_SUCCESS if the current primary server was found
+ *\li  #ISC_R_NOMORE if all the primaries were already iterated over
  */
 
 isc_time_t
index ca1d48e1eec63a7c018a8a5585793f1201b64184..536c8f3752aec28c5237ec637b0b78e4632d732e 100644 (file)
@@ -18385,18 +18385,22 @@ dns_zone_getsourceaddr(dns_zone_t *zone) {
        return sourceaddr;
 }
 
-isc_sockaddr_t
-dns_zone_getprimaryaddr(dns_zone_t *zone) {
-       isc_sockaddr_t curraddr;
+isc_result_t
+dns_zone_getprimaryaddr(dns_zone_t *zone, isc_sockaddr_t *dest) {
+       isc_result_t result = ISC_R_NOMORE;
 
        REQUIRE(DNS_ZONE_VALID(zone));
+       REQUIRE(dest != NULL);
 
        LOCK_ZONE(zone);
        INSIST(dns_remote_count(&zone->primaries) > 0);
-       curraddr = dns_remote_curraddr(&zone->primaries);
+       if (!dns_remote_done(&zone->primaries)) {
+               *dest = dns_remote_curraddr(&zone->primaries);
+               result = ISC_R_SUCCESS;
+       }
        UNLOCK_ZONE(zone);
 
-       return curraddr;
+       return result;
 }
 
 isc_time_t