1 /* 2 * services/localzone.c - local zones authority service. 3 * 4 * Copyright (c) 2007, NLnet Labs. All rights reserved. 5 * 6 * This software is open source. 7 * 8 * Redistribution and use in source and binary forms, with or without 9 * modification, are permitted provided that the following conditions 10 * are met: 11 * 12 * Redistributions of source code must retain the above copyright notice, 13 * this list of conditions and the following disclaimer. 14 * 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. 18 * 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. 22 * 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. 34 */ 35 36 /** 37 * \file 38 * 39 * This file contains functions to enable local zone authority service. 40 */ 41 #include "config.h" 42 #include "services/localzone.h" 43 #include "sldns/str2wire.h" 44 #include "sldns/sbuffer.h" 45 #include "util/regional.h" 46 #include "util/config_file.h" 47 #include "util/data/dname.h" 48 #include "util/data/packed_rrset.h" 49 #include "util/data/msgencode.h" 50 #include "util/net_help.h" 51 #include "util/netevent.h" 52 #include "util/data/msgreply.h" 53 #include "util/data/msgparse.h" 54 #include "util/as112.h" 55 56 /* maximum RRs in an RRset, to cap possible 'endless' list RRs. 57 * with 16 bytes for an A record, a 64K packet has about 4000 max */ 58 #define LOCALZONE_RRSET_COUNT_MAX 4096 59 60 struct local_zones* 61 local_zones_create(void) 62 { 63 struct local_zones* zones = (struct local_zones*)calloc(1, 64 sizeof(*zones)); 65 if(!zones) 66 return NULL; 67 rbtree_init(&zones->ztree, &local_zone_cmp); 68 lock_rw_init(&zones->lock); 69 lock_protect(&zones->lock, &zones->ztree, sizeof(zones->ztree)); 70 /* also lock protects the rbnode's in struct local_zone */ 71 return zones; 72 } 73 74 /** helper traverse to delete zones */ 75 static void 76 lzdel(rbnode_type* n, void* ATTR_UNUSED(arg)) 77 { 78 struct local_zone* z = (struct local_zone*)n->key; 79 local_zone_delete(z); 80 } 81 82 void 83 local_zones_delete(struct local_zones* zones) 84 { 85 if(!zones) 86 return; 87 lock_rw_destroy(&zones->lock); 88 /* walk through zones and delete them all */ 89 traverse_postorder(&zones->ztree, lzdel, NULL); 90 free(zones); 91 } 92 93 void 94 local_zone_delete(struct local_zone* z) 95 { 96 if(!z) 97 return; 98 lock_rw_destroy(&z->lock); 99 regional_destroy(z->region); 100 free(z->name); 101 free(z->taglist); 102 free(z); 103 } 104 105 int 106 local_zone_cmp(const void* z1, const void* z2) 107 { 108 /* first sort on class, so that hierarchy can be maintained within 109 * a class */ 110 struct local_zone* a = (struct local_zone*)z1; 111 struct local_zone* b = (struct local_zone*)z2; 112 int m; 113 if(a->dclass != b->dclass) { 114 if(a->dclass < b->dclass) 115 return -1; 116 return 1; 117 } 118 return dname_lab_cmp(a->name, a->namelabs, b->name, b->namelabs, &m); 119 } 120 121 int 122 local_data_cmp(const void* d1, const void* d2) 123 { 124 struct local_data* a = (struct local_data*)d1; 125 struct local_data* b = (struct local_data*)d2; 126 int m; 127 return dname_canon_lab_cmp(a->name, a->namelabs, b->name, 128 b->namelabs, &m); 129 } 130 131 /* form wireformat from text format domain name */ 132 int 133 parse_dname(const char* str, uint8_t** res, size_t* len, int* labs) 134 { 135 *res = sldns_str2wire_dname(str, len); 136 *labs = 0; 137 if(!*res) { 138 log_err("cannot parse name %s", str); 139 return 0; 140 } 141 *labs = dname_count_size_labels(*res, len); 142 return 1; 143 } 144 145 /** create a new localzone */ 146 static struct local_zone* 147 local_zone_create(uint8_t* nm, size_t len, int labs, 148 enum localzone_type t, uint16_t dclass) 149 { 150 struct local_zone* z = (struct local_zone*)calloc(1, sizeof(*z)); 151 if(!z) { 152 return NULL; 153 } 154 z->node.key = z; 155 z->dclass = dclass; 156 z->type = t; 157 z->name = nm; 158 z->namelen = len; 159 z->namelabs = labs; 160 lock_rw_init(&z->lock); 161 z->region = regional_create_custom(sizeof(struct regional)); 162 if(!z->region) { 163 free(z); 164 return NULL; 165 } 166 rbtree_init(&z->data, &local_data_cmp); 167 lock_protect(&z->lock, &z->parent, sizeof(*z)-sizeof(rbnode_type)); 168 /* also the zones->lock protects node, parent, name*, class */ 169 return z; 170 } 171 172 /** enter a new zone with allocated dname returns with WRlock */ 173 static struct local_zone* 174 lz_enter_zone_dname(struct local_zones* zones, uint8_t* nm, size_t len, 175 int labs, enum localzone_type t, uint16_t c) 176 { 177 struct local_zone* z = local_zone_create(nm, len, labs, t, c); 178 if(!z) { 179 free(nm); 180 log_err("out of memory"); 181 return NULL; 182 } 183 184 /* add to rbtree */ 185 lock_rw_wrlock(&zones->lock); 186 lock_rw_wrlock(&z->lock); 187 if(!rbtree_insert(&zones->ztree, &z->node)) { 188 struct local_zone* oldz; 189 char str[256]; 190 dname_str(nm, str); 191 log_warn("duplicate local-zone %s", str); 192 lock_rw_unlock(&z->lock); 193 /* save zone name locally before deallocation, 194 * otherwise, nm is gone if we zone_delete now. */ 195 oldz = z; 196 /* find the correct zone, so not an error for duplicate */ 197 z = local_zones_find(zones, nm, len, labs, c); 198 lock_rw_wrlock(&z->lock); 199 lock_rw_unlock(&zones->lock); 200 local_zone_delete(oldz); 201 return z; 202 } 203 lock_rw_unlock(&zones->lock); 204 return z; 205 } 206 207 /** enter a new zone */ 208 static struct local_zone* 209 lz_enter_zone(struct local_zones* zones, const char* name, const char* type, 210 uint16_t dclass) 211 { 212 struct local_zone* z; 213 enum localzone_type t; 214 uint8_t* nm; 215 size_t len; 216 int labs; 217 if(!parse_dname(name, &nm, &len, &labs)) { 218 log_err("bad zone name %s %s", name, type); 219 return NULL; 220 } 221 if(!local_zone_str2type(type, &t)) { 222 log_err("bad lz_enter_zone type %s %s", name, type); 223 free(nm); 224 return NULL; 225 } 226 if(!(z=lz_enter_zone_dname(zones, nm, len, labs, t, dclass))) { 227 log_err("could not enter zone %s %s", name, type); 228 return NULL; 229 } 230 return z; 231 } 232 233 int 234 rrstr_get_rr_content(const char* str, uint8_t** nm, uint16_t* type, 235 uint16_t* dclass, time_t* ttl, uint8_t* rr, size_t len, 236 uint8_t** rdata, size_t* rdata_len) 237 { 238 size_t dname_len = 0; 239 int e = sldns_str2wire_rr_buf(str, rr, &len, &dname_len, 3600, 240 NULL, 0, NULL, 0); 241 if(e) { 242 log_err("error parsing local-data at %d: '%s': %s", 243 LDNS_WIREPARSE_OFFSET(e), str, 244 sldns_get_errorstr_parse(e)); 245 return 0; 246 } 247 *nm = memdup(rr, dname_len); 248 if(!*nm) { 249 log_err("out of memory"); 250 return 0; 251 } 252 *dclass = sldns_wirerr_get_class(rr, len, dname_len); 253 *type = sldns_wirerr_get_type(rr, len, dname_len); 254 *ttl = (time_t)sldns_wirerr_get_ttl(rr, len, dname_len); 255 *rdata = sldns_wirerr_get_rdatawl(rr, len, dname_len); 256 *rdata_len = sldns_wirerr_get_rdatalen(rr, len, dname_len)+2; 257 return 1; 258 } 259 260 /** return name and class of rr; parses string */ 261 static int 262 get_rr_nameclass(const char* str, uint8_t** nm, uint16_t* dclass, 263 uint16_t* dtype) 264 { 265 uint8_t rr[LDNS_RR_BUF_SIZE]; 266 size_t len = sizeof(rr), dname_len = 0; 267 int s = sldns_str2wire_rr_buf(str, rr, &len, &dname_len, 3600, 268 NULL, 0, NULL, 0); 269 if(s != 0) { 270 log_err("error parsing local-data at %d '%s': %s", 271 LDNS_WIREPARSE_OFFSET(s), str, 272 sldns_get_errorstr_parse(s)); 273 return 0; 274 } 275 *nm = memdup(rr, dname_len); 276 *dclass = sldns_wirerr_get_class(rr, len, dname_len); 277 *dtype = sldns_wirerr_get_type(rr, len, dname_len); 278 if(!*nm) { 279 log_err("out of memory"); 280 return 0; 281 } 282 return 1; 283 } 284 285 /** 286 * Find an rrset in local data structure. 287 * @param data: local data domain name structure. 288 * @param type: type to look for (host order). 289 * @param alias_ok: 1 if matching a non-exact, alias type such as CNAME is 290 * allowed. otherwise 0. 291 * @return rrset pointer or NULL if not found. 292 */ 293 static struct local_rrset* 294 local_data_find_type(struct local_data* data, uint16_t type, int alias_ok) 295 { 296 struct local_rrset* p; 297 type = htons(type); 298 for(p = data->rrsets; p; p = p->next) { 299 if(p->rrset->rk.type == type) 300 return p; 301 if(alias_ok && p->rrset->rk.type == htons(LDNS_RR_TYPE_CNAME)) 302 return p; 303 } 304 return NULL; 305 } 306 307 /** check for RR duplicates */ 308 static int 309 rr_is_duplicate(struct packed_rrset_data* pd, uint8_t* rdata, size_t rdata_len) 310 { 311 size_t i; 312 for(i=0; i<pd->count; i++) { 313 if(pd->rr_len[i] == rdata_len && 314 memcmp(pd->rr_data[i], rdata, rdata_len) == 0) 315 return 1; 316 } 317 return 0; 318 } 319 320 /** new local_rrset */ 321 static struct local_rrset* 322 new_local_rrset(struct regional* region, struct local_data* node, 323 uint16_t rrtype, uint16_t rrclass) 324 { 325 struct packed_rrset_data* pd; 326 struct local_rrset* rrset = (struct local_rrset*) 327 regional_alloc_zero(region, sizeof(*rrset)); 328 if(!rrset) { 329 log_err("out of memory"); 330 return NULL; 331 } 332 rrset->next = node->rrsets; 333 node->rrsets = rrset; 334 rrset->rrset = (struct ub_packed_rrset_key*) 335 regional_alloc_zero(region, sizeof(*rrset->rrset)); 336 if(!rrset->rrset) { 337 log_err("out of memory"); 338 return NULL; 339 } 340 rrset->rrset->entry.key = rrset->rrset; 341 pd = (struct packed_rrset_data*)regional_alloc_zero(region, 342 sizeof(*pd)); 343 if(!pd) { 344 log_err("out of memory"); 345 return NULL; 346 } 347 pd->trust = rrset_trust_prim_noglue; 348 pd->security = sec_status_insecure; 349 rrset->rrset->entry.data = pd; 350 rrset->rrset->rk.dname = node->name; 351 rrset->rrset->rk.dname_len = node->namelen; 352 rrset->rrset->rk.type = htons(rrtype); 353 rrset->rrset->rk.rrset_class = htons(rrclass); 354 return rrset; 355 } 356 357 /** insert RR into RRset data structure; Wastes a couple of bytes */ 358 int 359 rrset_insert_rr(struct regional* region, struct packed_rrset_data* pd, 360 uint8_t* rdata, size_t rdata_len, time_t ttl, const char* rrstr) 361 { 362 size_t* oldlen = pd->rr_len; 363 time_t* oldttl = pd->rr_ttl; 364 uint8_t** olddata = pd->rr_data; 365 366 /* add RR to rrset */ 367 if(pd->count > LOCALZONE_RRSET_COUNT_MAX) { 368 log_warn("RRset '%s' has more than %d records, record ignored", 369 rrstr, LOCALZONE_RRSET_COUNT_MAX); 370 return 1; 371 } 372 pd->count++; 373 pd->rr_len = regional_alloc(region, sizeof(*pd->rr_len)*pd->count); 374 pd->rr_ttl = regional_alloc(region, sizeof(*pd->rr_ttl)*pd->count); 375 pd->rr_data = regional_alloc(region, sizeof(*pd->rr_data)*pd->count); 376 if(!pd->rr_len || !pd->rr_ttl || !pd->rr_data) { 377 log_err("out of memory"); 378 return 0; 379 } 380 if(pd->count > 1) { 381 memcpy(pd->rr_len+1, oldlen, 382 sizeof(*pd->rr_len)*(pd->count-1)); 383 memcpy(pd->rr_ttl+1, oldttl, 384 sizeof(*pd->rr_ttl)*(pd->count-1)); 385 memcpy(pd->rr_data+1, olddata, 386 sizeof(*pd->rr_data)*(pd->count-1)); 387 } 388 pd->rr_len[0] = rdata_len; 389 pd->rr_ttl[0] = ttl; 390 pd->rr_data[0] = regional_alloc_init(region, rdata, rdata_len); 391 if(!pd->rr_data[0]) { 392 log_err("out of memory"); 393 return 0; 394 } 395 return 1; 396 } 397 398 /** find a data node by exact name */ 399 static struct local_data* 400 lz_find_node(struct local_zone* z, uint8_t* nm, size_t nmlen, int nmlabs) 401 { 402 struct local_data key; 403 key.node.key = &key; 404 key.name = nm; 405 key.namelen = nmlen; 406 key.namelabs = nmlabs; 407 return (struct local_data*)rbtree_search(&z->data, &key.node); 408 } 409 410 /** find a node, create it if not and all its empty nonterminal parents */ 411 static int 412 lz_find_create_node(struct local_zone* z, uint8_t* nm, size_t nmlen, 413 int nmlabs, struct local_data** res) 414 { 415 struct local_data* ld = lz_find_node(z, nm, nmlen, nmlabs); 416 if(!ld) { 417 /* create a domain name to store rr. */ 418 ld = (struct local_data*)regional_alloc_zero(z->region, 419 sizeof(*ld)); 420 if(!ld) { 421 log_err("out of memory adding local data"); 422 return 0; 423 } 424 ld->node.key = ld; 425 ld->name = regional_alloc_init(z->region, nm, nmlen); 426 if(!ld->name) { 427 log_err("out of memory"); 428 return 0; 429 } 430 ld->namelen = nmlen; 431 ld->namelabs = nmlabs; 432 if(!rbtree_insert(&z->data, &ld->node)) { 433 log_assert(0); /* duplicate name */ 434 } 435 /* see if empty nonterminals need to be created */ 436 if(nmlabs > z->namelabs) { 437 dname_remove_label(&nm, &nmlen); 438 if(!lz_find_create_node(z, nm, nmlen, nmlabs-1, res)) 439 return 0; 440 } 441 } 442 *res = ld; 443 return 1; 444 } 445 446 /** enter data RR into auth zone */ 447 static int 448 lz_enter_rr_into_zone(struct local_zone* z, const char* rrstr) 449 { 450 uint8_t* nm; 451 size_t nmlen; 452 int nmlabs; 453 struct local_data* node; 454 struct local_rrset* rrset; 455 struct packed_rrset_data* pd; 456 uint16_t rrtype = 0, rrclass = 0; 457 time_t ttl = 0; 458 uint8_t rr[LDNS_RR_BUF_SIZE]; 459 uint8_t* rdata; 460 size_t rdata_len; 461 if(!rrstr_get_rr_content(rrstr, &nm, &rrtype, &rrclass, &ttl, rr, 462 sizeof(rr), &rdata, &rdata_len)) { 463 log_err("bad local-data: %s", rrstr); 464 return 0; 465 } 466 log_assert(z->dclass == rrclass); 467 if(z->type == local_zone_redirect && 468 query_dname_compare(z->name, nm) != 0) { 469 log_err("local-data in redirect zone must reside at top of zone" 470 ", not at %s", rrstr); 471 free(nm); 472 return 0; 473 } 474 nmlabs = dname_count_size_labels(nm, &nmlen); 475 if(!lz_find_create_node(z, nm, nmlen, nmlabs, &node)) { 476 free(nm); 477 return 0; 478 } 479 log_assert(node); 480 free(nm); 481 482 /* Reject it if we would end up having CNAME and other data (including 483 * another CNAME) for a redirect zone. */ 484 if(z->type == local_zone_redirect && node->rrsets) { 485 const char* othertype = NULL; 486 if (rrtype == LDNS_RR_TYPE_CNAME) 487 othertype = "other"; 488 else if (node->rrsets->rrset->rk.type == 489 htons(LDNS_RR_TYPE_CNAME)) { 490 othertype = "CNAME"; 491 } 492 if(othertype) { 493 log_err("local-data '%s' in redirect zone must not " 494 "coexist with %s local-data", rrstr, othertype); 495 return 0; 496 } 497 } 498 rrset = local_data_find_type(node, rrtype, 0); 499 if(!rrset) { 500 rrset = new_local_rrset(z->region, node, rrtype, rrclass); 501 if(!rrset) 502 return 0; 503 if(query_dname_compare(node->name, z->name) == 0) { 504 if(rrtype == LDNS_RR_TYPE_NSEC) 505 rrset->rrset->rk.flags = PACKED_RRSET_NSEC_AT_APEX; 506 if(rrtype == LDNS_RR_TYPE_SOA) 507 z->soa = rrset->rrset; 508 } 509 } 510 pd = (struct packed_rrset_data*)rrset->rrset->entry.data; 511 log_assert(rrset && pd); 512 513 /* check for duplicate RR */ 514 if(rr_is_duplicate(pd, rdata, rdata_len)) { 515 verbose(VERB_ALGO, "ignoring duplicate RR: %s", rrstr); 516 return 1; 517 } 518 return rrset_insert_rr(z->region, pd, rdata, rdata_len, ttl, rrstr); 519 } 520 521 /** enter a data RR into auth data; a zone for it must exist */ 522 static int 523 lz_enter_rr_str(struct local_zones* zones, const char* rr) 524 { 525 uint8_t* rr_name; 526 uint16_t rr_class, rr_type; 527 size_t len; 528 int labs; 529 struct local_zone* z; 530 int r; 531 if(!get_rr_nameclass(rr, &rr_name, &rr_class, &rr_type)) { 532 log_err("bad rr %s", rr); 533 return 0; 534 } 535 labs = dname_count_size_labels(rr_name, &len); 536 lock_rw_rdlock(&zones->lock); 537 z = local_zones_lookup(zones, rr_name, len, labs, rr_class, rr_type); 538 if(!z) { 539 lock_rw_unlock(&zones->lock); 540 fatal_exit("internal error: no zone for rr %s", rr); 541 } 542 lock_rw_wrlock(&z->lock); 543 lock_rw_unlock(&zones->lock); 544 free(rr_name); 545 r = lz_enter_rr_into_zone(z, rr); 546 lock_rw_unlock(&z->lock); 547 return r; 548 } 549 550 /** enter tagstring into zone */ 551 static int 552 lz_enter_zone_tag(struct local_zones* zones, char* zname, uint8_t* list, 553 size_t len, uint16_t rr_class) 554 { 555 uint8_t dname[LDNS_MAX_DOMAINLEN+1]; 556 size_t dname_len = sizeof(dname); 557 int dname_labs, r = 0; 558 struct local_zone* z; 559 560 if(sldns_str2wire_dname_buf(zname, dname, &dname_len) != 0) { 561 log_err("cannot parse zone name in local-zone-tag: %s", zname); 562 return 0; 563 } 564 dname_labs = dname_count_labels(dname); 565 566 lock_rw_rdlock(&zones->lock); 567 z = local_zones_find(zones, dname, dname_len, dname_labs, rr_class); 568 if(!z) { 569 lock_rw_unlock(&zones->lock); 570 log_err("no local-zone for tag %s", zname); 571 return 0; 572 } 573 lock_rw_wrlock(&z->lock); 574 lock_rw_unlock(&zones->lock); 575 free(z->taglist); 576 z->taglist = memdup(list, len); 577 z->taglen = len; 578 if(z->taglist) 579 r = 1; 580 lock_rw_unlock(&z->lock); 581 return r; 582 } 583 584 /** enter override into zone */ 585 static int 586 lz_enter_override(struct local_zones* zones, char* zname, char* netblock, 587 char* type, uint16_t rr_class) 588 { 589 uint8_t dname[LDNS_MAX_DOMAINLEN+1]; 590 size_t dname_len = sizeof(dname); 591 int dname_labs; 592 struct sockaddr_storage addr; 593 int net; 594 socklen_t addrlen; 595 struct local_zone* z; 596 enum localzone_type t; 597 598 /* parse zone name */ 599 if(sldns_str2wire_dname_buf(zname, dname, &dname_len) != 0) { 600 log_err("cannot parse zone name in local-zone-override: %s %s", 601 zname, netblock); 602 return 0; 603 } 604 dname_labs = dname_count_labels(dname); 605 606 /* parse netblock */ 607 if(!netblockstrtoaddr(netblock, UNBOUND_DNS_PORT, &addr, &addrlen, 608 &net)) { 609 log_err("cannot parse netblock in local-zone-override: %s %s", 610 zname, netblock); 611 return 0; 612 } 613 614 /* parse zone type */ 615 if(!local_zone_str2type(type, &t)) { 616 log_err("cannot parse type in local-zone-override: %s %s %s", 617 zname, netblock, type); 618 return 0; 619 } 620 621 /* find localzone entry */ 622 lock_rw_rdlock(&zones->lock); 623 z = local_zones_find(zones, dname, dname_len, dname_labs, rr_class); 624 if(!z) { 625 lock_rw_unlock(&zones->lock); 626 log_err("no local-zone for local-zone-override %s", zname); 627 return 0; 628 } 629 lock_rw_wrlock(&z->lock); 630 lock_rw_unlock(&zones->lock); 631 632 /* create netblock addr_tree if not present yet */ 633 if(!z->override_tree) { 634 z->override_tree = (struct rbtree_type*)regional_alloc_zero( 635 z->region, sizeof(*z->override_tree)); 636 if(!z->override_tree) { 637 lock_rw_unlock(&z->lock); 638 log_err("out of memory"); 639 return 0; 640 } 641 addr_tree_init(z->override_tree); 642 } 643 /* add new elem to tree */ 644 if(z->override_tree) { 645 struct local_zone_override* n; 646 n = (struct local_zone_override*)regional_alloc_zero( 647 z->region, sizeof(*n)); 648 if(!n) { 649 lock_rw_unlock(&z->lock); 650 log_err("out of memory"); 651 return 0; 652 } 653 n->type = t; 654 if(!addr_tree_insert(z->override_tree, 655 (struct addr_tree_node*)n, &addr, addrlen, net)) { 656 lock_rw_unlock(&z->lock); 657 log_err("duplicate local-zone-override %s %s", 658 zname, netblock); 659 return 1; 660 } 661 } 662 663 lock_rw_unlock(&z->lock); 664 return 1; 665 } 666 667 /** parse local-zone: statements */ 668 static int 669 lz_enter_zones(struct local_zones* zones, struct config_file* cfg) 670 { 671 struct config_str2list* p; 672 struct local_zone* z; 673 for(p = cfg->local_zones; p; p = p->next) { 674 if(!(z=lz_enter_zone(zones, p->str, p->str2, 675 LDNS_RR_CLASS_IN))) 676 return 0; 677 lock_rw_unlock(&z->lock); 678 } 679 return 1; 680 } 681 682 /** lookup a zone in rbtree; exact match only; SLOW due to parse */ 683 static int 684 lz_exists(struct local_zones* zones, const char* name) 685 { 686 struct local_zone z; 687 z.node.key = &z; 688 z.dclass = LDNS_RR_CLASS_IN; 689 if(!parse_dname(name, &z.name, &z.namelen, &z.namelabs)) { 690 log_err("bad name %s", name); 691 return 0; 692 } 693 lock_rw_rdlock(&zones->lock); 694 if(rbtree_search(&zones->ztree, &z.node)) { 695 lock_rw_unlock(&zones->lock); 696 free(z.name); 697 return 1; 698 } 699 lock_rw_unlock(&zones->lock); 700 free(z.name); 701 return 0; 702 } 703 704 /** lookup a zone in cfg->nodefault list */ 705 static int 706 lz_nodefault(struct config_file* cfg, const char* name) 707 { 708 struct config_strlist* p; 709 size_t len = strlen(name); 710 if(len == 0) return 0; 711 if(name[len-1] == '.') len--; 712 713 for(p = cfg->local_zones_nodefault; p; p = p->next) { 714 /* compare zone name, lowercase, compare without ending . */ 715 if(strncasecmp(p->str, name, len) == 0 && 716 (strlen(p->str) == len || (strlen(p->str)==len+1 && 717 p->str[len] == '.'))) 718 return 1; 719 } 720 return 0; 721 } 722 723 /** enter (AS112) empty default zone */ 724 static int 725 add_empty_default(struct local_zones* zones, struct config_file* cfg, 726 const char* name) 727 { 728 struct local_zone* z; 729 char str[1024]; /* known long enough */ 730 if(lz_exists(zones, name) || lz_nodefault(cfg, name)) 731 return 1; /* do not enter default content */ 732 if(!(z=lz_enter_zone(zones, name, "static", LDNS_RR_CLASS_IN))) 733 return 0; 734 snprintf(str, sizeof(str), "%s 10800 IN SOA localhost. " 735 "nobody.invalid. 1 3600 1200 604800 10800", name); 736 if(!lz_enter_rr_into_zone(z, str)) { 737 lock_rw_unlock(&z->lock); 738 return 0; 739 } 740 snprintf(str, sizeof(str), "%s 10800 IN NS localhost. ", name); 741 if(!lz_enter_rr_into_zone(z, str)) { 742 lock_rw_unlock(&z->lock); 743 return 0; 744 } 745 lock_rw_unlock(&z->lock); 746 return 1; 747 } 748 749 /** enter default zones */ 750 int local_zone_enter_defaults(struct local_zones* zones, struct config_file* cfg) 751 { 752 struct local_zone* z; 753 const char** zstr; 754 755 /* Do not add any default */ 756 if(cfg->local_zones_disable_default) 757 return 1; 758 759 /* this list of zones is from RFC 6303 and RFC 7686 */ 760 761 /* block localhost level zones first, then onion and later the LAN zones */ 762 763 /* localhost. zone */ 764 if(!lz_exists(zones, "localhost.") && 765 !lz_nodefault(cfg, "localhost.")) { 766 if(!(z=lz_enter_zone(zones, "localhost.", "redirect", 767 LDNS_RR_CLASS_IN)) || 768 !lz_enter_rr_into_zone(z, 769 "localhost. 10800 IN NS localhost.") || 770 !lz_enter_rr_into_zone(z, 771 "localhost. 10800 IN SOA localhost. nobody.invalid. " 772 "1 3600 1200 604800 10800") || 773 !lz_enter_rr_into_zone(z, 774 "localhost. 10800 IN A 127.0.0.1") || 775 !lz_enter_rr_into_zone(z, 776 "localhost. 10800 IN AAAA ::1")) { 777 log_err("out of memory adding default zone"); 778 if(z) { lock_rw_unlock(&z->lock); } 779 return 0; 780 } 781 lock_rw_unlock(&z->lock); 782 } 783 /* reverse ip4 zone */ 784 if(!lz_exists(zones, "127.in-addr.arpa.") && 785 !lz_nodefault(cfg, "127.in-addr.arpa.")) { 786 if(!(z=lz_enter_zone(zones, "127.in-addr.arpa.", "static", 787 LDNS_RR_CLASS_IN)) || 788 !lz_enter_rr_into_zone(z, 789 "127.in-addr.arpa. 10800 IN NS localhost.") || 790 !lz_enter_rr_into_zone(z, 791 "127.in-addr.arpa. 10800 IN SOA localhost. " 792 "nobody.invalid. 1 3600 1200 604800 10800") || 793 !lz_enter_rr_into_zone(z, 794 "1.0.0.127.in-addr.arpa. 10800 IN PTR localhost.")) { 795 log_err("out of memory adding default zone"); 796 if(z) { lock_rw_unlock(&z->lock); } 797 return 0; 798 } 799 lock_rw_unlock(&z->lock); 800 } 801 /* reverse ip6 zone */ 802 if(!lz_exists(zones, "1.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.ip6.arpa.") && 803 !lz_nodefault(cfg, "1.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.ip6.arpa.")) { 804 if(!(z=lz_enter_zone(zones, "1.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.ip6.arpa.", "static", 805 LDNS_RR_CLASS_IN)) || 806 !lz_enter_rr_into_zone(z, 807 "1.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.ip6.arpa. 10800 IN NS localhost.") || 808 !lz_enter_rr_into_zone(z, 809 "1.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.ip6.arpa. 10800 IN SOA localhost. " 810 "nobody.invalid. 1 3600 1200 604800 10800") || 811 !lz_enter_rr_into_zone(z, 812 "1.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.0.ip6.arpa. 10800 IN PTR localhost.")) { 813 log_err("out of memory adding default zone"); 814 if(z) { lock_rw_unlock(&z->lock); } 815 return 0; 816 } 817 lock_rw_unlock(&z->lock); 818 } 819 /* onion. zone (RFC 7686) */ 820 if(!add_empty_default(zones, cfg, "onion.")) { 821 log_err("out of memory adding default zone"); 822 return 0; 823 } 824 /* test. zone (RFC 7686) */ 825 if(!add_empty_default(zones, cfg, "test.")) { 826 log_err("out of memory adding default zone"); 827 return 0; 828 } 829 /* invalid. zone (RFC 7686) */ 830 if(!add_empty_default(zones, cfg, "invalid.")) { 831 log_err("out of memory adding default zone"); 832 return 0; 833 } 834 /* block AS112 zones, unless asked not to */ 835 if(!cfg->unblock_lan_zones) { 836 for(zstr = as112_zones; *zstr; zstr++) { 837 if(!add_empty_default(zones, cfg, *zstr)) { 838 log_err("out of memory adding default zone"); 839 return 0; 840 } 841 } 842 } 843 return 1; 844 } 845 846 /** parse local-zone-override: statements */ 847 static int 848 lz_enter_overrides(struct local_zones* zones, struct config_file* cfg) 849 { 850 struct config_str3list* p; 851 for(p = cfg->local_zone_overrides; p; p = p->next) { 852 if(!lz_enter_override(zones, p->str, p->str2, p->str3, 853 LDNS_RR_CLASS_IN)) 854 return 0; 855 } 856 return 1; 857 } 858 859 /** setup parent pointers, so that a lookup can be done for closest match */ 860 static void 861 init_parents(struct local_zones* zones) 862 { 863 struct local_zone* node, *prev = NULL, *p; 864 int m; 865 lock_rw_wrlock(&zones->lock); 866 RBTREE_FOR(node, struct local_zone*, &zones->ztree) { 867 lock_rw_wrlock(&node->lock); 868 node->parent = NULL; 869 if(!prev || prev->dclass != node->dclass) { 870 prev = node; 871 lock_rw_unlock(&node->lock); 872 continue; 873 } 874 (void)dname_lab_cmp(prev->name, prev->namelabs, node->name, 875 node->namelabs, &m); /* we know prev is smaller */ 876 /* sort order like: . com. bla.com. zwb.com. net. */ 877 /* find the previous, or parent-parent-parent */ 878 for(p = prev; p; p = p->parent) 879 /* looking for name with few labels, a parent */ 880 if(p->namelabs <= m) { 881 /* ==: since prev matched m, this is closest*/ 882 /* <: prev matches more, but is not a parent, 883 * this one is a (grand)parent */ 884 node->parent = p; 885 break; 886 } 887 prev = node; 888 889 if(node->override_tree) 890 addr_tree_init_parents(node->override_tree); 891 lock_rw_unlock(&node->lock); 892 } 893 lock_rw_unlock(&zones->lock); 894 } 895 896 /** enter implicit transparent zone for local-data: without local-zone: */ 897 static int 898 lz_setup_implicit(struct local_zones* zones, struct config_file* cfg) 899 { 900 /* walk over all items that have no parent zone and find 901 * the name that covers them all (could be the root) and 902 * add that as a transparent zone */ 903 struct config_strlist* p; 904 int have_name = 0; 905 int have_other_classes = 0; 906 uint16_t dclass = 0; 907 uint8_t* nm = 0; 908 size_t nmlen = 0; 909 int nmlabs = 0; 910 int match = 0; /* number of labels match count */ 911 912 init_parents(zones); /* to enable local_zones_lookup() */ 913 for(p = cfg->local_data; p; p = p->next) { 914 uint8_t* rr_name; 915 uint16_t rr_class, rr_type; 916 size_t len; 917 int labs; 918 if(!get_rr_nameclass(p->str, &rr_name, &rr_class, &rr_type)) { 919 log_err("Bad local-data RR %s", p->str); 920 return 0; 921 } 922 labs = dname_count_size_labels(rr_name, &len); 923 lock_rw_rdlock(&zones->lock); 924 if(!local_zones_lookup(zones, rr_name, len, labs, rr_class, 925 rr_type)) { 926 if(!have_name) { 927 dclass = rr_class; 928 nm = rr_name; 929 nmlen = len; 930 nmlabs = labs; 931 match = labs; 932 have_name = 1; 933 } else { 934 int m; 935 if(rr_class != dclass) { 936 /* process other classes later */ 937 free(rr_name); 938 have_other_classes = 1; 939 lock_rw_unlock(&zones->lock); 940 continue; 941 } 942 /* find smallest shared topdomain */ 943 (void)dname_lab_cmp(nm, nmlabs, 944 rr_name, labs, &m); 945 free(rr_name); 946 if(m < match) 947 match = m; 948 } 949 } else free(rr_name); 950 lock_rw_unlock(&zones->lock); 951 } 952 if(have_name) { 953 uint8_t* n2; 954 struct local_zone* z; 955 /* allocate zone of smallest shared topdomain to contain em */ 956 n2 = nm; 957 dname_remove_labels(&n2, &nmlen, nmlabs - match); 958 n2 = memdup(n2, nmlen); 959 free(nm); 960 if(!n2) { 961 log_err("out of memory"); 962 return 0; 963 } 964 log_nametypeclass(VERB_ALGO, "implicit transparent local-zone", 965 n2, 0, dclass); 966 if(!(z=lz_enter_zone_dname(zones, n2, nmlen, match, 967 local_zone_transparent, dclass))) { 968 return 0; 969 } 970 lock_rw_unlock(&z->lock); 971 } 972 if(have_other_classes) { 973 /* restart to setup other class */ 974 return lz_setup_implicit(zones, cfg); 975 } 976 return 1; 977 } 978 979 /** enter local-zone-tag info */ 980 static int 981 lz_enter_zone_tags(struct local_zones* zones, struct config_file* cfg) 982 { 983 struct config_strbytelist* p; 984 int c = 0; 985 for(p = cfg->local_zone_tags; p; p = p->next) { 986 if(!lz_enter_zone_tag(zones, p->str, p->str2, p->str2len, 987 LDNS_RR_CLASS_IN)) 988 return 0; 989 c++; 990 } 991 if(c) verbose(VERB_ALGO, "applied tags to %d local zones", c); 992 return 1; 993 } 994 995 /** enter auth data */ 996 static int 997 lz_enter_data(struct local_zones* zones, struct config_file* cfg) 998 { 999 struct config_strlist* p; 1000 for(p = cfg->local_data; p; p = p->next) { 1001 if(!lz_enter_rr_str(zones, p->str)) 1002 return 0; 1003 } 1004 return 1; 1005 } 1006 1007 /** free memory from config */ 1008 static void 1009 lz_freeup_cfg(struct config_file* cfg) 1010 { 1011 config_deldblstrlist(cfg->local_zones); 1012 cfg->local_zones = NULL; 1013 config_delstrlist(cfg->local_zones_nodefault); 1014 cfg->local_zones_nodefault = NULL; 1015 config_delstrlist(cfg->local_data); 1016 cfg->local_data = NULL; 1017 } 1018 1019 int 1020 local_zones_apply_cfg(struct local_zones* zones, struct config_file* cfg) 1021 { 1022 /* create zones from zone statements. */ 1023 if(!lz_enter_zones(zones, cfg)) { 1024 return 0; 1025 } 1026 /* apply default zones+content (unless disabled, or overridden) */ 1027 if(!local_zone_enter_defaults(zones, cfg)) { 1028 return 0; 1029 } 1030 /* enter local zone overrides */ 1031 if(!lz_enter_overrides(zones, cfg)) { 1032 return 0; 1033 } 1034 /* create implicit transparent zone from data. */ 1035 if(!lz_setup_implicit(zones, cfg)) { 1036 return 0; 1037 } 1038 1039 /* setup parent ptrs for lookup during data entry */ 1040 init_parents(zones); 1041 /* insert local zone tags */ 1042 if(!lz_enter_zone_tags(zones, cfg)) { 1043 return 0; 1044 } 1045 /* insert local data */ 1046 if(!lz_enter_data(zones, cfg)) { 1047 return 0; 1048 } 1049 /* freeup memory from cfg struct. */ 1050 lz_freeup_cfg(cfg); 1051 return 1; 1052 } 1053 1054 struct local_zone* 1055 local_zones_lookup(struct local_zones* zones, 1056 uint8_t* name, size_t len, int labs, uint16_t dclass, uint16_t dtype) 1057 { 1058 return local_zones_tags_lookup(zones, name, len, labs, 1059 dclass, dtype, NULL, 0, 1); 1060 } 1061 1062 struct local_zone* 1063 local_zones_tags_lookup(struct local_zones* zones, 1064 uint8_t* name, size_t len, int labs, uint16_t dclass, uint16_t dtype, 1065 uint8_t* taglist, size_t taglen, int ignoretags) 1066 { 1067 rbnode_type* res = NULL; 1068 struct local_zone *result; 1069 struct local_zone key; 1070 int m; 1071 /* for type DS use a zone higher when on a zonecut */ 1072 if(dtype == LDNS_RR_TYPE_DS && !dname_is_root(name)) { 1073 dname_remove_label(&name, &len); 1074 labs--; 1075 } 1076 key.node.key = &key; 1077 key.dclass = dclass; 1078 key.name = name; 1079 key.namelen = len; 1080 key.namelabs = labs; 1081 rbtree_find_less_equal(&zones->ztree, &key, &res); 1082 result = (struct local_zone*)res; 1083 /* exact or smaller element (or no element) */ 1084 if(!result || result->dclass != dclass) 1085 return NULL; 1086 /* count number of labels matched */ 1087 (void)dname_lab_cmp(result->name, result->namelabs, key.name, 1088 key.namelabs, &m); 1089 while(result) { /* go up until qname is zone or subdomain of zone */ 1090 if(result->namelabs <= m) 1091 if(ignoretags || !result->taglist || 1092 taglist_intersect(result->taglist, 1093 result->taglen, taglist, taglen)) 1094 break; 1095 result = result->parent; 1096 } 1097 return result; 1098 } 1099 1100 struct local_zone* 1101 local_zones_find(struct local_zones* zones, 1102 uint8_t* name, size_t len, int labs, uint16_t dclass) 1103 { 1104 struct local_zone key; 1105 key.node.key = &key; 1106 key.dclass = dclass; 1107 key.name = name; 1108 key.namelen = len; 1109 key.namelabs = labs; 1110 /* exact */ 1111 return (struct local_zone*)rbtree_search(&zones->ztree, &key); 1112 } 1113 1114 /** print all RRsets in local zone */ 1115 static void 1116 local_zone_out(struct local_zone* z) 1117 { 1118 struct local_data* d; 1119 struct local_rrset* p; 1120 RBTREE_FOR(d, struct local_data*, &z->data) { 1121 for(p = d->rrsets; p; p = p->next) { 1122 log_nametypeclass(0, "rrset", d->name, 1123 ntohs(p->rrset->rk.type), 1124 ntohs(p->rrset->rk.rrset_class)); 1125 } 1126 } 1127 } 1128 1129 void local_zones_print(struct local_zones* zones) 1130 { 1131 struct local_zone* z; 1132 lock_rw_rdlock(&zones->lock); 1133 log_info("number of auth zones %u", (unsigned)zones->ztree.count); 1134 RBTREE_FOR(z, struct local_zone*, &zones->ztree) { 1135 char buf[64]; 1136 lock_rw_rdlock(&z->lock); 1137 snprintf(buf, sizeof(buf), "%s zone", 1138 local_zone_type2str(z->type)); 1139 log_nametypeclass(0, buf, z->name, 0, z->dclass); 1140 local_zone_out(z); 1141 lock_rw_unlock(&z->lock); 1142 } 1143 lock_rw_unlock(&zones->lock); 1144 } 1145 1146 /** encode answer consisting of 1 rrset */ 1147 static int 1148 local_encode(struct query_info* qinfo, struct module_env* env, 1149 struct edns_data* edns, sldns_buffer* buf, struct regional* temp, 1150 struct ub_packed_rrset_key* rrset, int ansec, int rcode) 1151 { 1152 struct reply_info rep; 1153 uint16_t udpsize; 1154 /* make answer with time=0 for fixed TTL values */ 1155 memset(&rep, 0, sizeof(rep)); 1156 rep.flags = (uint16_t)((BIT_QR | BIT_AA | BIT_RA) | rcode); 1157 rep.qdcount = 1; 1158 if(ansec) 1159 rep.an_numrrsets = 1; 1160 else rep.ns_numrrsets = 1; 1161 rep.rrset_count = 1; 1162 rep.rrsets = &rrset; 1163 udpsize = edns->udp_size; 1164 edns->edns_version = EDNS_ADVERTISED_VERSION; 1165 edns->udp_size = EDNS_ADVERTISED_SIZE; 1166 edns->ext_rcode = 0; 1167 edns->bits &= EDNS_DO; 1168 if(!inplace_cb_reply_local_call(env, qinfo, NULL, &rep, rcode, edns, temp) 1169 || !reply_info_answer_encode(qinfo, &rep, 1170 *(uint16_t*)sldns_buffer_begin(buf), 1171 sldns_buffer_read_u16_at(buf, 2), 1172 buf, 0, 0, temp, udpsize, edns, 1173 (int)(edns->bits&EDNS_DO), 0)) 1174 error_encode(buf, (LDNS_RCODE_SERVFAIL|BIT_AA), qinfo, 1175 *(uint16_t*)sldns_buffer_begin(buf), 1176 sldns_buffer_read_u16_at(buf, 2), edns); 1177 return 1; 1178 } 1179 1180 /** encode local error answer */ 1181 static void 1182 local_error_encode(struct query_info* qinfo, struct module_env* env, 1183 struct edns_data* edns, sldns_buffer* buf, struct regional* temp, 1184 int rcode, int r) 1185 { 1186 edns->edns_version = EDNS_ADVERTISED_VERSION; 1187 edns->udp_size = EDNS_ADVERTISED_SIZE; 1188 edns->ext_rcode = 0; 1189 edns->bits &= EDNS_DO; 1190 1191 if(!inplace_cb_reply_local_call(env, qinfo, NULL, NULL, 1192 rcode, edns, temp)) 1193 edns->opt_list = NULL; 1194 error_encode(buf, r, qinfo, *(uint16_t*)sldns_buffer_begin(buf), 1195 sldns_buffer_read_u16_at(buf, 2), edns); 1196 } 1197 1198 /** find local data tag string match for the given type in the list */ 1199 int 1200 local_data_find_tag_datas(const struct query_info* qinfo, 1201 struct config_strlist* list, struct ub_packed_rrset_key* r, 1202 struct regional* temp) 1203 { 1204 struct config_strlist* p; 1205 char buf[65536]; 1206 uint8_t rr[LDNS_RR_BUF_SIZE]; 1207 size_t len; 1208 int res; 1209 struct packed_rrset_data* d; 1210 for(p=list; p; p=p->next) { 1211 uint16_t rdr_type; 1212 1213 len = sizeof(rr); 1214 /* does this element match the type? */ 1215 snprintf(buf, sizeof(buf), ". %s", p->str); 1216 res = sldns_str2wire_rr_buf(buf, rr, &len, NULL, 3600, 1217 NULL, 0, NULL, 0); 1218 if(res != 0) 1219 /* parse errors are already checked before, in 1220 * acllist check_data, skip this for robustness */ 1221 continue; 1222 if(len < 1 /* . */ + 8 /* typeclassttl*/ + 2 /*rdatalen*/) 1223 continue; 1224 rdr_type = sldns_wirerr_get_type(rr, len, 1); 1225 if(rdr_type != qinfo->qtype && rdr_type != LDNS_RR_TYPE_CNAME) 1226 continue; 1227 1228 /* do we have entries already? if not setup key */ 1229 if(r->rk.dname == NULL) { 1230 r->entry.key = r; 1231 r->rk.dname = qinfo->qname; 1232 r->rk.dname_len = qinfo->qname_len; 1233 r->rk.type = htons(rdr_type); 1234 r->rk.rrset_class = htons(qinfo->qclass); 1235 r->rk.flags = 0; 1236 d = (struct packed_rrset_data*)regional_alloc_zero( 1237 temp, sizeof(struct packed_rrset_data) 1238 + sizeof(size_t) + sizeof(uint8_t*) + 1239 sizeof(time_t)); 1240 if(!d) return 0; /* out of memory */ 1241 r->entry.data = d; 1242 d->ttl = sldns_wirerr_get_ttl(rr, len, 1); 1243 d->rr_len = (size_t*)((uint8_t*)d + 1244 sizeof(struct packed_rrset_data)); 1245 d->rr_data = (uint8_t**)&(d->rr_len[1]); 1246 d->rr_ttl = (time_t*)&(d->rr_data[1]); 1247 } 1248 d = (struct packed_rrset_data*)r->entry.data; 1249 /* add entry to the data */ 1250 if(d->count != 0) { 1251 size_t* oldlen = d->rr_len; 1252 uint8_t** olddata = d->rr_data; 1253 time_t* oldttl = d->rr_ttl; 1254 /* increase arrays for lookup */ 1255 /* this is of course slow for very many records, 1256 * but most redirects are expected with few records */ 1257 d->rr_len = (size_t*)regional_alloc_zero(temp, 1258 (d->count+1)*sizeof(size_t)); 1259 d->rr_data = (uint8_t**)regional_alloc_zero(temp, 1260 (d->count+1)*sizeof(uint8_t*)); 1261 d->rr_ttl = (time_t*)regional_alloc_zero(temp, 1262 (d->count+1)*sizeof(time_t)); 1263 if(!d->rr_len || !d->rr_data || !d->rr_ttl) 1264 return 0; /* out of memory */ 1265 /* first one was allocated after struct d, but new 1266 * ones get their own array increment alloc, so 1267 * copy old content */ 1268 memmove(d->rr_len, oldlen, d->count*sizeof(size_t)); 1269 memmove(d->rr_data, olddata, d->count*sizeof(uint8_t*)); 1270 memmove(d->rr_ttl, oldttl, d->count*sizeof(time_t)); 1271 } 1272 1273 d->rr_len[d->count] = sldns_wirerr_get_rdatalen(rr, len, 1)+2; 1274 d->rr_ttl[d->count] = sldns_wirerr_get_ttl(rr, len, 1); 1275 d->rr_data[d->count] = regional_alloc_init(temp, 1276 sldns_wirerr_get_rdatawl(rr, len, 1), 1277 d->rr_len[d->count]); 1278 if(!d->rr_data[d->count]) 1279 return 0; /* out of memory */ 1280 d->count++; 1281 } 1282 if(r->rk.dname) 1283 return 1; 1284 return 0; 1285 } 1286 1287 static int 1288 find_tag_datas(struct query_info* qinfo, struct config_strlist* list, 1289 struct ub_packed_rrset_key* r, struct regional* temp) 1290 { 1291 int result = local_data_find_tag_datas(qinfo, list, r, temp); 1292 1293 /* If we've found a non-exact alias type of local data, make a shallow 1294 * copy of the RRset and remember it in qinfo to complete the alias 1295 * chain later. */ 1296 if(result && qinfo->qtype != LDNS_RR_TYPE_CNAME && 1297 r->rk.type == htons(LDNS_RR_TYPE_CNAME)) { 1298 qinfo->local_alias = 1299 regional_alloc_zero(temp, sizeof(struct local_rrset)); 1300 if(!qinfo->local_alias) 1301 return 0; /* out of memory */ 1302 qinfo->local_alias->rrset = 1303 regional_alloc_init(temp, r, sizeof(*r)); 1304 if(!qinfo->local_alias->rrset) 1305 return 0; /* out of memory */ 1306 } 1307 return result; 1308 } 1309 1310 /** answer local data match */ 1311 static int 1312 local_data_answer(struct local_zone* z, struct module_env* env, 1313 struct query_info* qinfo, struct edns_data* edns, sldns_buffer* buf, 1314 struct regional* temp, int labs, struct local_data** ldp, 1315 enum localzone_type lz_type, int tag, struct config_strlist** tag_datas, 1316 size_t tag_datas_size, char** tagname, int num_tags) 1317 { 1318 struct local_data key; 1319 struct local_data* ld; 1320 struct local_rrset* lr; 1321 key.node.key = &key; 1322 key.name = qinfo->qname; 1323 key.namelen = qinfo->qname_len; 1324 key.namelabs = labs; 1325 if(lz_type == local_zone_redirect) { 1326 key.name = z->name; 1327 key.namelen = z->namelen; 1328 key.namelabs = z->namelabs; 1329 if(tag != -1 && (size_t)tag<tag_datas_size && tag_datas[tag]) { 1330 struct ub_packed_rrset_key r; 1331 memset(&r, 0, sizeof(r)); 1332 if(find_tag_datas(qinfo, tag_datas[tag], &r, temp)) { 1333 verbose(VERB_ALGO, "redirect with tag data [%d] %s", 1334 tag, (tag<num_tags?tagname[tag]:"null")); 1335 1336 /* If we found a matching alias, we should 1337 * use it as part of the answer, but we can't 1338 * encode it until we complete the alias 1339 * chain. */ 1340 if(qinfo->local_alias) 1341 return 1; 1342 return local_encode(qinfo, env, edns, buf, temp, 1343 &r, 1, LDNS_RCODE_NOERROR); 1344 } 1345 } 1346 } 1347 ld = (struct local_data*)rbtree_search(&z->data, &key.node); 1348 *ldp = ld; 1349 if(!ld) { 1350 return 0; 1351 } 1352 lr = local_data_find_type(ld, qinfo->qtype, 1); 1353 if(!lr) 1354 return 0; 1355 1356 /* Special case for alias matching. See local_data_answer(). */ 1357 if(lz_type == local_zone_redirect && 1358 qinfo->qtype != LDNS_RR_TYPE_CNAME && 1359 lr->rrset->rk.type == htons(LDNS_RR_TYPE_CNAME)) { 1360 qinfo->local_alias = 1361 regional_alloc_zero(temp, sizeof(struct local_rrset)); 1362 if(!qinfo->local_alias) 1363 return 0; /* out of memory */ 1364 qinfo->local_alias->rrset = 1365 regional_alloc_init(temp, lr->rrset, sizeof(*lr->rrset)); 1366 if(!qinfo->local_alias->rrset) 1367 return 0; /* out of memory */ 1368 qinfo->local_alias->rrset->rk.dname = qinfo->qname; 1369 qinfo->local_alias->rrset->rk.dname_len = qinfo->qname_len; 1370 return 1; 1371 } 1372 if(lz_type == local_zone_redirect) { 1373 /* convert rrset name to query name; like a wildcard */ 1374 struct ub_packed_rrset_key r = *lr->rrset; 1375 r.rk.dname = qinfo->qname; 1376 r.rk.dname_len = qinfo->qname_len; 1377 return local_encode(qinfo, env, edns, buf, temp, &r, 1, 1378 LDNS_RCODE_NOERROR); 1379 } 1380 return local_encode(qinfo, env, edns, buf, temp, lr->rrset, 1, 1381 LDNS_RCODE_NOERROR); 1382 } 1383 1384 /** 1385 * answer in case where no exact match is found 1386 * @param z: zone for query 1387 * @param env: module environment 1388 * @param qinfo: query 1389 * @param edns: edns from query 1390 * @param buf: buffer for answer. 1391 * @param temp: temp region for encoding 1392 * @param ld: local data, if NULL, no such name exists in localdata. 1393 * @param lz_type: type of the local zone 1394 * @return 1 if a reply is to be sent, 0 if not. 1395 */ 1396 static int 1397 lz_zone_answer(struct local_zone* z, struct module_env* env, 1398 struct query_info* qinfo, struct edns_data* edns, sldns_buffer* buf, 1399 struct regional* temp, struct local_data* ld, enum localzone_type lz_type) 1400 { 1401 if(lz_type == local_zone_deny || lz_type == local_zone_inform_deny) { 1402 /** no reply at all, signal caller by clearing buffer. */ 1403 sldns_buffer_clear(buf); 1404 sldns_buffer_flip(buf); 1405 return 1; 1406 } else if(lz_type == local_zone_refuse 1407 || lz_type == local_zone_always_refuse) { 1408 local_error_encode(qinfo, env, edns, buf, temp, 1409 LDNS_RCODE_REFUSED, (LDNS_RCODE_REFUSED|BIT_AA)); 1410 return 1; 1411 } else if(lz_type == local_zone_static || 1412 lz_type == local_zone_redirect || 1413 lz_type == local_zone_always_nxdomain) { 1414 /* for static, reply nodata or nxdomain 1415 * for redirect, reply nodata */ 1416 /* no additional section processing, 1417 * cname, dname or wildcard processing, 1418 * or using closest match for NSEC. 1419 * or using closest match for returning delegation downwards 1420 */ 1421 int rcode = (ld || lz_type == local_zone_redirect)? 1422 LDNS_RCODE_NOERROR:LDNS_RCODE_NXDOMAIN; 1423 if(z->soa) 1424 return local_encode(qinfo, env, edns, buf, temp, 1425 z->soa, 0, rcode); 1426 local_error_encode(qinfo, env, edns, buf, temp, rcode, 1427 (rcode|BIT_AA)); 1428 return 1; 1429 } else if(lz_type == local_zone_typetransparent 1430 || lz_type == local_zone_always_transparent) { 1431 /* no NODATA or NXDOMAINS for this zone type */ 1432 return 0; 1433 } 1434 /* else lz_type == local_zone_transparent */ 1435 1436 /* if the zone is transparent and the name exists, but the type 1437 * does not, then we should make this noerror/nodata */ 1438 if(ld && ld->rrsets) { 1439 int rcode = LDNS_RCODE_NOERROR; 1440 if(z->soa) 1441 return local_encode(qinfo, env, edns, buf, temp, 1442 z->soa, 0, rcode); 1443 local_error_encode(qinfo, env, edns, buf, temp, rcode, 1444 (rcode|BIT_AA)); 1445 return 1; 1446 } 1447 1448 /* stop here, and resolve further on */ 1449 return 0; 1450 } 1451 1452 /** print log information for an inform zone query */ 1453 static void 1454 lz_inform_print(struct local_zone* z, struct query_info* qinfo, 1455 struct comm_reply* repinfo) 1456 { 1457 char ip[128], txt[512]; 1458 char zname[LDNS_MAX_DOMAINLEN+1]; 1459 uint16_t port = ntohs(((struct sockaddr_in*)&repinfo->addr)->sin_port); 1460 dname_str(z->name, zname); 1461 addr_to_str(&repinfo->addr, repinfo->addrlen, ip, sizeof(ip)); 1462 snprintf(txt, sizeof(txt), "%s inform %s@%u", zname, ip, 1463 (unsigned)port); 1464 log_nametypeclass(0, txt, qinfo->qname, qinfo->qtype, qinfo->qclass); 1465 } 1466 1467 static enum localzone_type 1468 lz_type(uint8_t *taglist, size_t taglen, uint8_t *taglist2, size_t taglen2, 1469 uint8_t *tagactions, size_t tagactionssize, enum localzone_type lzt, 1470 struct comm_reply* repinfo, struct rbtree_type* override_tree, 1471 int* tag, char** tagname, int num_tags) 1472 { 1473 struct local_zone_override* lzo; 1474 if(repinfo && override_tree) { 1475 lzo = (struct local_zone_override*)addr_tree_lookup( 1476 override_tree, &repinfo->addr, repinfo->addrlen); 1477 if(lzo && lzo->type) { 1478 verbose(VERB_ALGO, "local zone override to type %s", 1479 local_zone_type2str(lzo->type)); 1480 return lzo->type; 1481 } 1482 } 1483 if(!taglist || !taglist2) 1484 return lzt; 1485 return local_data_find_tag_action(taglist, taglen, taglist2, taglen2, 1486 tagactions, tagactionssize, lzt, tag, tagname, num_tags); 1487 } 1488 1489 enum localzone_type 1490 local_data_find_tag_action(const uint8_t* taglist, size_t taglen, 1491 const uint8_t* taglist2, size_t taglen2, const uint8_t* tagactions, 1492 size_t tagactionssize, enum localzone_type lzt, int* tag, 1493 char* const* tagname, int num_tags) 1494 { 1495 size_t i, j; 1496 uint8_t tagmatch; 1497 1498 for(i=0; i<taglen && i<taglen2; i++) { 1499 tagmatch = (taglist[i] & taglist2[i]); 1500 for(j=0; j<8 && tagmatch>0; j++) { 1501 if((tagmatch & 0x1)) { 1502 *tag = (int)(i*8+j); 1503 verbose(VERB_ALGO, "matched tag [%d] %s", 1504 *tag, (*tag<num_tags?tagname[*tag]:"null")); 1505 /* does this tag have a tag action? */ 1506 if(i*8+j < tagactionssize && tagactions 1507 && tagactions[i*8+j] != 0) { 1508 verbose(VERB_ALGO, "tag action [%d] %s to type %s", 1509 *tag, (*tag<num_tags?tagname[*tag]:"null"), 1510 local_zone_type2str( 1511 (enum localzone_type) 1512 tagactions[i*8+j])); 1513 return (enum localzone_type)tagactions[i*8+j]; 1514 } 1515 return lzt; 1516 } 1517 tagmatch >>= 1; 1518 } 1519 } 1520 return lzt; 1521 } 1522 1523 int 1524 local_zones_answer(struct local_zones* zones, struct module_env* env, 1525 struct query_info* qinfo, struct edns_data* edns, sldns_buffer* buf, 1526 struct regional* temp, struct comm_reply* repinfo, uint8_t* taglist, 1527 size_t taglen, uint8_t* tagactions, size_t tagactionssize, 1528 struct config_strlist** tag_datas, size_t tag_datas_size, 1529 char** tagname, int num_tags, struct view* view) 1530 { 1531 /* see if query is covered by a zone, 1532 * if so: - try to match (exact) local data 1533 * - look at zone type for negative response. */ 1534 int labs = dname_count_labels(qinfo->qname); 1535 struct local_data* ld = NULL; 1536 struct local_zone* z = NULL; 1537 enum localzone_type lzt = local_zone_transparent; 1538 int r, tag = -1; 1539 1540 if(view) { 1541 lock_rw_rdlock(&view->lock); 1542 if(view->local_zones && 1543 (z = local_zones_lookup(view->local_zones, 1544 qinfo->qname, qinfo->qname_len, labs, 1545 qinfo->qclass, qinfo->qtype))) { 1546 if(z->type != local_zone_noview) 1547 verbose(VERB_ALGO, 1548 "using localzone from view: %s", 1549 view->name); 1550 lock_rw_rdlock(&z->lock); 1551 lzt = z->type; 1552 } 1553 if(lzt == local_zone_noview) { 1554 lock_rw_unlock(&z->lock); 1555 z = NULL; 1556 } 1557 if(view->local_zones && !z && !view->isfirst){ 1558 lock_rw_unlock(&view->lock); 1559 return 0; 1560 } 1561 lock_rw_unlock(&view->lock); 1562 } 1563 if(!z) { 1564 /* try global local_zones tree */ 1565 lock_rw_rdlock(&zones->lock); 1566 if(!(z = local_zones_tags_lookup(zones, qinfo->qname, 1567 qinfo->qname_len, labs, qinfo->qclass, qinfo->qtype, 1568 taglist, taglen, 0))) { 1569 lock_rw_unlock(&zones->lock); 1570 return 0; 1571 } 1572 lock_rw_rdlock(&z->lock); 1573 1574 lzt = lz_type(taglist, taglen, z->taglist, z->taglen, 1575 tagactions, tagactionssize, z->type, repinfo, 1576 z->override_tree, &tag, tagname, num_tags); 1577 lock_rw_unlock(&zones->lock); 1578 } 1579 if((lzt == local_zone_inform || lzt == local_zone_inform_deny) 1580 && repinfo) 1581 lz_inform_print(z, qinfo, repinfo); 1582 1583 if(lzt != local_zone_always_refuse 1584 && lzt != local_zone_always_transparent 1585 && lzt != local_zone_always_nxdomain 1586 && local_data_answer(z, env, qinfo, edns, buf, temp, labs, &ld, lzt, 1587 tag, tag_datas, tag_datas_size, tagname, num_tags)) { 1588 lock_rw_unlock(&z->lock); 1589 /* We should tell the caller that encode is deferred if we found 1590 * a local alias. */ 1591 return !qinfo->local_alias; 1592 } 1593 r = lz_zone_answer(z, env, qinfo, edns, buf, temp, ld, lzt); 1594 lock_rw_unlock(&z->lock); 1595 return r && !qinfo->local_alias; /* see above */ 1596 } 1597 1598 const char* local_zone_type2str(enum localzone_type t) 1599 { 1600 switch(t) { 1601 case local_zone_unset: return "unset"; 1602 case local_zone_deny: return "deny"; 1603 case local_zone_refuse: return "refuse"; 1604 case local_zone_redirect: return "redirect"; 1605 case local_zone_transparent: return "transparent"; 1606 case local_zone_typetransparent: return "typetransparent"; 1607 case local_zone_static: return "static"; 1608 case local_zone_nodefault: return "nodefault"; 1609 case local_zone_inform: return "inform"; 1610 case local_zone_inform_deny: return "inform_deny"; 1611 case local_zone_always_transparent: return "always_transparent"; 1612 case local_zone_always_refuse: return "always_refuse"; 1613 case local_zone_always_nxdomain: return "always_nxdomain"; 1614 case local_zone_noview: return "noview"; 1615 } 1616 return "badtyped"; 1617 } 1618 1619 int local_zone_str2type(const char* type, enum localzone_type* t) 1620 { 1621 if(strcmp(type, "deny") == 0) 1622 *t = local_zone_deny; 1623 else if(strcmp(type, "refuse") == 0) 1624 *t = local_zone_refuse; 1625 else if(strcmp(type, "static") == 0) 1626 *t = local_zone_static; 1627 else if(strcmp(type, "transparent") == 0) 1628 *t = local_zone_transparent; 1629 else if(strcmp(type, "typetransparent") == 0) 1630 *t = local_zone_typetransparent; 1631 else if(strcmp(type, "redirect") == 0) 1632 *t = local_zone_redirect; 1633 else if(strcmp(type, "inform") == 0) 1634 *t = local_zone_inform; 1635 else if(strcmp(type, "inform_deny") == 0) 1636 *t = local_zone_inform_deny; 1637 else if(strcmp(type, "always_transparent") == 0) 1638 *t = local_zone_always_transparent; 1639 else if(strcmp(type, "always_refuse") == 0) 1640 *t = local_zone_always_refuse; 1641 else if(strcmp(type, "always_nxdomain") == 0) 1642 *t = local_zone_always_nxdomain; 1643 else if(strcmp(type, "noview") == 0) 1644 *t = local_zone_noview; 1645 else if(strcmp(type, "nodefault") == 0) 1646 *t = local_zone_nodefault; 1647 else return 0; 1648 return 1; 1649 } 1650 1651 /** iterate over the kiddies of the given name and set their parent ptr */ 1652 static void 1653 set_kiddo_parents(struct local_zone* z, struct local_zone* match, 1654 struct local_zone* newp) 1655 { 1656 /* both zones and z are locked already */ 1657 /* in the sorted rbtree, the kiddies of z are located after z */ 1658 /* z must be present in the tree */ 1659 struct local_zone* p = z; 1660 p = (struct local_zone*)rbtree_next(&p->node); 1661 while(p!=(struct local_zone*)RBTREE_NULL && 1662 p->dclass == z->dclass && dname_strict_subdomain(p->name, 1663 p->namelabs, z->name, z->namelabs)) { 1664 /* update parent ptr */ 1665 /* only when matches with existing parent pointer, so that 1666 * deeper child structures are not touched, i.e. 1667 * update of x, and a.x, b.x, f.b.x, g.b.x, c.x, y 1668 * gets to update a.x, b.x and c.x */ 1669 lock_rw_wrlock(&p->lock); 1670 if(p->parent == match) 1671 p->parent = newp; 1672 lock_rw_unlock(&p->lock); 1673 p = (struct local_zone*)rbtree_next(&p->node); 1674 } 1675 } 1676 1677 struct local_zone* local_zones_add_zone(struct local_zones* zones, 1678 uint8_t* name, size_t len, int labs, uint16_t dclass, 1679 enum localzone_type tp) 1680 { 1681 /* create */ 1682 struct local_zone* z = local_zone_create(name, len, labs, tp, dclass); 1683 if(!z) { 1684 free(name); 1685 return NULL; 1686 } 1687 lock_rw_wrlock(&z->lock); 1688 1689 /* find the closest parent */ 1690 z->parent = local_zones_find(zones, name, len, labs, dclass); 1691 1692 /* insert into the tree */ 1693 if(!rbtree_insert(&zones->ztree, &z->node)) { 1694 /* duplicate entry! */ 1695 lock_rw_unlock(&z->lock); 1696 local_zone_delete(z); 1697 log_err("internal: duplicate entry in local_zones_add_zone"); 1698 return NULL; 1699 } 1700 1701 /* set parent pointers right */ 1702 set_kiddo_parents(z, z->parent, z); 1703 1704 lock_rw_unlock(&z->lock); 1705 return z; 1706 } 1707 1708 void local_zones_del_zone(struct local_zones* zones, struct local_zone* z) 1709 { 1710 /* fix up parents in tree */ 1711 lock_rw_wrlock(&z->lock); 1712 set_kiddo_parents(z, z, z->parent); 1713 1714 /* remove from tree */ 1715 (void)rbtree_delete(&zones->ztree, z); 1716 1717 /* delete the zone */ 1718 lock_rw_unlock(&z->lock); 1719 local_zone_delete(z); 1720 } 1721 1722 int 1723 local_zones_add_RR(struct local_zones* zones, const char* rr) 1724 { 1725 uint8_t* rr_name; 1726 uint16_t rr_class, rr_type; 1727 size_t len; 1728 int labs; 1729 struct local_zone* z; 1730 int r; 1731 if(!get_rr_nameclass(rr, &rr_name, &rr_class, &rr_type)) { 1732 return 0; 1733 } 1734 labs = dname_count_size_labels(rr_name, &len); 1735 /* could first try readlock then get writelock if zone does not exist, 1736 * but we do not add enough RRs (from multiple threads) to optimize */ 1737 lock_rw_wrlock(&zones->lock); 1738 z = local_zones_lookup(zones, rr_name, len, labs, rr_class, rr_type); 1739 if(!z) { 1740 z = local_zones_add_zone(zones, rr_name, len, labs, rr_class, 1741 local_zone_transparent); 1742 if(!z) { 1743 lock_rw_unlock(&zones->lock); 1744 return 0; 1745 } 1746 } else { 1747 free(rr_name); 1748 } 1749 lock_rw_wrlock(&z->lock); 1750 lock_rw_unlock(&zones->lock); 1751 r = lz_enter_rr_into_zone(z, rr); 1752 lock_rw_unlock(&z->lock); 1753 return r; 1754 } 1755 1756 /** returns true if the node is terminal so no deeper domain names exist */ 1757 static int 1758 is_terminal(struct local_data* d) 1759 { 1760 /* for empty nonterminals, the deeper domain names are sorted 1761 * right after them, so simply check the next name in the tree 1762 */ 1763 struct local_data* n = (struct local_data*)rbtree_next(&d->node); 1764 if(n == (struct local_data*)RBTREE_NULL) 1765 return 1; /* last in tree, no deeper node */ 1766 if(dname_strict_subdomain(n->name, n->namelabs, d->name, d->namelabs)) 1767 return 0; /* there is a deeper node */ 1768 return 1; 1769 } 1770 1771 /** delete empty terminals from tree when final data is deleted */ 1772 static void 1773 del_empty_term(struct local_zone* z, struct local_data* d, 1774 uint8_t* name, size_t len, int labs) 1775 { 1776 while(d && d->rrsets == NULL && is_terminal(d)) { 1777 /* is this empty nonterminal? delete */ 1778 /* note, no memory recycling in zone region */ 1779 (void)rbtree_delete(&z->data, d); 1780 1781 /* go up and to the next label */ 1782 if(dname_is_root(name)) 1783 return; 1784 dname_remove_label(&name, &len); 1785 labs--; 1786 d = lz_find_node(z, name, len, labs); 1787 } 1788 } 1789 1790 /** find and remove type from list in domain struct */ 1791 static void 1792 del_local_rrset(struct local_data* d, uint16_t dtype) 1793 { 1794 struct local_rrset* prev=NULL, *p=d->rrsets; 1795 while(p && ntohs(p->rrset->rk.type) != dtype) { 1796 prev = p; 1797 p = p->next; 1798 } 1799 if(!p) 1800 return; /* rrset type not found */ 1801 /* unlink it */ 1802 if(prev) prev->next = p->next; 1803 else d->rrsets = p->next; 1804 /* no memory recycling for zone deletions ... */ 1805 } 1806 1807 void local_zones_del_data(struct local_zones* zones, 1808 uint8_t* name, size_t len, int labs, uint16_t dclass) 1809 { 1810 /* find zone */ 1811 struct local_zone* z; 1812 struct local_data* d; 1813 1814 /* remove DS */ 1815 lock_rw_rdlock(&zones->lock); 1816 z = local_zones_lookup(zones, name, len, labs, dclass, LDNS_RR_TYPE_DS); 1817 if(z) { 1818 lock_rw_wrlock(&z->lock); 1819 d = lz_find_node(z, name, len, labs); 1820 if(d) { 1821 del_local_rrset(d, LDNS_RR_TYPE_DS); 1822 del_empty_term(z, d, name, len, labs); 1823 } 1824 lock_rw_unlock(&z->lock); 1825 } 1826 lock_rw_unlock(&zones->lock); 1827 1828 /* remove other types */ 1829 lock_rw_rdlock(&zones->lock); 1830 z = local_zones_lookup(zones, name, len, labs, dclass, 0); 1831 if(!z) { 1832 /* no such zone, we're done */ 1833 lock_rw_unlock(&zones->lock); 1834 return; 1835 } 1836 lock_rw_wrlock(&z->lock); 1837 lock_rw_unlock(&zones->lock); 1838 1839 /* find the domain */ 1840 d = lz_find_node(z, name, len, labs); 1841 if(d) { 1842 /* no memory recycling for zone deletions ... */ 1843 d->rrsets = NULL; 1844 /* did we delete the soa record ? */ 1845 if(query_dname_compare(d->name, z->name) == 0) 1846 z->soa = NULL; 1847 1848 /* cleanup the empty nonterminals for this name */ 1849 del_empty_term(z, d, name, len, labs); 1850 } 1851 1852 lock_rw_unlock(&z->lock); 1853 } 1854