summaryrefslogtreecommitdiff
path: root/lib/dns/zone.c
diff options
context:
space:
mode:
Diffstat (limited to 'lib/dns/zone.c')
-rw-r--r--lib/dns/zone.c81
1 files changed, 56 insertions, 25 deletions
diff --git a/lib/dns/zone.c b/lib/dns/zone.c
index 108aefbd9b4a..606c59b28b89 100644
--- a/lib/dns/zone.c
+++ b/lib/dns/zone.c
@@ -1,5 +1,5 @@
/*
- * Copyright (C) 2004-2010 Internet Systems Consortium, Inc. ("ISC")
+ * Copyright (C) 2004-2011 Internet Systems Consortium, Inc. ("ISC")
* Copyright (C) 1999-2003 Internet Software Consortium.
*
* Permission to use, copy, modify, and/or distribute this software for any
@@ -15,12 +15,13 @@
* PERFORMANCE OF THIS SOFTWARE.
*/
-/* $Id: zone.c,v 1.483.36.23 2010-12-14 00:48:22 marka Exp $ */
+/* $Id: zone.c,v 1.483.36.33 2011-07-21 06:23:20 marka Exp $ */
/*! \file */
#include <config.h>
#include <errno.h>
+#include <stdlib.h>
#include <isc/file.h>
#include <isc/mutex.h>
@@ -1326,6 +1327,7 @@ zone_load(dns_zone_t *zone, unsigned int flags) {
isc_time_t now;
isc_time_t loadtime, filetime;
dns_db_t *db = NULL;
+ isc_boolean_t rbt;
REQUIRE(DNS_ZONE_VALID(zone));
@@ -1341,14 +1343,15 @@ zone_load(dns_zone_t *zone, unsigned int flags) {
goto cleanup;
}
- if (zone->db != NULL && zone->masterfile == NULL) {
+
+ INSIST(zone->db_argc >= 1);
+
+ rbt = strcmp(zone->db_argv[0], "rbt") == 0 ||
+ strcmp(zone->db_argv[0], "rbt64") == 0;
+
+ if (zone->db != NULL && zone->masterfile == NULL && rbt) {
/*
- * The zone has no master file configured, but it already
- * has a database. It could be the built-in
- * version.bind. CH zone, a zone with a persistent
- * database being reloaded, or maybe a zone that
- * used to have a master file but whose configuration
- * was changed so that it no longer has one. Do nothing.
+ * The zone has no master file configured.
*/
result = ISC_R_SUCCESS;
goto cleanup;
@@ -1367,7 +1370,6 @@ zone_load(dns_zone_t *zone, unsigned int flags) {
goto cleanup;
}
-
/*
* Store the current time before the zone is loaded, so that if the
* file changes between the time of the load and the time that
@@ -1407,21 +1409,20 @@ zone_load(dns_zone_t *zone, unsigned int flags) {
}
}
- INSIST(zone->db_argc >= 1);
-
/*
- * Built in zones don't need to be reloaded.
+ * Built in zones (with the exception of empty zones) don't need
+ * to be reloaded.
*/
if (zone->type == dns_zone_master &&
strcmp(zone->db_argv[0], "_builtin") == 0 &&
+ (zone->db_argc < 2 || strcmp(zone->db_argv[1], "empty") != 0) &&
DNS_ZONE_FLAG(zone, DNS_ZONEFLG_LOADED)) {
result = ISC_R_SUCCESS;
goto cleanup;
}
if ((zone->type == dns_zone_slave || zone->type == dns_zone_stub) &&
- (strcmp(zone->db_argv[0], "rbt") == 0 ||
- strcmp(zone->db_argv[0], "rbt64") == 0)) {
+ rbt) {
if (zone->masterfile == NULL ||
!isc_file_exists(zone->masterfile)) {
if (zone->masterfile != NULL) {
@@ -1541,7 +1542,8 @@ get_master_options(dns_zone_t *zone) {
if (DNS_ZONE_OPTION(zone, DNS_ZONEOPT_CHECKWILDCARD))
options |= DNS_MASTER_CHECKWILDCARD;
if (zone->type == dns_zone_master &&
- (zone->update_acl != NULL || zone->ssutable != NULL))
+ ((zone->update_acl != NULL && !dns_acl_isnone(zone->update_acl)) ||
+ zone->ssutable != NULL))
options |= DNS_MASTER_RESIGN;
return (options);
}
@@ -1933,8 +1935,7 @@ zone_check_glue(dns_zone_t *zone, dns_db_t *db, dns_name_t *name,
dns_rdataset_disassociate(&aaaa);
return (answer);
}
- } else
- tresult = result;
+ }
dns_name_format(owner, ownerbuf, sizeof ownerbuf);
dns_name_format(name, namebuf, sizeof namebuf);
@@ -5325,6 +5326,7 @@ zone_nsec3chain(dns_zone_t *zone) {
LOCK_ZONE(zone);
zone_needdump(zone, DNS_DUMP_DELAY);
+ DNS_ZONE_SETFLAG(zone, DNS_ZONEFLG_NEEDNOTIFY);
UNLOCK_ZONE(zone);
done:
@@ -5527,7 +5529,7 @@ zone_sign(dns_zone_t *zone) {
isc_boolean_t build_nsec3 = ISC_FALSE, build_nsec = ISC_FALSE;
isc_boolean_t first;
isc_result_t result;
- isc_stdtime_t now, inception, soaexpire, expire, stop;
+ isc_stdtime_t now, inception, soaexpire, expire;
isc_uint32_t jitter;
unsigned int i;
unsigned int nkeys = 0;
@@ -5582,7 +5584,6 @@ zone_sign(dns_zone_t *zone) {
*/
isc_random_get(&jitter);
expire = soaexpire - jitter % 3600;
- stop = now + 5;
check_ksk = DNS_ZONE_OPTION(zone, DNS_ZONEOPT_UPDATECHECKKSK);
if (check_ksk)
@@ -6098,7 +6099,8 @@ void
dns_zone_markdirty(dns_zone_t *zone) {
LOCK_ZONE(zone);
- set_resigntime(zone); /* XXXMPA make separate call back */
+ if (zone->type == dns_zone_master)
+ set_resigntime(zone); /* XXXMPA make separate call back */
zone_needdump(zone, DNS_DUMP_DELAY);
UNLOCK_ZONE(zone);
}
@@ -6169,7 +6171,7 @@ dns_zone_refresh(dns_zone_t *zone) {
isc_interval_set(&i, isc_random_jitter(zone->retry, zone->retry / 4),
0);
result = isc_time_nowplusinterval(&zone->refreshtime, &i);
- if (result |= ISC_R_SUCCESS)
+ if (result != ISC_R_SUCCESS)
dns_zone_log(zone, ISC_LOG_WARNING,
"isc_time_nowplusinterval() failed: %s",
dns_result_totext(result));
@@ -7523,7 +7525,7 @@ refresh_callback(isc_task_t *task, isc_event_t *event) {
goto tcp_transfer;
}
dns_zone_log(zone, ISC_LOG_DEBUG(1),
- "refresh: skipped tcp fallback"
+ "refresh: skipped tcp fallback "
"as master %s (source %s) is "
"unreachable (cached)",
master, source);
@@ -7704,6 +7706,7 @@ refresh_callback(isc_task_t *task, isc_event_t *event) {
} else
zone_debuglog(zone, me, 1, "serial: new %u, old not loaded",
serial);
+
if (!DNS_ZONE_FLAG(zone, DNS_ZONEFLG_LOADED) ||
DNS_ZONE_FLAG(zone, DNS_ZONEFLG_FORCEXFER) ||
isc_serial_gt(serial, oldserial)) {
@@ -8278,6 +8281,7 @@ ns_query(dns_zone_t *zone, dns_rdataset_t *soardataset, dns_stub_t *stub) {
* XXX Optimisation: Create message when zone is setup and reuse.
*/
result = create_query(zone, dns_rdatatype_ns, &message);
+ INSIST(result == ISC_R_SUCCESS);
INSIST(zone->masterscnt > 0);
INSIST(zone->curmaster < zone->masterscnt);
@@ -8351,6 +8355,7 @@ ns_query(dns_zone_t *zone, dns_rdataset_t *soardataset, dns_stub_t *stub) {
break;
default:
result = ISC_R_NOTIMPLEMENTED;
+ POST(result);
goto cleanup;
}
timeout = 15;
@@ -10472,6 +10477,28 @@ dns_zone_first(dns_zonemgr_t *zmgr, dns_zone_t **first) {
return (ISC_R_SUCCESS);
}
+/*
+ * Size of the zone task table. For best results, this should be a
+ * prime number, approximately 1% of the maximum number of authoritative
+ * zones expected to be served by this server.
+ */
+#define DEFAULT_ZONE_TASKS 101
+static int
+calculate_zone_tasks(void) {
+ int ntasks = DEFAULT_ZONE_TASKS;
+
+#ifdef HAVE_GETENV
+ char *env = getenv("BIND9_ZONE_TASKS_HINT");
+ if (env != NULL)
+ ntasks = atoi(env);
+
+ if (ntasks < DEFAULT_ZONE_TASKS)
+ ntasks = DEFAULT_ZONE_TASKS;
+#endif
+
+ return (ntasks);
+}
+
/***
*** Zone manager.
***/
@@ -10484,6 +10511,7 @@ dns_zonemgr_create(isc_mem_t *mctx, isc_taskmgr_t *taskmgr,
dns_zonemgr_t *zmgr;
isc_result_t result;
isc_interval_t interval;
+ int zone_tasks = calculate_zone_tasks();
zmgr = isc_mem_get(mctx, sizeof(*zmgr));
if (zmgr == NULL)
@@ -10509,11 +10537,14 @@ dns_zonemgr_create(isc_mem_t *mctx, isc_taskmgr_t *taskmgr,
zmgr->transfersperns = 2;
/* Create the zone task pool. */
- result = isc_taskpool_create(taskmgr, mctx,
- 8 /* XXX */, 2, &zmgr->zonetasks);
+ result = isc_taskpool_create(taskmgr, mctx, zone_tasks, 2,
+ &zmgr->zonetasks);
if (result != ISC_R_SUCCESS)
goto free_rwlock;
+ isc_log_write(dns_lctx, DNS_LOGCATEGORY_GENERAL, DNS_LOGMODULE_ZONE,
+ ISC_LOG_NOTICE, "Using %d tasks for zone loading", zone_tasks);
+
/* Create a single task for queueing of SOA queries. */
result = isc_task_create(taskmgr, 1, &zmgr->task);
if (result != ISC_R_SUCCESS)