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.c178
1 files changed, 87 insertions, 91 deletions
diff --git a/lib/dns/zone.c b/lib/dns/zone.c
index 01ff97b11dcbc..7a9825bd96b02 100644
--- a/lib/dns/zone.c
+++ b/lib/dns/zone.c
@@ -2639,8 +2639,8 @@ integrity_checks(dns_zone_t *zone, dns_db_t *db) {
checkspf:
/*
- * Check if there is a type TXT spf record without a type SPF
- * RRset being present.
+ * Check if there is a type SPF record without an
+ * SPF-formatted type TXT record also being present.
*/
if (!DNS_ZONE_OPTION(zone, DNS_ZONEOPT_CHECKSPF))
goto next;
@@ -2669,16 +2669,13 @@ integrity_checks(dns_zone_t *zone, dns_db_t *db) {
dns_rdataset_disassociate(&rdataset);
notxt:
- if (have_spf != have_txt) {
+ if (have_spf && !have_txt) {
char namebuf[DNS_NAME_FORMATSIZE];
- const char *found = have_txt ? "TXT" : "SPF";
- const char *need = have_txt ? "SPF" : "TXT";
dns_name_format(name, namebuf, sizeof(namebuf));
- dns_zone_log(zone, ISC_LOG_WARNING, "'%s' found SPF/%s "
- "record but no SPF/%s record found, add "
- "matching type %s record", namebuf, found,
- need, need);
+ dns_zone_log(zone, ISC_LOG_WARNING, "'%s' found type "
+ "SPF record but no SPF TXT record found, "
+ "add matching type TXT record", namebuf);
}
next:
@@ -4567,6 +4564,21 @@ zone_get_from_db(dns_zone_t *zone, dns_db_t *db, unsigned int *nscount,
dns_db_currentversion(db, &version);
+ if (nscount != NULL)
+ *nscount = 0;
+ if (soacount != NULL)
+ *soacount = 0;
+ if (serial != NULL)
+ *serial = 0;
+ if (refresh != NULL)
+ *refresh = 0;
+ if (retry != NULL)
+ *retry = 0;
+ if (expire != NULL)
+ *expire = 0;
+ if (errors != NULL)
+ *errors = 0;
+
node = NULL;
result = dns_db_findnode(db, &zone->origin, ISC_FALSE, &node);
if (result != ISC_R_SUCCESS) {
@@ -8544,8 +8556,10 @@ keyfetch_done(isc_task_t *task, isc_event_t *event) {
trust_key(zone, keyname, &dnskey, mctx);
}
- if (!deletekey)
+ if (!deletekey) {
+ INSIST(newkey || updatekey);
set_refreshkeytimer(zone, &keydata, now);
+ }
}
/*
@@ -10933,70 +10947,25 @@ create_query(dns_zone_t *zone, dns_rdatatype_t rdtype,
static isc_result_t
add_opt(dns_message_t *message, isc_uint16_t udpsize, isc_boolean_t reqnsid) {
- dns_rdataset_t *rdataset = NULL;
- dns_rdatalist_t *rdatalist = NULL;
- dns_rdata_t *rdata = NULL;
isc_result_t result;
-
- result = dns_message_gettemprdatalist(message, &rdatalist);
- if (result != ISC_R_SUCCESS)
- goto cleanup;
- result = dns_message_gettemprdata(message, &rdata);
- if (result != ISC_R_SUCCESS)
- goto cleanup;
- result = dns_message_gettemprdataset(message, &rdataset);
- if (result != ISC_R_SUCCESS)
- goto cleanup;
- dns_rdataset_init(rdataset);
-
- rdatalist->type = dns_rdatatype_opt;
- rdatalist->covers = 0;
-
- /*
- * Set Maximum UDP buffer size.
- */
- rdatalist->rdclass = udpsize;
-
- /*
- * Set EXTENDED-RCODE, VERSION, DO and Z to 0.
- */
- rdatalist->ttl = 0;
+ dns_rdataset_t *rdataset = NULL;
+ dns_ednsopt_t ednsopts[DNS_EDNSOPTIONS];
+ int count = 0;
/* Set EDNS options if applicable */
if (reqnsid) {
- unsigned char data[4];
- isc_buffer_t buf;
-
- isc_buffer_init(&buf, data, sizeof(data));
- isc_buffer_putuint16(&buf, DNS_OPT_NSID);
- isc_buffer_putuint16(&buf, 0);
- rdata->data = data;
- rdata->length = sizeof(data);
- } else {
- rdata->data = NULL;
- rdata->length = 0;
+ INSIST(count < DNS_EDNSOPTIONS);
+ ednsopts[count].code = DNS_OPT_NSID;
+ ednsopts[count].length = 0;
+ ednsopts[count].value = NULL;
+ count++;
}
-
- rdata->rdclass = rdatalist->rdclass;
- rdata->type = rdatalist->type;
- rdata->flags = 0;
-
- ISC_LIST_INIT(rdatalist->rdata);
- ISC_LIST_APPEND(rdatalist->rdata, rdata, link);
- RUNTIME_CHECK(dns_rdatalist_tordataset(rdatalist, rdataset)
- == ISC_R_SUCCESS);
+ result = dns_message_buildopt(message, &rdataset, 0, udpsize, 0,
+ ednsopts, count);
+ if (result != ISC_R_SUCCESS)
+ return (result);
return (dns_message_setopt(message, rdataset));
-
- cleanup:
- if (rdatalist != NULL)
- dns_message_puttemprdatalist(message, &rdatalist);
- if (rdataset != NULL)
- dns_message_puttemprdataset(message, &rdataset);
- if (rdata != NULL)
- dns_message_puttemprdata(message, &rdata);
-
- return (result);
}
static void
@@ -11846,6 +11815,8 @@ dns_zone_notifyreceive(dns_zone_t *zone, isc_sockaddr_t *from,
int match = 0;
isc_netaddr_t netaddr;
isc_sockaddr_t local, remote;
+ dns_tsigkey_t *tsigkey;
+ dns_name_t *tsig;
REQUIRE(DNS_ZONE_VALID(zone));
@@ -11930,8 +11901,10 @@ dns_zone_notifyreceive(dns_zone_t *zone, isc_sockaddr_t *from,
* Accept notify requests from non masters if they are on
* 'zone->notify_acl'.
*/
+ tsigkey = dns_message_gettsigkey(msg);
+ tsig = dns_tsigkey_identity(tsigkey);
if (i >= zone->masterscnt && zone->notify_acl != NULL &&
- dns_acl_match(&netaddr, NULL, zone->notify_acl,
+ dns_acl_match(&netaddr, tsig, zone->notify_acl,
&zone->view->aclenv,
&match, NULL) == ISC_R_SUCCESS &&
match > 0)
@@ -13048,7 +13021,6 @@ save_nsec3param(dns_zone_t *zone, nsec3paramlist_t *nsec3list) {
isc_result_t result;
dns_dbnode_t *node = NULL;
dns_rdataset_t rdataset, prdataset;
- dns_rdata_t rdata_in, prdata_in, prdata_out;
dns_dbversion_t *version = NULL;
nsec3param_t *nsec3param = NULL;
nsec3param_t *nsec3p = NULL;
@@ -13060,10 +13032,12 @@ save_nsec3param(dns_zone_t *zone, nsec3paramlist_t *nsec3list) {
REQUIRE(nsec3list != NULL);
REQUIRE(ISC_LIST_EMPTY(*nsec3list));
+ dns_rdataset_init(&rdataset);
+ dns_rdataset_init(&prdataset);
+
dns_db_attach(zone->db, &db);
CHECK(dns_db_getoriginnode(db, &node));
- dns_rdataset_init(&rdataset);
dns_db_currentversion(db, &version);
result = dns_db_findrdataset(db, node, version,
dns_rdatatype_nsec3param,
@@ -13082,8 +13056,10 @@ save_nsec3param(dns_zone_t *zone, nsec3paramlist_t *nsec3list) {
result == ISC_R_SUCCESS;
result = dns_rdataset_next(&rdataset))
{
- dns_rdata_init(&rdata_in);
- dns_rdataset_current(&rdataset, &rdata_in);
+ dns_rdata_t rdata = DNS_RDATA_INIT;
+ dns_rdata_t private = DNS_RDATA_INIT;
+
+ dns_rdataset_current(&rdataset, &rdata);
isc_log_write(dns_lctx, DNS_LOGCATEGORY_GENERAL,
DNS_LOGMODULE_ZONE, ISC_LOG_DEBUG(3),
"looping through nsec3param data");
@@ -13096,16 +13072,14 @@ save_nsec3param(dns_zone_t *zone, nsec3paramlist_t *nsec3list) {
* now transfer the data from the rdata to
* the nsec3param
*/
- dns_rdata_init(&prdata_out);
- dns_nsec3param_toprivate(&rdata_in, &prdata_out,
+ dns_nsec3param_toprivate(&rdata, &private,
zone->privatetype, nsec3param->data,
sizeof(nsec3param->data));
- nsec3param->length = prdata_out.length;
+ nsec3param->length = private.length;
ISC_LIST_APPEND(*nsec3list, nsec3param, link);
}
getprivate:
- dns_rdataset_init(&prdataset);
result = dns_db_findrdataset(db, node, version, zone->privatetype,
dns_rdatatype_none, 0, &prdataset, NULL);
if (result != ISC_R_SUCCESS)
@@ -13120,26 +13094,39 @@ save_nsec3param(dns_zone_t *zone, nsec3paramlist_t *nsec3list) {
result == ISC_R_SUCCESS;
result = dns_rdataset_next(&prdataset))
{
- dns_rdata_init(&prdata_in);
- dns_rdataset_current(&prdataset, &prdata_in);
+ dns_rdata_t rdata = DNS_RDATA_INIT;
+ dns_rdata_t private = DNS_RDATA_INIT;
+
+ dns_rdataset_current(&prdataset, &private);
isc_log_write(dns_lctx, DNS_LOGCATEGORY_GENERAL,
DNS_LOGMODULE_ZONE, ISC_LOG_DEBUG(3),
"looping through nsec3param private data");
- if (!dns_nsec3param_fromprivate(&prdata_in, &prdata_out,
+ /*
+ * Do we have a valid private record?
+ */
+ if (!dns_nsec3param_fromprivate(&private, &rdata,
buf, sizeof(buf)))
continue;
- if ((prdata_out.data[1] & DNS_NSEC3FLAG_REMOVE) !=0) {
- prdata_out.data[1] = 0;
+ /*
+ * Remove any NSEC3PARAM records scheduled to be removed.
+ */
+ if (NSEC3REMOVE(rdata.data[1])) {
+ /*
+ * Zero out the flags.
+ */
+ rdata.data[1] = 0;
for (nsec3p = ISC_LIST_HEAD(*nsec3list);
nsec3p != NULL;
nsec3p = next)
{
next = ISC_LIST_NEXT(nsec3p, link);
- if (memcmp(prdata_out.data, nsec3p->data,
- sizeof(nsec3p->data)) == 0) {
+
+ if (nsec3p->length == rdata.length + 1 &&
+ memcmp(rdata.data, nsec3p->data + 1,
+ nsec3p->length - 1) == 0) {
ISC_LIST_UNLINK(*nsec3list,
nsec3p, link);
isc_mem_put(zone->mctx, nsec3p,
@@ -13154,11 +13141,13 @@ save_nsec3param(dns_zone_t *zone, nsec3paramlist_t *nsec3list) {
CHECK(ISC_R_NOMEMORY);
ISC_LINK_INIT(nsec3param, link);
- dns_rdata_init(&prdata_out);
- dns_nsec3param_toprivate(&prdata_in, &prdata_out,
- zone->privatetype, nsec3param->data,
- sizeof(nsec3param->data));
- nsec3param->length = prdata_out.length;
+ /*
+ * Copy the remaining private records so the nsec/nsec3
+ * chain gets created.
+ */
+ INSIST(private.length <= sizeof(nsec3param->data));
+ memmove(nsec3param->data, private.data, private.length);
+ nsec3param->length = private.length;
ISC_LIST_APPEND(*nsec3list, nsec3param, link);
}
@@ -13374,6 +13363,12 @@ receive_secure_db(isc_task_t *task, isc_event_t *event) {
dns_zone_log(zone, ISC_LOG_ERROR, "receive_secure_db: %s",
dns_result_totext(result));
+ while (!ISC_LIST_EMPTY(nsec3list)) {
+ nsec3param_t *nsec3p;
+ nsec3p = ISC_LIST_HEAD(nsec3list);
+ ISC_LIST_UNLINK(nsec3list, nsec3p, link);
+ isc_mem_put(zone->mctx, nsec3p, sizeof(nsec3param_t));
+ }
if (dns_rdataset_isassociated(&rdataset))
dns_rdataset_disassociate(&rdataset);
if (db != NULL) {
@@ -13493,7 +13488,6 @@ zone_replacedb(dns_zone_t *zone, dns_db_t *db, isc_boolean_t dump) {
!DNS_ZONE_FLAG(zone, DNS_ZONEFLG_FORCEXFER))
{
isc_uint32_t serial, oldserial;
- unsigned int soacount;
dns_zone_log(zone, ISC_LOG_DEBUG(3), "generating diffs");
@@ -15691,10 +15685,12 @@ dns_zone_checknames(dns_zone_t *zone, dns_name_t *name, dns_rdata_t *rdata) {
REQUIRE(DNS_ZONE_VALID(zone));
- if (!DNS_ZONE_OPTION(zone, DNS_ZONEOPT_CHECKNAMES))
+ if (!DNS_ZONE_OPTION(zone, DNS_ZONEOPT_CHECKNAMES) &&
+ rdata->type != dns_rdatatype_nsec3)
return (ISC_R_SUCCESS);
- if (DNS_ZONE_OPTION(zone, DNS_ZONEOPT_CHECKNAMESFAIL)) {
+ if (DNS_ZONE_OPTION(zone, DNS_ZONEOPT_CHECKNAMESFAIL) ||
+ rdata->type == dns_rdatatype_nsec3) {
level = ISC_LOG_ERROR;
fail = ISC_TRUE;
}