2 * services/authzone.c - authoritative zone that is locally hosted.
4 * Copyright (c) 2017, NLnet Labs. All rights reserved.
6 * This software is open source.
8 * Redistribution and use in source and binary forms, with or without
9 * modification, are permitted provided that the following conditions
12 * Redistributions of source code must retain the above copyright notice,
13 * this list of conditions and the following disclaimer.
15 * Redistributions in binary form must reproduce the above copyright notice,
16 * this list of conditions and the following disclaimer in the documentation
17 * and/or other materials provided with the distribution.
19 * Neither the name of the NLNET LABS nor the names of its contributors may
20 * be used to endorse or promote products derived from this software without
21 * specific prior written permission.
23 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
24 * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
25 * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
26 * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
27 * HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
28 * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED
29 * TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
30 * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
31 * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
32 * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
33 * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
39 * This file contains the functions for an authority zone. This zone
40 * is queried by the iterator, just like a stub or forward zone, but then
41 * the data is locally held.
45 #include "services/authzone.h"
46 #include "util/data/dname.h"
47 #include "util/data/msgreply.h"
48 #include "util/data/packed_rrset.h"
49 #include "util/regional.h"
50 #include "util/net_help.h"
51 #include "util/config_file.h"
53 #include "services/cache/dns.h"
54 #include "sldns/rrdef.h"
55 #include "sldns/pkthdr.h"
56 #include "sldns/sbuffer.h"
57 #include "sldns/str2wire.h"
58 #include "sldns/wire2str.h"
59 #include "sldns/parseutil.h"
60 #include "validator/val_nsec3.h"
61 #include "validator/val_secalgo.h"
63 /** bytes to use for NSEC3 hash buffer. 20 for sha1 */
64 #define N3HASHBUFLEN 32
65 /** max number of CNAMEs we are willing to follow (in one answer) */
66 #define MAX_CNAME_CHAIN 8
68 /** create new dns_msg */
69 static struct dns_msg*
70 msg_create(struct regional* region, struct query_info* qinfo)
72 struct dns_msg* msg = (struct dns_msg*)regional_alloc(region,
73 sizeof(struct dns_msg));
76 msg->qinfo.qname = regional_alloc_init(region, qinfo->qname,
80 msg->qinfo.qname_len = qinfo->qname_len;
81 msg->qinfo.qtype = qinfo->qtype;
82 msg->qinfo.qclass = qinfo->qclass;
83 msg->qinfo.local_alias = NULL;
84 /* non-packed reply_info, because it needs to grow the array */
85 msg->rep = (struct reply_info*)regional_alloc_zero(region,
86 sizeof(struct reply_info)-sizeof(struct rrset_ref));
89 msg->rep->flags = (uint16_t)(BIT_QR | BIT_AA);
90 msg->rep->authoritative = 1;
91 msg->rep->qdcount = 1;
92 /* rrsets is NULL, no rrsets yet */
96 /** grow rrset array by one in msg */
98 msg_grow_array(struct regional* region, struct dns_msg* msg)
100 if(msg->rep->rrsets == NULL) {
101 msg->rep->rrsets = regional_alloc_zero(region,
102 sizeof(struct ub_packed_rrset_key*)*(msg->rep->rrset_count+1));
103 if(!msg->rep->rrsets)
106 struct ub_packed_rrset_key** rrsets_old = msg->rep->rrsets;
107 msg->rep->rrsets = regional_alloc_zero(region,
108 sizeof(struct ub_packed_rrset_key*)*(msg->rep->rrset_count+1));
109 if(!msg->rep->rrsets)
111 memmove(msg->rep->rrsets, rrsets_old,
112 sizeof(struct ub_packed_rrset_key*)*msg->rep->rrset_count);
117 /** get ttl of rrset */
119 get_rrset_ttl(struct ub_packed_rrset_key* k)
121 struct packed_rrset_data* d = (struct packed_rrset_data*)
126 /** Copy rrset into region from domain-datanode and packet rrset */
127 static struct ub_packed_rrset_key*
128 auth_packed_rrset_copy_region(struct auth_zone* z, struct auth_data* node,
129 struct auth_rrset* rrset, struct regional* region, time_t adjust)
131 struct ub_packed_rrset_key key;
132 memset(&key, 0, sizeof(key));
133 key.entry.key = &key;
134 key.entry.data = rrset->data;
135 key.rk.dname = node->name;
136 key.rk.dname_len = node->namelen;
137 key.rk.type = htons(rrset->type);
138 key.rk.rrset_class = htons(z->dclass);
139 key.entry.hash = rrset_key_hash(&key.rk);
140 return packed_rrset_copy_region(&key, region, adjust);
143 /** fix up msg->rep TTL and prefetch ttl */
145 msg_ttl(struct dns_msg* msg)
147 if(msg->rep->rrset_count == 0) return;
148 if(msg->rep->rrset_count == 1) {
149 msg->rep->ttl = get_rrset_ttl(msg->rep->rrsets[0]);
150 msg->rep->prefetch_ttl = PREFETCH_TTL_CALC(msg->rep->ttl);
151 } else if(get_rrset_ttl(msg->rep->rrsets[msg->rep->rrset_count-1]) <
153 msg->rep->ttl = get_rrset_ttl(msg->rep->rrsets[
154 msg->rep->rrset_count-1]);
155 msg->rep->prefetch_ttl = PREFETCH_TTL_CALC(msg->rep->ttl);
159 /** see if rrset is a duplicate in the answer message */
161 msg_rrset_duplicate(struct dns_msg* msg, uint8_t* nm, size_t nmlen,
162 uint16_t type, uint16_t dclass)
165 for(i=0; i<msg->rep->rrset_count; i++) {
166 struct ub_packed_rrset_key* k = msg->rep->rrsets[i];
167 if(ntohs(k->rk.type) == type && k->rk.dname_len == nmlen &&
168 ntohs(k->rk.rrset_class) == dclass &&
169 query_dname_compare(k->rk.dname, nm) == 0)
175 /** add rrset to answer section (no auth, add rrsets yet) */
177 msg_add_rrset_an(struct auth_zone* z, struct regional* region,
178 struct dns_msg* msg, struct auth_data* node, struct auth_rrset* rrset)
180 log_assert(msg->rep->ns_numrrsets == 0);
181 log_assert(msg->rep->ar_numrrsets == 0);
184 if(msg_rrset_duplicate(msg, node->name, node->namelen, rrset->type,
188 if(!msg_grow_array(region, msg))
191 if(!(msg->rep->rrsets[msg->rep->rrset_count] =
192 auth_packed_rrset_copy_region(z, node, rrset, region, 0)))
194 msg->rep->rrset_count++;
195 msg->rep->an_numrrsets++;
200 /** add rrset to authority section (no additonal section rrsets yet) */
202 msg_add_rrset_ns(struct auth_zone* z, struct regional* region,
203 struct dns_msg* msg, struct auth_data* node, struct auth_rrset* rrset)
205 log_assert(msg->rep->ar_numrrsets == 0);
208 if(msg_rrset_duplicate(msg, node->name, node->namelen, rrset->type,
212 if(!msg_grow_array(region, msg))
215 if(!(msg->rep->rrsets[msg->rep->rrset_count] =
216 auth_packed_rrset_copy_region(z, node, rrset, region, 0)))
218 msg->rep->rrset_count++;
219 msg->rep->ns_numrrsets++;
224 /** add rrset to additional section */
226 msg_add_rrset_ar(struct auth_zone* z, struct regional* region,
227 struct dns_msg* msg, struct auth_data* node, struct auth_rrset* rrset)
231 if(msg_rrset_duplicate(msg, node->name, node->namelen, rrset->type,
235 if(!msg_grow_array(region, msg))
238 if(!(msg->rep->rrsets[msg->rep->rrset_count] =
239 auth_packed_rrset_copy_region(z, node, rrset, region, 0)))
241 msg->rep->rrset_count++;
242 msg->rep->ar_numrrsets++;
247 struct auth_zones* auth_zones_create(void)
249 struct auth_zones* az = (struct auth_zones*)calloc(1, sizeof(*az));
251 log_err("out of memory");
254 rbtree_init(&az->ztree, &auth_zone_cmp);
255 lock_rw_init(&az->lock);
256 lock_protect(&az->lock, &az->ztree, sizeof(az->ztree));
257 /* also lock protects the rbnode's in struct auth_zone */
261 int auth_zone_cmp(const void* z1, const void* z2)
263 /* first sort on class, so that hierarchy can be maintained within
265 struct auth_zone* a = (struct auth_zone*)z1;
266 struct auth_zone* b = (struct auth_zone*)z2;
268 if(a->dclass != b->dclass) {
269 if(a->dclass < b->dclass)
273 /* sorted such that higher zones sort before lower zones (their
275 return dname_lab_cmp(a->name, a->namelabs, b->name, b->namelabs, &m);
278 int auth_data_cmp(const void* z1, const void* z2)
280 struct auth_data* a = (struct auth_data*)z1;
281 struct auth_data* b = (struct auth_data*)z2;
283 /* canonical sort, because DNSSEC needs that */
284 return dname_canon_lab_cmp(a->name, a->namelabs, b->name,
288 /** delete auth rrset node */
290 auth_rrset_delete(struct auth_rrset* rrset)
297 /** delete auth data domain node */
299 auth_data_delete(struct auth_data* n)
301 struct auth_rrset* p, *np;
306 auth_rrset_delete(p);
313 /** helper traverse to delete zones */
315 auth_data_del(rbnode_type* n, void* ATTR_UNUSED(arg))
317 struct auth_data* z = (struct auth_data*)n->key;
321 /** delete an auth zone structure (tree remove must be done elsewhere) */
323 auth_zone_delete(struct auth_zone* z)
326 lock_rw_destroy(&z->lock);
327 traverse_postorder(&z->data, auth_data_del, NULL);
334 auth_zone_create(struct auth_zones* az, uint8_t* nm, size_t nmlen,
337 struct auth_zone* z = (struct auth_zone*)calloc(1, sizeof(*z));
344 z->namelabs = dname_count_labels(nm);
345 z->name = memdup(nm, nmlen);
350 rbtree_init(&z->data, &auth_data_cmp);
351 lock_rw_init(&z->lock);
352 lock_protect(&z->lock, &z->name, sizeof(*z)-sizeof(rbnode_type));
353 lock_rw_wrlock(&z->lock);
354 /* z lock protects all, except rbtree itself, which is az->lock */
355 if(!rbtree_insert(&az->ztree, &z->node)) {
356 lock_rw_unlock(&z->lock);
358 log_warn("duplicate auth zone");
365 auth_zone_find(struct auth_zones* az, uint8_t* nm, size_t nmlen,
368 struct auth_zone key;
373 key.namelabs = dname_count_labels(nm);
374 return (struct auth_zone*)rbtree_search(&az->ztree, &key);
377 /** find an auth zone or sorted less-or-equal, return true if exact */
379 auth_zone_find_less_equal(struct auth_zones* az, uint8_t* nm, size_t nmlen,
380 uint16_t dclass, struct auth_zone** z)
382 struct auth_zone key;
387 key.namelabs = dname_count_labels(nm);
388 return rbtree_find_less_equal(&az->ztree, &key, (rbnode_type**)z);
391 /** find the auth zone that is above the given qname */
393 auth_zones_find_zone(struct auth_zones* az, struct query_info* qinfo)
395 uint8_t* nm = qinfo->qname;
396 size_t nmlen = qinfo->qname_len;
398 if(auth_zone_find_less_equal(az, nm, nmlen, qinfo->qclass, &z)) {
402 /* less-or-nothing */
403 if(!z) return NULL; /* nothing smaller, nothing above it */
404 /* we found smaller name; smaller may be above the qname,
405 * but not below it. */
406 nm = dname_get_shared_topdomain(z->name, qinfo->qname);
407 dname_count_size_labels(nm, &nmlen);
410 while(!z && !dname_is_root(nm)) {
411 dname_remove_label(&nm, &nmlen);
412 z = auth_zone_find(az, nm, nmlen, qinfo->qclass);
417 /** find or create zone with name str. caller must have lock on az.
418 * returns a wrlocked zone */
419 static struct auth_zone*
420 auth_zones_find_or_add_zone(struct auth_zones* az, char* name)
422 uint8_t nm[LDNS_MAX_DOMAINLEN+1];
423 size_t nmlen = sizeof(nm);
426 if(sldns_str2wire_dname_buf(name, nm, &nmlen) != 0) {
427 log_err("cannot parse auth zone name: %s", name);
430 z = auth_zone_find(az, nm, nmlen, LDNS_RR_CLASS_IN);
432 /* not found, create the zone */
433 z = auth_zone_create(az, nm, nmlen, LDNS_RR_CLASS_IN);
435 lock_rw_wrlock(&z->lock);
441 auth_zone_set_zonefile(struct auth_zone* z, char* zonefile)
443 if(z->zonefile) free(z->zonefile);
444 if(zonefile == NULL) {
447 z->zonefile = strdup(zonefile);
449 log_err("malloc failure");
456 /** set auth zone fallback. caller must have lock on zone */
458 auth_zone_set_fallback(struct auth_zone* z, char* fallbackstr)
460 if(strcmp(fallbackstr, "yes") != 0 && strcmp(fallbackstr, "no") != 0){
461 log_err("auth zone fallback, expected yes or no, got %s",
465 z->fallback_enabled = (strcmp(fallbackstr, "yes")==0);
469 /** create domain with the given name */
470 static struct auth_data*
471 az_domain_create(struct auth_zone* z, uint8_t* nm, size_t nmlen)
473 struct auth_data* n = (struct auth_data*)malloc(sizeof(*n));
475 memset(n, 0, sizeof(*n));
477 n->name = memdup(nm, nmlen);
483 n->namelabs = dname_count_labels(nm);
484 if(!rbtree_insert(&z->data, &n->node)) {
485 log_warn("duplicate auth domain name");
493 /** find domain with exactly the given name */
494 static struct auth_data*
495 az_find_name(struct auth_zone* z, uint8_t* nm, size_t nmlen)
497 struct auth_zone key;
501 key.namelabs = dname_count_labels(nm);
502 return (struct auth_data*)rbtree_search(&z->data, &key);
505 /** Find domain name (or closest match) */
507 az_find_domain(struct auth_zone* z, struct query_info* qinfo, int* node_exact,
508 struct auth_data** node)
510 struct auth_zone key;
512 key.name = qinfo->qname;
513 key.namelen = qinfo->qname_len;
514 key.namelabs = dname_count_labels(key.name);
515 *node_exact = rbtree_find_less_equal(&z->data, &key,
516 (rbnode_type**)node);
519 /** find or create domain with name in zone */
520 static struct auth_data*
521 az_domain_find_or_create(struct auth_zone* z, uint8_t* dname,
524 struct auth_data* n = az_find_name(z, dname, dname_len);
526 n = az_domain_create(z, dname, dname_len);
531 /** find rrset of given type in the domain */
532 static struct auth_rrset*
533 az_domain_rrset(struct auth_data* n, uint16_t t)
535 struct auth_rrset* rrset;
546 /** remove rrset of this type from domain */
548 domain_remove_rrset(struct auth_data* node, uint16_t rr_type)
550 struct auth_rrset* rrset, *prev;
553 rrset = node->rrsets;
555 if(rrset->type == rr_type) {
556 /* found it, now delete it */
557 if(prev) prev->next = rrset->next;
558 else node->rrsets = rrset->next;
559 auth_rrset_delete(rrset);
567 /** see if rdata is duplicate */
569 rdata_duplicate(struct packed_rrset_data* d, uint8_t* rdata, size_t len)
572 for(i=0; i<d->count + d->rrsig_count; i++) {
573 if(d->rr_len[i] != len)
575 if(memcmp(d->rr_data[i], rdata, len) == 0)
581 /** get rrsig type covered from rdata.
582 * @param rdata: rdata in wireformat, starting with 16bit rdlength.
583 * @param rdatalen: length of rdata buffer.
584 * @return type covered (or 0).
587 rrsig_rdata_get_type_covered(uint8_t* rdata, size_t rdatalen)
591 return sldns_read_uint16(rdata+2);
594 /** add RR to existing RRset. If insert_sig is true, add to rrsigs.
595 * This reallocates the packed rrset for a new one */
597 rrset_add_rr(struct auth_rrset* rrset, uint32_t rr_ttl, uint8_t* rdata,
598 size_t rdatalen, int insert_sig)
600 struct packed_rrset_data* d, *old = rrset->data;
601 size_t total, old_total;
603 d = (struct packed_rrset_data*)calloc(1, packed_rrset_sizeof(old)
604 + sizeof(size_t) + sizeof(uint8_t*) + sizeof(time_t)
607 log_err("out of memory");
610 /* copy base values */
611 memcpy(d, old, sizeof(struct packed_rrset_data));
617 old_total = old->count + old->rrsig_count;
618 total = d->count + d->rrsig_count;
619 /* set rr_len, needed for ptr_fixup */
620 d->rr_len = (size_t*)((uint8_t*)d +
621 sizeof(struct packed_rrset_data));
623 memmove(d->rr_len, old->rr_len, old->count*sizeof(size_t));
624 if(old->rrsig_count != 0)
625 memmove(d->rr_len+d->count, old->rr_len+old->count,
626 old->rrsig_count*sizeof(size_t));
628 d->rr_len[d->count-1] = rdatalen;
629 else d->rr_len[total-1] = rdatalen;
630 packed_rrset_ptr_fixup(d);
631 if((time_t)rr_ttl < d->ttl)
634 /* copy old values into new array */
635 if(old->count != 0) {
636 memmove(d->rr_ttl, old->rr_ttl, old->count*sizeof(time_t));
637 /* all the old rr pieces are allocated sequential, so we
638 * can copy them in one go */
639 memmove(d->rr_data[0], old->rr_data[0],
640 (old->rr_data[old->count-1] - old->rr_data[0]) +
641 old->rr_len[old->count-1]);
643 if(old->rrsig_count != 0) {
644 memmove(d->rr_ttl+d->count, old->rr_ttl+old->count,
645 old->rrsig_count*sizeof(time_t));
646 memmove(d->rr_data[d->count], old->rr_data[old->count],
647 (old->rr_data[old_total-1] - old->rr_data[old->count]) +
648 old->rr_len[old_total-1]);
651 /* insert new value */
653 d->rr_ttl[d->count-1] = rr_ttl;
654 memmove(d->rr_data[d->count-1], rdata, rdatalen);
656 d->rr_ttl[total-1] = rr_ttl;
657 memmove(d->rr_data[total-1], rdata, rdatalen);
665 /** Create new rrset for node with packed rrset with one RR element */
666 static struct auth_rrset*
667 rrset_create(struct auth_data* node, uint16_t rr_type, uint32_t rr_ttl,
668 uint8_t* rdata, size_t rdatalen)
670 struct auth_rrset* rrset = (struct auth_rrset*)calloc(1,
672 struct auth_rrset* p, *prev;
673 struct packed_rrset_data* d;
675 log_err("out of memory");
678 rrset->type = rr_type;
680 /* the rrset data structure, with one RR */
681 d = (struct packed_rrset_data*)calloc(1,
682 sizeof(struct packed_rrset_data) + sizeof(size_t) +
683 sizeof(uint8_t*) + sizeof(time_t) + rdatalen);
686 log_err("out of memory");
691 d->trust = rrset_trust_prim_noglue;
692 d->rr_len = (size_t*)((uint8_t*)d + sizeof(struct packed_rrset_data));
693 d->rr_data = (uint8_t**)&(d->rr_len[1]);
694 d->rr_ttl = (time_t*)&(d->rr_data[1]);
695 d->rr_data[0] = (uint8_t*)&(d->rr_ttl[1]);
698 d->rr_len[0] = rdatalen;
699 d->rr_ttl[0] = rr_ttl;
700 memmove(d->rr_data[0], rdata, rdatalen);
703 /* insert rrset into linked list for domain */
704 /* find sorted place to link the rrset into the list */
707 while(p && p->type<=rr_type) {
711 /* so, prev is smaller, and p is larger than rr_type */
713 if(prev) prev->next = rrset;
714 else node->rrsets = rrset;
718 /** count number (and size) of rrsigs that cover a type */
720 rrsig_num_that_cover(struct auth_rrset* rrsig, uint16_t rr_type, size_t* sigsz)
722 struct packed_rrset_data* d = rrsig->data;
725 log_assert(d && rrsig->type == LDNS_RR_TYPE_RRSIG);
726 for(i=0; i<d->count+d->rrsig_count; i++) {
727 if(rrsig_rdata_get_type_covered(d->rr_data[i],
728 d->rr_len[i]) == rr_type) {
730 (*sigsz) += d->rr_len[i];
736 /** See if rrsig set has covered sigs for rrset and move them over */
738 rrset_moveover_rrsigs(struct auth_data* node, uint16_t rr_type,
739 struct auth_rrset* rrset, struct auth_rrset* rrsig)
741 size_t sigs, sigsz, i, j, total;
742 struct packed_rrset_data* sigold = rrsig->data;
743 struct packed_rrset_data* old = rrset->data;
744 struct packed_rrset_data* d, *sigd;
746 log_assert(rrset->type == rr_type);
747 log_assert(rrsig->type == LDNS_RR_TYPE_RRSIG);
748 sigs = rrsig_num_that_cover(rrsig, rr_type, &sigsz);
750 /* 0 rrsigs to move over, done */
753 log_info("moveover %d sigs size %d", (int)sigs, (int)sigsz);
755 /* allocate rrset sigsz larger for extra sigs elements, and
756 * allocate rrsig sigsz smaller for less sigs elements. */
757 d = (struct packed_rrset_data*)calloc(1, packed_rrset_sizeof(old)
758 + sigs*(sizeof(size_t) + sizeof(uint8_t*) + sizeof(time_t))
761 log_err("out of memory");
764 /* copy base values */
765 total = old->count + old->rrsig_count;
766 memcpy(d, old, sizeof(struct packed_rrset_data));
767 d->rrsig_count += sigs;
769 d->rr_len = (size_t*)((uint8_t*)d +
770 sizeof(struct packed_rrset_data));
772 memmove(d->rr_len, old->rr_len, total*sizeof(size_t));
773 j = d->count+d->rrsig_count-sigs;
774 for(i=0; i<sigold->count+sigold->rrsig_count; i++) {
775 if(rrsig_rdata_get_type_covered(sigold->rr_data[i],
776 sigold->rr_len[i]) == rr_type) {
777 d->rr_len[j] = sigold->rr_len[i];
781 packed_rrset_ptr_fixup(d);
783 /* copy old values into new array */
785 memmove(d->rr_ttl, old->rr_ttl, total*sizeof(time_t));
786 /* all the old rr pieces are allocated sequential, so we
787 * can copy them in one go */
788 memmove(d->rr_data[0], old->rr_data[0],
789 (old->rr_data[total-1] - old->rr_data[0]) +
790 old->rr_len[total-1]);
793 /* move over the rrsigs to the larger rrset*/
794 j = d->count+d->rrsig_count-sigs;
795 for(i=0; i<sigold->count+sigold->rrsig_count; i++) {
796 if(rrsig_rdata_get_type_covered(sigold->rr_data[i],
797 sigold->rr_len[i]) == rr_type) {
798 /* move this one over to location j */
799 d->rr_ttl[j] = sigold->rr_ttl[i];
800 memmove(d->rr_data[j], sigold->rr_data[i],
802 if(d->rr_ttl[j] < d->ttl)
803 d->ttl = d->rr_ttl[j];
808 /* put it in and deallocate the old rrset */
812 /* now make rrsig set smaller */
813 if(sigold->count+sigold->rrsig_count == sigs) {
814 /* remove all sigs from rrsig, remove it entirely */
815 domain_remove_rrset(node, LDNS_RR_TYPE_RRSIG);
818 log_assert(packed_rrset_sizeof(sigold) > sigs*(sizeof(size_t) +
819 sizeof(uint8_t*) + sizeof(time_t)) + sigsz);
820 sigd = (struct packed_rrset_data*)calloc(1, packed_rrset_sizeof(sigold)
821 - sigs*(sizeof(size_t) + sizeof(uint8_t*) + sizeof(time_t))
824 /* no need to free up d, it has already been placed in the
825 * node->rrset structure */
826 log_err("out of memory");
829 /* copy base values */
830 memcpy(sigd, sigold, sizeof(struct packed_rrset_data));
831 sigd->rrsig_count -= sigs;
833 sigd->rr_len = (size_t*)((uint8_t*)sigd +
834 sizeof(struct packed_rrset_data));
836 for(i=0; i<sigold->count+sigold->rrsig_count; i++) {
837 if(rrsig_rdata_get_type_covered(sigold->rr_data[i],
838 sigold->rr_len[i]) != rr_type) {
839 sigd->rr_len[j] = sigold->rr_len[i];
843 packed_rrset_ptr_fixup(sigd);
845 /* copy old values into new rrsig array */
847 for(i=0; i<sigold->count+sigold->rrsig_count; i++) {
848 if(rrsig_rdata_get_type_covered(sigold->rr_data[i],
849 sigold->rr_len[i]) != rr_type) {
850 /* move this one over to location j */
851 sigd->rr_ttl[j] = sigold->rr_ttl[i];
852 memmove(sigd->rr_data[j], sigold->rr_data[i],
854 if(j==0) sigd->ttl = sigd->rr_ttl[j];
856 if(sigd->rr_ttl[j] < sigd->ttl)
857 sigd->ttl = sigd->rr_ttl[j];
863 /* put it in and deallocate the old rrset */
870 /** Add rr to node, ignores duplicate RRs,
871 * rdata points to buffer with rdatalen octets, starts with 2bytelength. */
873 az_domain_add_rr(struct auth_data* node, uint16_t rr_type, uint32_t rr_ttl,
874 uint8_t* rdata, size_t rdatalen)
876 struct auth_rrset* rrset;
877 /* packed rrsets have their rrsigs along with them, sort them out */
878 if(rr_type == LDNS_RR_TYPE_RRSIG) {
879 uint16_t ctype = rrsig_rdata_get_type_covered(rdata, rdatalen);
880 if((rrset=az_domain_rrset(node, ctype))!= NULL) {
881 /* a node of the correct type exists, add the RRSIG
882 * to the rrset of the covered data type */
883 if(rdata_duplicate(rrset->data, rdata, rdatalen))
885 if(!rrset_add_rr(rrset, rr_ttl, rdata, rdatalen, 1))
887 } else if((rrset=az_domain_rrset(node, rr_type))!= NULL) {
888 /* add RRSIG to rrset of type RRSIG */
889 if(rdata_duplicate(rrset->data, rdata, rdatalen))
891 if(!rrset_add_rr(rrset, rr_ttl, rdata, rdatalen, 0))
894 /* create rrset of type RRSIG */
895 if(!rrset_create(node, rr_type, rr_ttl, rdata,
901 if((rrset=az_domain_rrset(node, rr_type))!= NULL) {
902 /* add data to existing node with data type */
903 if(rdata_duplicate(rrset->data, rdata, rdatalen))
905 if(!rrset_add_rr(rrset, rr_ttl, rdata, rdatalen, 0))
908 struct auth_rrset* rrsig;
909 /* create new node with data type */
910 if(!(rrset=rrset_create(node, rr_type, rr_ttl, rdata,
914 /* see if node of type RRSIG has signatures that
915 * cover the data type, and move them over */
916 /* and then make the RRSIG type smaller */
917 if((rrsig=az_domain_rrset(node, LDNS_RR_TYPE_RRSIG))
919 if(!rrset_moveover_rrsigs(node, rr_type,
928 /** insert RR into zone, ignore duplicates */
930 az_insert_rr(struct auth_zone* z, uint8_t* rr, size_t rr_len,
933 struct auth_data* node;
935 uint16_t rr_type = sldns_wirerr_get_type(rr, rr_len, dname_len);
936 uint16_t rr_class = sldns_wirerr_get_class(rr, rr_len, dname_len);
937 uint32_t rr_ttl = sldns_wirerr_get_ttl(rr, rr_len, dname_len);
938 size_t rdatalen = ((size_t)sldns_wirerr_get_rdatalen(rr, rr_len,
940 /* rdata points to rdata prefixed with uint16 rdatalength */
941 uint8_t* rdata = sldns_wirerr_get_rdatawl(rr, rr_len, dname_len);
943 if(rr_class != z->dclass) {
944 log_err("wrong class for RR");
947 if(!(node=az_domain_find_or_create(z, dname, dname_len))) {
948 log_err("cannot create domain");
951 if(!az_domain_add_rr(node, rr_type, rr_ttl, rdata, rdatalen)) {
952 log_err("cannot add RR to domain");
960 * @param z: zone to read in.
961 * @param in: file to read from (just opened).
962 * @param rr: buffer to use for RRs, 64k.
963 * passed so that recursive includes can use the same buffer and do
964 * not grow the stack too much.
965 * @param rrbuflen: sizeof rr buffer.
966 * @param state: parse state with $ORIGIN, $TTL and 'prev-dname' and so on,
967 * that is kept between includes.
968 * The lineno is set at 1 and then increased by the function.
969 * returns false on failure, has printed an error message
972 az_parse_file(struct auth_zone* z, FILE* in, uint8_t* rr, size_t rrbuflen,
973 struct sldns_file_parse_state* state)
975 size_t rr_len, dname_len;
982 status = sldns_fp2wire_rr_buf(in, rr, &rr_len, &dname_len,
984 if(status == LDNS_WIREPARSE_ERR_INCLUDE && rr_len == 0) {
985 /* we have $INCLUDE or $something */
986 if(strncmp((char*)rr, "$INCLUDE ", 9) == 0 ||
987 strncmp((char*)rr, "$INCLUDE\t", 9) == 0) {
989 int lineno_orig = state->lineno;
990 char* incfile = (char*)rr + 8;
992 while(*incfile == ' ' || *incfile == '\t')
994 verbose(VERB_ALGO, "opening $INCLUDE %s",
996 inc = fopen(incfile, "r");
998 log_err("%s:%d cannot open include "
999 "file %s: %s", z->zonefile,
1000 lineno_orig, incfile,
1004 /* recurse read that file now */
1005 if(!az_parse_file(z, inc, rr, rrbuflen,
1007 log_err("%s:%d cannot parse include "
1008 "file %s", z->zonefile,
1009 lineno_orig, incfile);
1014 verbose(VERB_ALGO, "done with $INCLUDE %s",
1016 state->lineno = lineno_orig;
1021 log_err("parse error %s %d:%d: %s", z->zonefile,
1022 state->lineno, LDNS_WIREPARSE_OFFSET(status),
1023 sldns_get_errorstr_parse(status));
1027 /* EMPTY line, TTL or ORIGIN */
1030 /* insert wirerr in rrbuf */
1031 if(!az_insert_rr(z, rr, rr_len, dname_len)) {
1033 sldns_wire2str_type_buf(sldns_wirerr_get_type(rr,
1034 rr_len, dname_len), buf, sizeof(buf));
1035 log_err("%s:%d cannot insert RR of type %s",
1036 z->zonefile, state->lineno, buf);
1044 auth_zone_read_zonefile(struct auth_zone* z)
1046 uint8_t rr[LDNS_RR_BUF_SIZE];
1047 struct sldns_file_parse_state state;
1049 if(!z || !z->zonefile || z->zonefile[0]==0)
1050 return 1; /* no file, or "", nothing to read */
1051 verbose(VERB_ALGO, "read zonefile %s", z->zonefile);
1052 in = fopen(z->zonefile, "r");
1054 char* n = sldns_wire2str_dname(z->name, z->namelen);
1055 log_err("cannot open zonefile %s for %s: %s",
1056 z->zonefile, n?n:"error", strerror(errno));
1060 memset(&state, 0, sizeof(state));
1061 /* default TTL to 3600 */
1062 state.default_ttl = 3600;
1063 /* set $ORIGIN to the zone name */
1064 if(z->namelen <= sizeof(state.origin)) {
1065 memcpy(state.origin, z->name, z->namelen);
1066 state.origin_len = z->namelen;
1068 /* parse the (toplevel) file */
1069 if(!az_parse_file(z, in, rr, sizeof(rr), &state)) {
1070 char* n = sldns_wire2str_dname(z->name, z->namelen);
1071 log_err("error parsing zonefile %s for %s",
1072 z->zonefile, n?n:"error");
1081 /** write buffer to file and check return codes */
1083 write_out(FILE* out, const char* str)
1085 size_t r, len = strlen(str);
1088 r = fwrite(str, 1, len, out);
1090 log_err("write failed: %s", strerror(errno));
1092 } else if(r < len) {
1093 log_err("write failed: too short (disk full?)");
1099 /** write rrset to file */
1101 auth_zone_write_rrset(struct auth_zone* z, struct auth_data* node,
1102 struct auth_rrset* r, FILE* out)
1104 size_t i, count = r->data->count + r->data->rrsig_count;
1105 char buf[LDNS_RR_BUF_SIZE];
1106 for(i=0; i<count; i++) {
1107 struct ub_packed_rrset_key key;
1108 memset(&key, 0, sizeof(key));
1109 key.entry.key = &key;
1110 key.entry.data = r->data;
1111 key.rk.dname = node->name;
1112 key.rk.dname_len = node->namelen;
1113 key.rk.type = htons(r->type);
1114 key.rk.rrset_class = htons(z->dclass);
1115 if(!packed_rr_to_string(&key, i, 0, buf, sizeof(buf))) {
1116 verbose(VERB_ALGO, "failed to rr2str rr %d", (int)i);
1119 if(!write_out(out, buf))
1125 /** write domain to file */
1127 auth_zone_write_domain(struct auth_zone* z, struct auth_data* n, FILE* out)
1129 struct auth_rrset* r;
1130 /* if this is zone apex, write SOA first */
1131 if(z->namelen == n->namelen) {
1132 struct auth_rrset* soa = az_domain_rrset(n, LDNS_RR_TYPE_SOA);
1134 if(!auth_zone_write_rrset(z, n, soa, out))
1138 /* write all the RRsets for this domain */
1139 for(r = n->rrsets; r; r = r->next) {
1140 if(z->namelen == n->namelen &&
1141 r->type == LDNS_RR_TYPE_SOA)
1142 continue; /* skip SOA here */
1143 if(!auth_zone_write_rrset(z, n, r, out))
1149 int auth_zone_write_file(struct auth_zone* z, const char* fname)
1152 struct auth_data* n;
1153 out = fopen(fname, "w");
1155 log_err("could not open %s: %s", fname, strerror(errno));
1158 RBTREE_FOR(n, struct auth_data*, &z->data) {
1159 if(!auth_zone_write_domain(z, n, out)) {
1160 log_err("could not write domain to %s", fname);
1169 /** read all auth zones from file (if they have) */
1171 auth_zones_read_zones(struct auth_zones* az)
1173 struct auth_zone* z;
1174 lock_rw_wrlock(&az->lock);
1175 RBTREE_FOR(z, struct auth_zone*, &az->ztree) {
1176 lock_rw_wrlock(&z->lock);
1177 if(!auth_zone_read_zonefile(z)) {
1178 lock_rw_unlock(&z->lock);
1179 lock_rw_unlock(&az->lock);
1182 lock_rw_unlock(&z->lock);
1184 lock_rw_unlock(&az->lock);
1188 /** set str2list with (zonename, zonefile) config items and create zones */
1190 auth_zones_cfg_zonefile(struct auth_zones* az, struct config_str2list* zlist)
1192 struct auth_zone* z;
1194 lock_rw_wrlock(&az->lock);
1195 if(!(z=auth_zones_find_or_add_zone(az, zlist->str))) {
1196 lock_rw_unlock(&az->lock);
1199 lock_rw_unlock(&az->lock);
1200 if(!auth_zone_set_zonefile(z, zlist->str2)) {
1201 lock_rw_unlock(&z->lock);
1204 lock_rw_unlock(&z->lock);
1205 zlist = zlist->next;
1210 /** set str2list with (zonename, fallback) config items and create zones */
1212 auth_zones_cfg_fallback(struct auth_zones* az, struct config_str2list* zlist)
1214 struct auth_zone* z;
1216 lock_rw_wrlock(&az->lock);
1217 if(!(z=auth_zones_find_or_add_zone(az, zlist->str))) {
1218 lock_rw_unlock(&az->lock);
1221 lock_rw_unlock(&az->lock);
1222 if(!auth_zone_set_fallback(z, zlist->str2)) {
1223 lock_rw_unlock(&z->lock);
1226 lock_rw_unlock(&z->lock);
1227 zlist = zlist->next;
1232 int auth_zones_apply_config(struct auth_zones* az, struct config_file* cfg)
1235 /* TODO cfg str2lists */
1236 /* create config items for
1237 * auth-zone: name: "example.com"
1238 * zonefile: "zones/example.com"
1241 if(!auth_zones_cfg_zonefile(az, NULL /*cfg->auth_zones*/))
1243 if(!auth_zones_cfg_fallback(az, NULL /*cfg->auth_zones*/))
1245 if(!auth_zones_read_zones(az))
1250 /** helper traverse to delete zones */
1252 auth_zone_del(rbnode_type* n, void* ATTR_UNUSED(arg))
1254 struct auth_zone* z = (struct auth_zone*)n->key;
1255 auth_zone_delete(z);
1258 void auth_zones_delete(struct auth_zones* az)
1261 lock_rw_destroy(&az->lock);
1262 traverse_postorder(&az->ztree, auth_zone_del, NULL);
1266 /** true if domain has only nsec3 */
1268 domain_has_only_nsec3(struct auth_data* n)
1270 struct auth_rrset* rrset = n->rrsets;
1273 if(rrset->type == LDNS_RR_TYPE_NSEC3) {
1275 } else if(rrset->type != LDNS_RR_TYPE_RRSIG) {
1278 rrset = rrset->next;
1283 /** see if the domain has a wildcard child '*.domain' */
1284 static struct auth_data*
1285 az_find_wildcard_domain(struct auth_zone* z, uint8_t* nm, size_t nmlen)
1287 uint8_t wc[LDNS_MAX_DOMAINLEN];
1288 if(nmlen+2 > sizeof(wc))
1289 return NULL; /* result would be too long */
1290 wc[0] = 1; /* length of wildcard label */
1291 wc[1] = (uint8_t)'*'; /* wildcard label */
1292 memmove(wc+2, nm, nmlen);
1293 return az_find_name(z, wc, nmlen+2);
1296 /** find wildcard between qname and cename */
1297 static struct auth_data*
1298 az_find_wildcard(struct auth_zone* z, struct query_info* qinfo,
1299 struct auth_data* ce)
1301 uint8_t* nm = qinfo->qname;
1302 size_t nmlen = qinfo->qname_len;
1303 struct auth_data* node;
1304 if(!dname_subdomain_c(nm, z->name))
1305 return NULL; /* out of zone */
1306 while((node=az_find_wildcard_domain(z, nm, nmlen))==NULL) {
1307 /* see if we can go up to find the wildcard */
1308 if(nmlen == z->namelen)
1309 return NULL; /* top of zone reached */
1310 if(ce && nmlen == ce->namelen)
1311 return NULL; /* ce reached */
1312 if(dname_is_root(nm))
1313 return NULL; /* cannot go up */
1314 dname_remove_label(&nm, &nmlen);
1319 /** domain is not exact, find first candidate ce (name that matches
1320 * a part of qname) in tree */
1321 static struct auth_data*
1322 az_find_candidate_ce(struct auth_zone* z, struct query_info* qinfo,
1323 struct auth_data* n)
1328 nm = dname_get_shared_topdomain(qinfo->qname, n->name);
1332 dname_count_size_labels(nm, &nmlen);
1333 n = az_find_name(z, nm, nmlen);
1334 /* delete labels and go up on name */
1336 if(dname_is_root(nm))
1337 return NULL; /* cannot go up */
1338 dname_remove_label(&nm, &nmlen);
1339 n = az_find_name(z, nm, nmlen);
1344 /** go up the auth tree to next existing name. */
1345 static struct auth_data*
1346 az_domain_go_up(struct auth_zone* z, struct auth_data* n)
1348 uint8_t* nm = n->name;
1349 size_t nmlen = n->namelen;
1350 while(!dname_is_root(nm)) {
1351 dname_remove_label(&nm, &nmlen);
1352 if((n=az_find_name(z, nm, nmlen)) != NULL)
1358 /** Find the closest encloser, an name that exists and is above the
1360 * return true if the node (param node) is existing, nonobscured and
1361 * can be used to generate answers from. It is then also node_exact.
1362 * returns false if the node is not good enough (or it wasn't node_exact)
1363 * in this case the ce can be filled.
1364 * if ce is NULL, no ce exists, and likely the zone is completely empty,
1365 * not even with a zone apex.
1366 * if ce is nonNULL it is the closest enclosing upper name (that exists
1367 * itself for answer purposes). That name may have DNAME, NS or wildcard
1368 * rrset is the closest DNAME or NS rrset that was found.
1371 az_find_ce(struct auth_zone* z, struct query_info* qinfo,
1372 struct auth_data* node, int node_exact, struct auth_data** ce,
1373 struct auth_rrset** rrset)
1375 struct auth_data* n = node;
1379 /* if not exact, lookup closest exact match */
1380 n = az_find_candidate_ce(z, qinfo, n);
1382 /* if exact, the node itself is the first candidate ce */
1386 /* no direct answer from nsec3-only domains */
1387 if(n && domain_has_only_nsec3(n)) {
1392 /* with exact matches, walk up the labels until we find the
1393 * delegation, or DNAME or zone end */
1395 /* see if the current candidate has issues */
1396 /* not zone apex and has type NS */
1397 if(n->namelen != z->namelen &&
1398 (*rrset=az_domain_rrset(n, LDNS_RR_TYPE_NS)) &&
1399 /* delegate here, but DS at exact the dp has notype */
1400 (qinfo->qtype != LDNS_RR_TYPE_DS ||
1401 n->namelen != qinfo->qname_len)) {
1403 /* this is ce and the lowernode is nonexisting */
1407 /* not equal to qname and has type DNAME */
1408 if(n->namelen != qinfo->qname_len &&
1409 (*rrset=az_domain_rrset(n, LDNS_RR_TYPE_DNAME))) {
1410 /* this is ce and the lowernode is nonexisting */
1415 if(*ce == NULL && !domain_has_only_nsec3(n)) {
1416 /* if not found yet, this exact name must be
1417 * our lowest match (but not nsec3onlydomain) */
1421 /* walk up the tree by removing labels from name and lookup */
1422 n = az_domain_go_up(z, n);
1424 /* found no problems, if it was an exact node, it is fine to use */
1428 /** add additional A/AAAA from domain names in rrset rdata (+offset)
1429 * offset is number of bytes in rdata where the dname is located. */
1431 az_add_additionals_from(struct auth_zone* z, struct regional* region,
1432 struct dns_msg* msg, struct auth_rrset* rrset, size_t offset)
1434 struct packed_rrset_data* d = rrset->data;
1437 for(i=0; i<d->count; i++) {
1439 struct auth_data* domain;
1440 struct auth_rrset* ref;
1441 if(d->rr_len[i] < 2+offset)
1442 continue; /* too short */
1443 if(!(dlen = dname_valid(d->rr_data[i]+2+offset,
1444 d->rr_len[i]-2-offset)))
1445 continue; /* malformed */
1446 domain = az_find_name(z, d->rr_data[i]+2+offset, dlen);
1449 if((ref=az_domain_rrset(domain, LDNS_RR_TYPE_A)) != NULL) {
1450 if(!msg_add_rrset_ar(z, region, msg, domain, ref))
1453 if((ref=az_domain_rrset(domain, LDNS_RR_TYPE_AAAA)) != NULL) {
1454 if(!msg_add_rrset_ar(z, region, msg, domain, ref))
1461 /** add negative SOA record (with negative TTL) */
1463 az_add_negative_soa(struct auth_zone* z, struct regional* region,
1464 struct dns_msg* msg)
1467 struct packed_rrset_data* d;
1468 struct auth_rrset* soa;
1469 struct auth_data* apex = az_find_name(z, z->name, z->namelen);
1471 soa = az_domain_rrset(apex, LDNS_RR_TYPE_SOA);
1473 /* must be first to put in message; we want to fix the TTL with
1474 * one RRset here, otherwise we'd need to loop over the RRs to get
1475 * the resulting lower TTL */
1476 log_assert(msg->rep->rrset_count == 0);
1477 if(!msg_add_rrset_ns(z, region, msg, apex, soa)) return 0;
1479 d = (struct packed_rrset_data*)msg->rep->rrsets[msg->rep->rrset_count-1]->entry.data;
1480 /* last 4 bytes are minimum ttl in network format */
1481 if(d->count == 0) return 0;
1482 if(d->rr_len[0] < 2+4) return 0;
1483 minimum = sldns_read_uint32(d->rr_data[0]+(d->rr_len[0]-4));
1484 d->ttl = (time_t)minimum;
1485 d->rr_ttl[0] = (time_t)minimum;
1486 msg->rep->ttl = get_rrset_ttl(msg->rep->rrsets[0]);
1487 msg->rep->prefetch_ttl = PREFETCH_TTL_CALC(msg->rep->ttl);
1491 /** See if the query goes to empty nonterminal (that has no auth_data,
1492 * but there are nodes underneath. We already checked that there are
1493 * not NS, or DNAME above, so that we only need to check if some node
1494 * exists below (with nonempty rr list), return true if emptynonterminal */
1496 az_empty_nonterminal(struct auth_zone* z, struct query_info* qinfo,
1497 struct auth_data* node)
1499 struct auth_data* next;
1501 /* no smaller was found, use first (smallest) node as the
1503 next = (struct auth_data*)rbtree_first(&z->data);
1505 next = (struct auth_data*)rbtree_next(&node->node);
1507 while(next && (rbnode_type*)next != RBTREE_NULL && next->rrsets == NULL) {
1508 /* the next name has empty rrsets, is an empty nonterminal
1509 * itself, see if there exists something below it */
1510 next = (struct auth_data*)rbtree_next(&node->node);
1512 if((rbnode_type*)next == RBTREE_NULL || !next) {
1513 /* there is no next node, so something below it cannot
1517 /* a next node exists, if there was something below the query,
1518 * this node has to be it. See if it is below the query name */
1519 if(dname_strict_subdomain_c(next->name, qinfo->qname))
1524 /** create synth cname target name in buffer, or fail if too long */
1526 synth_cname_buf(uint8_t* qname, size_t qname_len, size_t dname_len,
1527 uint8_t* dtarg, size_t dtarglen, uint8_t* buf, size_t buflen)
1529 size_t newlen = qname_len + dtarglen - dname_len;
1530 if(newlen > buflen) {
1531 /* YXDOMAIN error */
1534 /* new name is concatenation of qname front (without DNAME owner)
1535 * and DNAME target name */
1536 memcpy(buf, qname, qname_len-dname_len);
1537 memmove(buf+(qname_len-dname_len), dtarg, dtarglen);
1541 /** create synthetic CNAME rrset for in a DNAME answer in region,
1542 * false on alloc failure, cname==NULL when name too long. */
1544 create_synth_cname(uint8_t* qname, size_t qname_len, struct regional* region,
1545 struct auth_data* node, struct auth_rrset* dname, uint16_t dclass,
1546 struct ub_packed_rrset_key** cname)
1548 uint8_t buf[LDNS_MAX_DOMAINLEN];
1550 size_t dtarglen, newlen;
1551 struct packed_rrset_data* d;
1553 /* get DNAME target name */
1554 if(dname->data->count < 1) return 0;
1555 if(dname->data->rr_len[0] < 3) return 0; /* at least rdatalen +1 */
1556 dtarg = dname->data->rr_data[0]+2;
1557 dtarglen = dname->data->rr_len[0]-2;
1558 if(sldns_read_uint16(dname->data->rr_data[0]) != dtarglen)
1559 return 0; /* rdatalen in DNAME rdata is malformed */
1560 if(dname_valid(dtarg, dtarglen) != dtarglen)
1561 return 0; /* DNAME RR has malformed rdata */
1563 /* synthesize a CNAME */
1564 newlen = synth_cname_buf(qname, qname_len, node->namelen,
1565 dtarg, dtarglen, buf, sizeof(buf));
1567 /* YXDOMAIN error */
1571 *cname = (struct ub_packed_rrset_key*)regional_alloc(region,
1572 sizeof(struct ub_packed_rrset_key));
1574 return 0; /* out of memory */
1575 memset(&(*cname)->entry, 0, sizeof((*cname)->entry));
1576 (*cname)->entry.key = (*cname);
1577 (*cname)->rk.type = htons(LDNS_RR_TYPE_CNAME);
1578 (*cname)->rk.rrset_class = htons(dclass);
1579 (*cname)->rk.flags = 0;
1580 (*cname)->rk.dname = regional_alloc_init(region, qname, qname_len);
1581 if(!(*cname)->rk.dname)
1582 return 0; /* out of memory */
1583 (*cname)->rk.dname_len = qname_len;
1584 (*cname)->entry.hash = rrset_key_hash(&(*cname)->rk);
1585 d = (struct packed_rrset_data*)regional_alloc_zero(region,
1586 sizeof(struct packed_rrset_data) + sizeof(size_t) +
1587 sizeof(uint8_t*) + sizeof(time_t) + sizeof(uint16_t)
1590 return 0; /* out of memory */
1591 (*cname)->entry.data = d;
1592 d->ttl = 0; /* 0 for synthesized CNAME TTL */
1595 d->trust = rrset_trust_ans_noAA;
1596 d->rr_len = (size_t*)((uint8_t*)d +
1597 sizeof(struct packed_rrset_data));
1598 d->rr_len[0] = newlen + sizeof(uint16_t);
1599 packed_rrset_ptr_fixup(d);
1600 d->rr_ttl[0] = d->ttl;
1601 sldns_write_uint16(d->rr_data[0], newlen);
1602 memmove(d->rr_data[0] + sizeof(uint16_t), buf, newlen);
1606 /** add a synthesized CNAME to the answer section */
1608 add_synth_cname(struct auth_zone* z, uint8_t* qname, size_t qname_len,
1609 struct regional* region, struct dns_msg* msg, struct auth_data* dname,
1610 struct auth_rrset* rrset)
1612 struct ub_packed_rrset_key* cname;
1613 /* synthesize a CNAME */
1614 if(!create_synth_cname(qname, qname_len, region, dname, rrset,
1615 z->dclass, &cname)) {
1620 /* cname cannot be create because of YXDOMAIN */
1621 msg->rep->flags |= LDNS_RCODE_YXDOMAIN;
1624 /* add cname to message */
1625 if(!msg_grow_array(region, msg))
1627 msg->rep->rrsets[msg->rep->rrset_count] = cname;
1628 msg->rep->rrset_count++;
1629 msg->rep->an_numrrsets++;
1634 /** Change a dname to a different one, for wildcard namechange */
1636 az_change_dnames(struct dns_msg* msg, uint8_t* oldname, uint8_t* newname,
1637 size_t newlen, int an_only)
1640 size_t start = 0, end = msg->rep->rrset_count;
1641 if(!an_only) start = msg->rep->an_numrrsets;
1642 if(an_only) end = msg->rep->an_numrrsets;
1643 for(i=start; i<end; i++) {
1644 /* allocated in region so we can change the ptrs */
1645 if(query_dname_compare(msg->rep->rrsets[i]->rk.dname, oldname)
1647 msg->rep->rrsets[i]->rk.dname = newname;
1648 msg->rep->rrsets[i]->rk.dname_len = newlen;
1653 /** find NSEC record covering the query */
1654 static struct auth_rrset*
1655 az_find_nsec_cover(struct auth_zone* z, struct auth_data** node)
1657 uint8_t* nm = (*node)->name;
1658 size_t nmlen = (*node)->namelen;
1659 struct auth_rrset* rrset;
1660 /* find the NSEC for the smallest-or-equal node */
1661 /* if node == NULL, we did not find a smaller name. But the zone
1662 * name is the smallest name and should have an NSEC. So there is
1663 * no NSEC to return (for a properly signed zone) */
1664 /* for empty nonterminals, the auth-data node should not exist,
1665 * and thus we don't need to go rbtree_previous here to find
1666 * a domain with an NSEC record */
1667 /* but there could be glue, and if this is node, then it has no NSEC.
1668 * Go up to find nonglue (previous) NSEC-holding nodes */
1669 while((rrset=az_domain_rrset(*node, LDNS_RR_TYPE_NSEC)) == NULL) {
1670 if(dname_is_root(nm)) return NULL;
1671 if(nmlen == z->namelen) return NULL;
1672 dname_remove_label(&nm, &nmlen);
1673 /* adjust *node for the nsec rrset to find in */
1674 *node = az_find_name(z, nm, nmlen);
1679 /** Find NSEC and add for wildcard denial */
1681 az_nsec_wildcard_denial(struct auth_zone* z, struct regional* region,
1682 struct dns_msg* msg, uint8_t* cenm, size_t cenmlen)
1684 struct query_info qinfo;
1686 struct auth_data* node;
1687 struct auth_rrset* nsec;
1688 uint8_t wc[LDNS_MAX_DOMAINLEN];
1689 if(cenmlen+2 > sizeof(wc))
1690 return 0; /* result would be too long */
1691 wc[0] = 1; /* length of wildcard label */
1692 wc[1] = (uint8_t)'*'; /* wildcard label */
1693 memmove(wc+2, cenm, cenmlen);
1695 /* we have '*.ce' in wc wildcard name buffer */
1696 /* get nsec cover for that */
1698 qinfo.qname_len = cenmlen+2;
1701 az_find_domain(z, &qinfo, &node_exact, &node);
1702 if((nsec=az_find_nsec_cover(z, &node)) != NULL) {
1703 if(!msg_add_rrset_ns(z, region, msg, node, nsec)) return 0;
1708 /** Find the NSEC3PARAM rrset (if any) and if true you have the parameters */
1710 az_nsec3_param(struct auth_zone* z, int* algo, size_t* iter, uint8_t** salt,
1713 struct auth_data* apex;
1714 struct auth_rrset* param;
1716 apex = az_find_name(z, z->name, z->namelen);
1718 param = az_domain_rrset(apex, LDNS_RR_TYPE_NSEC3PARAM);
1719 if(!param || param->data->count==0)
1720 return 0; /* no RRset or no RRs in rrset */
1721 /* find out which NSEC3PARAM RR has supported parameters */
1722 /* skip unknown flags (dynamic signer is recalculating nsec3 chain) */
1723 for(i=0; i<param->data->count; i++) {
1724 uint8_t* rdata = param->data->rr_data[i]+2;
1725 size_t rdatalen = param->data->rr_len[i];
1727 continue; /* too short */
1728 if(!nsec3_hash_algo_size_supported((int)(rdata[0])))
1729 continue; /* unsupported algo */
1730 if(rdatalen < (size_t)(2+5+(size_t)rdata[4]))
1731 continue; /* salt missing */
1732 if((rdata[1]&NSEC3_UNKNOWN_FLAGS)!=0)
1733 continue; /* unknown flags */
1734 *algo = (int)(rdata[0]);
1735 *iter = sldns_read_uint16(rdata+2);
1736 *saltlen = rdata[4];
1739 else *salt = rdata+5;
1742 /* no supported params */
1746 /** Hash a name with nsec3param into buffer, it has zone name appended.
1747 * return length of hash */
1749 az_nsec3_hash(uint8_t* buf, size_t buflen, uint8_t* nm, size_t nmlen,
1750 int algo, size_t iter, uint8_t* salt, size_t saltlen)
1752 size_t hlen = nsec3_hash_algo_size_supported(algo);
1753 /* buffer has domain name, nsec3hash, and 256 is for max saltlen
1754 * (salt has 0-255 length) */
1755 unsigned char p[LDNS_MAX_DOMAINLEN+1+N3HASHBUFLEN+256];
1757 if(nmlen+saltlen > sizeof(p) || hlen+saltlen > sizeof(p))
1760 return 0; /* somehow too large for destination buffer */
1761 /* hashfunc(name, salt) */
1762 memmove(p, nm, nmlen);
1763 query_dname_tolower(p);
1764 memmove(p+nmlen, salt, saltlen);
1765 (void)secalgo_nsec3_hash(algo, p, nmlen+saltlen, (unsigned char*)buf);
1766 for(i=0; i<iter; i++) {
1767 /* hashfunc(hash, salt) */
1768 memmove(p, buf, hlen);
1769 memmove(p+hlen, salt, saltlen);
1770 (void)secalgo_nsec3_hash(algo, p, hlen+saltlen,
1771 (unsigned char*)buf);
1776 /** Hash name and return b32encoded hashname for lookup, zone name appended */
1778 az_nsec3_hashname(struct auth_zone* z, uint8_t* hashname, size_t* hashnmlen,
1779 uint8_t* nm, size_t nmlen, int algo, size_t iter, uint8_t* salt,
1782 uint8_t hash[N3HASHBUFLEN];
1785 hlen = az_nsec3_hash(hash, sizeof(hash), nm, nmlen, algo, iter,
1789 if(*hashnmlen < hlen*2+1+z->namelen) /* approx b32 as hexb16 */
1791 ret = sldns_b32_ntop_extended_hex(hash, hlen, (char*)(hashname+1),
1795 hashname[0] = (uint8_t)ret;
1797 if((*hashnmlen) - ret < z->namelen)
1799 memmove(hashname+ret, z->name, z->namelen);
1800 *hashnmlen = z->namelen+(size_t)ret;
1804 /** Find the datanode that covers the nsec3hash-name */
1806 az_nsec3_findnode(struct auth_zone* z, uint8_t* hashnm, size_t hashnmlen)
1808 struct query_info qinfo;
1809 struct auth_data* node;
1813 qinfo.qname = hashnm;
1814 qinfo.qname_len = hashnmlen;
1815 /* because canonical ordering and b32 nsec3 ordering are the same.
1816 * this is a good lookup to find the nsec3 name. */
1817 az_find_domain(z, &qinfo, &node_exact, &node);
1818 /* but we may have to skip non-nsec3 nodes */
1819 /* this may be a lot, the way to speed that up is to have a
1820 * separate nsec3 tree with nsec3 nodes */
1821 while(node && (rbnode_type*)node != RBTREE_NULL &&
1822 !az_domain_rrset(node, LDNS_RR_TYPE_NSEC3)) {
1823 node = (struct auth_data*)rbtree_previous(&node->node);
1825 if((rbnode_type*)node == RBTREE_NULL)
1830 /** Find cover for hashed(nm, nmlen) (or NULL) */
1831 static struct auth_data*
1832 az_nsec3_find_cover(struct auth_zone* z, uint8_t* nm, size_t nmlen,
1833 int algo, size_t iter, uint8_t* salt, size_t saltlen)
1835 struct auth_data* node;
1836 uint8_t hname[LDNS_MAX_DOMAINLEN];
1837 size_t hlen = sizeof(hname);
1838 if(!az_nsec3_hashname(z, hname, &hlen, nm, nmlen, algo, iter,
1841 node = az_nsec3_findnode(z, hname, hlen);
1844 /* we did not find any, perhaps because the NSEC3 hash is before
1845 * the first hash, we have to find the 'last hash' in the zone */
1846 node = (struct auth_data*)rbtree_last(&z->data);
1847 while(node && (rbnode_type*)node != RBTREE_NULL &&
1848 !az_domain_rrset(node, LDNS_RR_TYPE_NSEC3)) {
1849 node = (struct auth_data*)rbtree_previous(&node->node);
1851 if((rbnode_type*)node == RBTREE_NULL)
1856 /** Find exact match for hashed(nm, nmlen) NSEC3 record or NULL */
1857 static struct auth_data*
1858 az_nsec3_find_exact(struct auth_zone* z, uint8_t* nm, size_t nmlen,
1859 int algo, size_t iter, uint8_t* salt, size_t saltlen)
1861 struct auth_data* node;
1862 uint8_t hname[LDNS_MAX_DOMAINLEN];
1863 size_t hlen = sizeof(hname);
1864 if(!az_nsec3_hashname(z, hname, &hlen, nm, nmlen, algo, iter,
1867 node = az_find_name(z, hname, hlen);
1868 if(az_domain_rrset(node, LDNS_RR_TYPE_NSEC3))
1873 /** Return nextcloser name (as a ref into the qname). This is one label
1874 * more than the cenm (cename must be a suffix of qname) */
1876 az_nsec3_get_nextcloser(uint8_t* cenm, uint8_t* qname, size_t qname_len,
1877 uint8_t** nx, size_t* nxlen)
1879 int celabs = dname_count_labels(cenm);
1880 int qlabs = dname_count_labels(qname);
1881 int strip = qlabs - celabs -1;
1882 log_assert(dname_strict_subdomain(qname, qlabs, cenm, celabs));
1886 dname_remove_labels(nx, nxlen, strip);
1889 /** Find the closest encloser that has exact NSEC3.
1890 * updated cenm to the new name. If it went up no-exact-ce is true. */
1891 static struct auth_data*
1892 az_nsec3_find_ce(struct auth_zone* z, uint8_t** cenm, size_t* cenmlen,
1893 int* no_exact_ce, int algo, size_t iter, uint8_t* salt, size_t saltlen)
1895 struct auth_data* node;
1896 while((node = az_nsec3_find_exact(z, *cenm, *cenmlen,
1897 algo, iter, salt, saltlen)) == NULL) {
1898 if(*cenmlen == z->namelen) {
1899 /* next step up would take us out of the zone. fail */
1903 dname_remove_label(cenm, cenmlen);
1908 /* Insert NSEC3 record in authority section, if NULL does nothing */
1910 az_nsec3_insert(struct auth_zone* z, struct regional* region,
1911 struct dns_msg* msg, struct auth_data* node)
1913 struct auth_rrset* nsec3;
1914 if(!node) return 1; /* no node, skip this */
1915 nsec3 = az_domain_rrset(node, LDNS_RR_TYPE_NSEC3);
1916 if(!nsec3) return 1; /* if no nsec3 RR, skip it */
1917 if(!msg_add_rrset_ns(z, region, msg, node, nsec3)) return 0;
1921 /** add NSEC3 records to the zone for the nsec3 proof.
1922 * Specify with the flags with parts of the proof are required.
1923 * the ce is the exact matching name (for notype) but also delegation points.
1924 * qname is the one where the nextcloser name can be derived from.
1925 * If NSEC3 is not properly there (in the zone) nothing is added.
1926 * always enabled: include nsec3 proving about the Closest Encloser.
1927 * that is an exact match that should exist for it.
1928 * If that does not exist, a higher exact match + nxproof is enabled
1929 * (for some sort of opt-out empty nonterminal cases).
1930 * nxproof: include denial of the qname.
1931 * wcproof: include denial of wildcard (wildcard.ce).
1934 az_add_nsec3_proof(struct auth_zone* z, struct regional* region,
1935 struct dns_msg* msg, uint8_t* cenm, size_t cenmlen, uint8_t* qname,
1936 size_t qname_len, int nxproof, int wcproof)
1939 size_t iter, saltlen;
1941 int no_exact_ce = 0;
1942 struct auth_data* node;
1944 /* find parameters of nsec3 proof */
1945 if(!az_nsec3_param(z, &algo, &iter, &salt, &saltlen))
1946 return 1; /* no nsec3 */
1947 /* find ce that has an NSEC3 */
1948 node = az_nsec3_find_ce(z, &cenm, &cenmlen, &no_exact_ce,
1949 algo, iter, salt, saltlen);
1950 if(no_exact_ce) nxproof = 1;
1951 if(!az_nsec3_insert(z, region, msg, node))
1957 /* create nextcloser domain name */
1958 az_nsec3_get_nextcloser(cenm, qname, qname_len, &nx, &nxlen);
1959 /* find nsec3 that matches or covers it */
1960 node = az_nsec3_find_cover(z, nx, nxlen, algo, iter, salt,
1962 if(!az_nsec3_insert(z, region, msg, node))
1966 /* create wildcard name *.ce */
1967 uint8_t wc[LDNS_MAX_DOMAINLEN];
1969 if(cenmlen+2 > sizeof(wc))
1970 return 0; /* result would be too long */
1971 wc[0] = 1; /* length of wildcard label */
1972 wc[1] = (uint8_t)'*'; /* wildcard label */
1973 memmove(wc+2, cenm, cenmlen);
1975 /* find nsec3 that matches or covers it */
1976 node = az_nsec3_find_cover(z, wc, wclen, algo, iter, salt,
1978 if(!az_nsec3_insert(z, region, msg, node))
1984 /** generate answer for positive answer */
1986 az_generate_positive_answer(struct auth_zone* z, struct regional* region,
1987 struct dns_msg* msg, struct auth_data* node, struct auth_rrset* rrset)
1989 if(!msg_add_rrset_an(z, region, msg, node, rrset)) return 0;
1990 /* see if we want additional rrs */
1991 if(rrset->type == LDNS_RR_TYPE_MX) {
1992 if(!az_add_additionals_from(z, region, msg, rrset, 2))
1994 } else if(rrset->type == LDNS_RR_TYPE_SRV) {
1995 if(!az_add_additionals_from(z, region, msg, rrset, 6))
1997 } else if(rrset->type == LDNS_RR_TYPE_NS) {
1998 if(!az_add_additionals_from(z, region, msg, rrset, 0))
2004 /** generate answer for type ANY answer */
2006 az_generate_any_answer(struct auth_zone* z, struct regional* region,
2007 struct dns_msg* msg, struct auth_data* node)
2009 struct auth_rrset* rrset;
2011 /* add a couple (at least one) RRs */
2012 if((rrset=az_domain_rrset(node, LDNS_RR_TYPE_SOA)) != NULL) {
2013 if(!msg_add_rrset_an(z, region, msg, node, rrset)) return 0;
2016 if((rrset=az_domain_rrset(node, LDNS_RR_TYPE_MX)) != NULL) {
2017 if(!msg_add_rrset_an(z, region, msg, node, rrset)) return 0;
2020 if((rrset=az_domain_rrset(node, LDNS_RR_TYPE_A)) != NULL) {
2021 if(!msg_add_rrset_an(z, region, msg, node, rrset)) return 0;
2024 if((rrset=az_domain_rrset(node, LDNS_RR_TYPE_AAAA)) != NULL) {
2025 if(!msg_add_rrset_an(z, region, msg, node, rrset)) return 0;
2028 if(added == 0 && node->rrsets) {
2029 if(!msg_add_rrset_an(z, region, msg, node,
2030 node->rrsets)) return 0;
2035 /** follow cname chain and add more data to the answer section */
2037 follow_cname_chain(struct auth_zone* z, uint16_t qtype,
2038 struct regional* region, struct dns_msg* msg,
2039 struct packed_rrset_data* d)
2042 /* see if we can add the target of the CNAME into the answer */
2043 while(maxchain++ < MAX_CNAME_CHAIN) {
2044 struct auth_data* node;
2045 struct auth_rrset* rrset;
2047 /* d has cname rdata */
2048 if(d->count == 0) break; /* no CNAME */
2049 if(d->rr_len[0] < 2+1) break; /* too small */
2050 if((clen=dname_valid(d->rr_data[0]+2, d->rr_len[0]-2))==0)
2051 break; /* malformed */
2052 if(!dname_subdomain_c(d->rr_data[0]+2, z->name))
2053 break; /* target out of zone */
2054 if((node = az_find_name(z, d->rr_data[0]+2, clen))==NULL)
2055 break; /* no such target name */
2056 if((rrset=az_domain_rrset(node, qtype))!=NULL) {
2057 /* done we found the target */
2058 if(!msg_add_rrset_an(z, region, msg, node, rrset))
2062 if((rrset=az_domain_rrset(node, LDNS_RR_TYPE_CNAME))==NULL)
2063 break; /* no further CNAME chain, notype */
2064 if(!msg_add_rrset_an(z, region, msg, node, rrset)) return 0;
2070 /** generate answer for cname answer */
2072 az_generate_cname_answer(struct auth_zone* z, struct query_info* qinfo,
2073 struct regional* region, struct dns_msg* msg,
2074 struct auth_data* node, struct auth_rrset* rrset)
2076 if(!msg_add_rrset_an(z, region, msg, node, rrset)) return 0;
2077 if(!rrset) return 1;
2078 if(!follow_cname_chain(z, qinfo->qtype, region, msg, rrset->data))
2083 /** generate answer for notype answer */
2085 az_generate_notype_answer(struct auth_zone* z, struct regional* region,
2086 struct dns_msg* msg, struct auth_data* node)
2088 struct auth_rrset* rrset;
2089 if(!az_add_negative_soa(z, region, msg)) return 0;
2090 /* DNSSEC denial NSEC */
2091 if((rrset=az_domain_rrset(node, LDNS_RR_TYPE_NSEC))!=NULL) {
2092 if(!msg_add_rrset_ns(z, region, msg, node, rrset)) return 0;
2094 /* DNSSEC denial NSEC3 */
2095 if(!az_add_nsec3_proof(z, region, msg, node->name,
2096 node->namelen, msg->qinfo.qname,
2097 msg->qinfo.qname_len, 0, 0))
2103 /** generate answer for referral answer */
2105 az_generate_referral_answer(struct auth_zone* z, struct regional* region,
2106 struct dns_msg* msg, struct auth_data* ce, struct auth_rrset* rrset)
2108 struct auth_rrset* ds, *nsec;
2109 /* turn off AA flag, referral is nonAA because it leaves the zone */
2111 msg->rep->flags &= ~BIT_AA;
2112 if(!msg_add_rrset_ns(z, region, msg, ce, rrset)) return 0;
2113 /* add DS or deny it */
2114 if((ds=az_domain_rrset(ce, LDNS_RR_TYPE_DS))!=NULL) {
2115 if(!msg_add_rrset_ns(z, region, msg, ce, ds)) return 0;
2118 if((nsec=az_domain_rrset(ce, LDNS_RR_TYPE_NSEC))!=NULL) {
2119 if(!msg_add_rrset_ns(z, region, msg, ce, nsec))
2122 if(!az_add_nsec3_proof(z, region, msg, ce->name,
2123 ce->namelen, msg->qinfo.qname,
2124 msg->qinfo.qname_len, 0, 0))
2128 /* add additional rrs for type NS */
2129 if(!az_add_additionals_from(z, region, msg, rrset, 0)) return 0;
2133 /** generate answer for DNAME answer */
2135 az_generate_dname_answer(struct auth_zone* z, struct query_info* qinfo,
2136 struct regional* region, struct dns_msg* msg, struct auth_data* ce,
2137 struct auth_rrset* rrset)
2140 /* add the DNAME and then a CNAME */
2141 if(!msg_add_rrset_an(z, region, msg, ce, rrset)) return 0;
2142 if(!add_synth_cname(z, qinfo->qname, qinfo->qname_len, region,
2143 msg, ce, rrset)) return 0;
2144 if(FLAGS_GET_RCODE(msg->rep->flags) == LDNS_RCODE_YXDOMAIN)
2146 if(msg->rep->rrset_count == 0 ||
2147 !msg->rep->rrsets[msg->rep->rrset_count-1])
2149 if(!follow_cname_chain(z, qinfo->qtype, region, msg,
2150 (struct packed_rrset_data*)msg->rep->rrsets[
2151 msg->rep->rrset_count-1]->entry.data))
2156 /** generate answer for wildcard answer */
2158 az_generate_wildcard_answer(struct auth_zone* z, struct query_info* qinfo,
2159 struct regional* region, struct dns_msg* msg, struct auth_data* ce,
2160 struct auth_data* wildcard, struct auth_data* node)
2162 struct auth_rrset* rrset, *nsec;
2163 if(verbosity>=VERB_ALGO) {
2165 sldns_wire2str_dname_buf(wildcard->name, wildcard->namelen,
2166 wcname, sizeof(wcname));
2167 log_info("wildcard %s", wcname);
2169 if((rrset=az_domain_rrset(wildcard, qinfo->qtype)) != NULL) {
2170 /* wildcard has type, add it */
2171 if(!msg_add_rrset_an(z, region, msg, wildcard, rrset))
2173 az_change_dnames(msg, wildcard->name, msg->qinfo.qname,
2174 msg->qinfo.qname_len, 1);
2175 } else if((rrset=az_domain_rrset(wildcard, LDNS_RR_TYPE_CNAME))!=NULL) {
2176 /* wildcard has cname instead, do that */
2177 if(!msg_add_rrset_an(z, region, msg, wildcard, rrset))
2179 az_change_dnames(msg, wildcard->name, msg->qinfo.qname,
2180 msg->qinfo.qname_len, 1);
2181 if(!follow_cname_chain(z, qinfo->qtype, region, msg,
2184 } else if(qinfo->qtype == LDNS_RR_TYPE_ANY && wildcard->rrsets) {
2185 /* add ANY rrsets from wildcard node */
2186 if(!az_generate_any_answer(z, region, msg, wildcard))
2188 az_change_dnames(msg, wildcard->name, msg->qinfo.qname,
2189 msg->qinfo.qname_len, 1);
2191 /* wildcard has nodata, notype answer */
2192 /* call other notype routine for dnssec notype denials */
2193 if(!az_generate_notype_answer(z, region, msg, wildcard))
2197 /* ce and node for dnssec denial of wildcard original name */
2198 if((nsec=az_find_nsec_cover(z, &node)) != NULL) {
2199 if(!msg_add_rrset_ns(z, region, msg, node, nsec)) return 0;
2201 if(!az_add_nsec3_proof(z, region, msg, ce->name,
2202 ce->namelen, msg->qinfo.qname,
2203 msg->qinfo.qname_len, 1, 0))
2207 /* fixup name of wildcard from *.zone to qname, use already allocated
2208 * pointer to msg qname */
2209 az_change_dnames(msg, wildcard->name, msg->qinfo.qname,
2210 msg->qinfo.qname_len, 0);
2214 /** generate answer for nxdomain answer */
2216 az_generate_nxdomain_answer(struct auth_zone* z, struct regional* region,
2217 struct dns_msg* msg, struct auth_data* ce, struct auth_data* node)
2219 struct auth_rrset* nsec;
2220 msg->rep->flags |= LDNS_RCODE_NXDOMAIN;
2221 if(!az_add_negative_soa(z, region, msg)) return 0;
2222 if((nsec=az_find_nsec_cover(z, &node)) != NULL) {
2223 if(!msg_add_rrset_ns(z, region, msg, node, nsec)) return 0;
2224 if(ce && !az_nsec_wildcard_denial(z, region, msg, ce->name,
2225 ce->namelen)) return 0;
2227 if(!az_add_nsec3_proof(z, region, msg, ce->name,
2228 ce->namelen, msg->qinfo.qname,
2229 msg->qinfo.qname_len, 1, 1))
2235 /** Create answers when an exact match exists for the domain name */
2237 az_generate_answer_with_node(struct auth_zone* z, struct query_info* qinfo,
2238 struct regional* region, struct dns_msg* msg, struct auth_data* node)
2240 struct auth_rrset* rrset;
2241 /* positive answer, rrset we are looking for exists */
2242 if((rrset=az_domain_rrset(node, qinfo->qtype)) != NULL) {
2243 return az_generate_positive_answer(z, region, msg, node, rrset);
2246 if((rrset=az_domain_rrset(node, LDNS_RR_TYPE_CNAME)) != NULL) {
2247 return az_generate_cname_answer(z, qinfo, region, msg,
2251 if(qinfo->qtype == LDNS_RR_TYPE_ANY) {
2252 return az_generate_any_answer(z, region, msg, node);
2254 /* NOERROR/NODATA (no such type at domain name) */
2255 return az_generate_notype_answer(z, region, msg, node);
2258 /** Generate answer without an existing-node that we can use.
2259 * So it'll be a referral, DNAME or nxdomain */
2261 az_generate_answer_nonexistnode(struct auth_zone* z, struct query_info* qinfo,
2262 struct regional* region, struct dns_msg* msg, struct auth_data* ce,
2263 struct auth_rrset* rrset, struct auth_data* node)
2265 struct auth_data* wildcard;
2267 /* we do not have an exact matching name (that exists) */
2268 /* see if we have a NS or DNAME in the ce */
2269 if(ce && rrset && rrset->type == LDNS_RR_TYPE_NS) {
2270 return az_generate_referral_answer(z, region, msg, ce, rrset);
2272 if(ce && rrset && rrset->type == LDNS_RR_TYPE_DNAME) {
2273 return az_generate_dname_answer(z, qinfo, region, msg, ce,
2276 /* if there is an empty nonterminal, wildcard and nxdomain don't
2277 * happen, it is a notype answer */
2278 if(az_empty_nonterminal(z, qinfo, node)) {
2279 return az_generate_notype_answer(z, region, msg, node);
2281 /* see if we have a wildcard under the ce */
2282 if((wildcard=az_find_wildcard(z, qinfo, ce)) != NULL) {
2283 return az_generate_wildcard_answer(z, qinfo, region, msg,
2284 ce, wildcard, node);
2286 /* generate nxdomain answer */
2287 return az_generate_nxdomain_answer(z, region, msg, ce, node);
2290 /** Lookup answer in a zone. */
2292 auth_zone_generate_answer(struct auth_zone* z, struct query_info* qinfo,
2293 struct regional* region, struct dns_msg** msg, int* fallback)
2295 struct auth_data* node, *ce;
2296 struct auth_rrset* rrset;
2297 int node_exact, node_exists;
2298 /* does the zone want fallback in case of failure? */
2299 *fallback = z->fallback_enabled;
2300 if(!(*msg=msg_create(region, qinfo))) return 0;
2302 /* lookup if there is a matching domain name for the query */
2303 az_find_domain(z, qinfo, &node_exact, &node);
2305 /* see if node exists for generating answers from (i.e. not glue and
2306 * obscured by NS or DNAME or NSEC3-only), and also return the
2307 * closest-encloser from that, closest node that should be used
2308 * to generate answers from that is above the query */
2309 node_exists = az_find_ce(z, qinfo, node, node_exact, &ce, &rrset);
2311 if(verbosity >= VERB_ALGO) {
2312 char zname[256], qname[256], nname[256], cename[256],
2313 tpstr[32], rrstr[32];
2314 sldns_wire2str_dname_buf(qinfo->qname, qinfo->qname_len, qname,
2316 sldns_wire2str_type_buf(qinfo->qtype, tpstr, sizeof(tpstr));
2317 sldns_wire2str_dname_buf(z->name, z->namelen, zname,
2320 sldns_wire2str_dname_buf(node->name, node->namelen,
2321 nname, sizeof(nname));
2322 else snprintf(nname, sizeof(nname), "NULL");
2324 sldns_wire2str_dname_buf(ce->name, ce->namelen,
2325 cename, sizeof(cename));
2326 else snprintf(cename, sizeof(cename), "NULL");
2327 if(rrset) sldns_wire2str_type_buf(rrset->type, rrstr,
2329 else snprintf(rrstr, sizeof(rrstr), "NULL");
2330 log_info("auth_zone %s query %s %s, domain %s %s %s, "
2331 "ce %s, rrset %s", zname, qname, tpstr, nname,
2332 (node_exact?"exact":"notexact"),
2333 (node_exists?"exist":"notexist"), cename, rrstr);
2337 /* the node is fine, generate answer from node */
2338 return az_generate_answer_with_node(z, qinfo, region, *msg,
2341 return az_generate_answer_nonexistnode(z, qinfo, region, *msg,
2345 int auth_zones_lookup(struct auth_zones* az, struct query_info* qinfo,
2346 struct regional* region, struct dns_msg** msg, int* fallback,
2347 uint8_t* dp_nm, size_t dp_nmlen)
2350 struct auth_zone* z;
2352 /* find the zone that should contain the answer. */
2353 lock_rw_rdlock(&az->lock);
2354 z = auth_zone_find(az, dp_nm, dp_nmlen, qinfo->qclass);
2356 lock_rw_unlock(&az->lock);
2357 verbose(VERB_ALGO, "no auth zone for query, fallback");
2358 /* no auth zone, fallback to internet */
2362 lock_rw_rdlock(&z->lock);
2363 lock_rw_unlock(&az->lock);
2365 /* see what answer that zone would generate */
2366 r = auth_zone_generate_answer(z, qinfo, region, msg, fallback);
2367 lock_rw_unlock(&z->lock);