extern unsigned int dns_zone_mkey_day;
extern unsigned int dns_zone_mkey_month;
+extern size_t dns_adb_addrslimit;
+
static bool want_stats = false;
static char program_name[NAME_MAX] = "named";
static char absolute_conffile[PATH_MAX];
transferstuck = true;
} else if (!strncmp(option, "tat=", 4)) {
named_g_tat_interval = atoi(option + 4);
+ } else if (!strncmp(option, "adbaddrslimit=", 14)) {
+ size_t adb_addrslimit = atoi(option + 14);
+ if (adb_addrslimit < 1) {
+ named_main_earlyfatal("adbaddrslimit must be at "
+ "least 1");
+ }
+ dns_adb_addrslimit = adb_addrslimit;
} else {
fprintf(stderr, "unknown -T flag '%s'\n", option);
}
#define DNS_ADB_MINADBSIZE (1024U * 1024U) /*%< 1 Megabyte */
+/*
+ * Default and override for the per-find address limit, the sum of the number of
+ * A and AAAA RR from an ADB NS name resolution. When non-zero, this value is
+ * used instead of the default. Can be set via 'named -T adbaddrslimit=N' for
+ * testing.
+ */
+#define DEFAULT_ADDRSLIMIT 6
+size_t dns_adb_addrslimit = 0;
+
typedef ISC_LIST(dns_adbname_t) dns_adbnamelist_t;
typedef struct dns_adbnamehook dns_adbnamehook_t;
typedef ISC_LIST(dns_adbnamehook_t) dns_adbnamehooklist_t;
dns_adbaddrinfo_t *addrinfo;
dns_adbentry_t *entry;
int bucket;
+ size_t count = 0;
+ size_t limit = dns_adb_addrslimit != 0 ? dns_adb_addrslimit
+ : DEFAULT_ADDRSLIMIT;
bucket = DNS_ADB_INVALIDBUCKET;
inc_entry_refcnt(adb, entry, false);
ISC_LIST_APPEND(find->list, addrinfo, publink);
addrinfo = NULL;
+
+ if (++count >= limit) {
+ DP(ISC_LOG_DEBUG(3), "skipping addresses");
+ UNLOCK(&adb->entrylocks[bucket]);
+ return;
+ }
+
nextv4:
UNLOCK(&adb->entrylocks[bucket]);
bucket = DNS_ADB_INVALIDBUCKET;
inc_entry_refcnt(adb, entry, false);
ISC_LIST_APPEND(find->list, addrinfo, publink);
addrinfo = NULL;
+
+ if (++count >= limit) {
+ DP(ISC_LOG_DEBUG(3), "skipping addresses");
+ UNLOCK(&adb->entrylocks[bucket]);
+ return;
+ }
+
nextv6:
UNLOCK(&adb->entrylocks[bucket]);
bucket = DNS_ADB_INVALIDBUCKET;