From: Wouter Wijngaards Date: Thu, 18 Feb 2010 09:47:08 +0000 (+0000) Subject: A little more strict DS scrubbing. X-Git-Tag: release-1.4.2~25 X-Git-Url: http://git.ipfire.org/cgi-bin/gitweb.cgi?a=commitdiff_plain;h=38c6664caf710fd603efc739830d3a1be0f14514;p=thirdparty%2Funbound.git A little more strict DS scrubbing. git-svn-id: file:///svn/unbound/trunk@1986 be551aaa-1e26-0410-a405-d3ace91eadb9 --- diff --git a/doc/Changelog b/doc/Changelog index 5e6632055..bb11365f1 100644 --- a/doc/Changelog +++ b/doc/Changelog @@ -1,3 +1,6 @@ +18 February 2010: Wouter + - A little more strict DS scrubbing. + 17 February 2010: Wouter - Disregard DNSKEY from authority section for chain of trust. DS records that are irrelevant to a referral scrubbed. Anti-poison. diff --git a/iterator/iter_utils.c b/iterator/iter_utils.c index 2416f3abb..396814edf 100644 --- a/iterator/iter_utils.c +++ b/iterator/iter_utils.c @@ -757,20 +757,22 @@ iter_get_next_root(struct iter_hints* hints, struct iter_forwards* fwd, } void -iter_scrub_ds(struct ub_packed_rrset_key* ns, struct dns_msg* msg) +iter_scrub_ds(struct dns_msg* msg, struct ub_packed_rrset_key* ns, uint8_t* z) { /* Only the DS record for the delegation itself is expected. * We allow DS for everything between the bailiwick and the * zonecut, thus DS records must be at or above the zonecut. + * And the DS records must be below the server authority zone. * The answer section is already scrubbed. */ size_t i = msg->rep->an_numrrsets; while(i < (msg->rep->an_numrrsets + msg->rep->ns_numrrsets)) { struct ub_packed_rrset_key* s = msg->rep->rrsets[i]; if(ntohs(s->rk.type) == LDNS_RR_TYPE_DS && - !dname_subdomain_c(ns->rk.dname, s->rk.dname)) { - log_nametypeclass(VERB_ALGO, "removing irrelevant DS " - "from referral", s->rk.dname, - ntohs(s->rk.type), ntohs(s->rk.rrset_class)); + (!ns || !dname_subdomain_c(ns->rk.dname, s->rk.dname) + || query_dname_compare(z, s->rk.dname) == 0)) { + log_nametypeclass(VERB_ALGO, "removing irrelevant DS", + s->rk.dname, ntohs(s->rk.type), + ntohs(s->rk.rrset_class)); memmove(msg->rep->rrsets+i, msg->rep->rrsets+i+1, sizeof(struct ub_packed_rrset_key*) * (msg->rep->rrset_count-i-1)); diff --git a/iterator/iter_utils.h b/iterator/iter_utils.h index 85d9c1a21..2a1a724c2 100644 --- a/iterator/iter_utils.h +++ b/iterator/iter_utils.h @@ -248,9 +248,12 @@ int iter_get_next_root(struct iter_hints* hints, struct iter_forwards* fwd, /** * Remove DS records that are inappropriate before they are cached. - * @param ns: RRSET that is the NS record for the referral. * @param msg: the response to scrub. + * @param ns: RRSET that is the NS record for the referral. + * if NULL, then all DS records are removed from the authority section. + * @param z: zone name that the response is from. */ -void iter_scrub_ds(struct ub_packed_rrset_key* ns, struct dns_msg* msg); +void iter_scrub_ds(struct dns_msg* msg, struct ub_packed_rrset_key* ns, + uint8_t* z); #endif /* ITERATOR_ITER_UTILS_H */ diff --git a/iterator/iterator.c b/iterator/iterator.c index cc66c4895..4a82d6437 100644 --- a/iterator/iterator.c +++ b/iterator/iterator.c @@ -1613,8 +1613,8 @@ processQueryResponse(struct module_qstate* qstate, struct iter_qstate* iq, verbose(VERB_ALGO, "bad referral, throwaway"); type = RESPONSE_TYPE_THROWAWAY; } else - iter_scrub_ds(ns, iq->response); - } + iter_scrub_ds(iq->response, ns, iq->dp->name); + } else iter_scrub_ds(iq->response, NULL, NULL); /* handle each of the type cases */ if(type == RESPONSE_TYPE_ANSWER) {