From: Wouter Wijngaards Date: Fri, 26 Jun 2015 07:27:32 +0000 (+0000) Subject: - Fix #677 Fix DNAME responses from cache that failed internal chain X-Git-Tag: release-1.5.4~8 X-Git-Url: http://git.ipfire.org/cgi-bin/gitweb.cgi?a=commitdiff_plain;h=cb907820873d312622a11a993ceeb6ff41d2ac40;p=thirdparty%2Funbound.git - Fix #677 Fix DNAME responses from cache that failed internal chain test. git-svn-id: file:///svn/unbound/trunk@3435 be551aaa-1e26-0410-a405-d3ace91eadb9 --- diff --git a/daemon/worker.c b/daemon/worker.c index f4e87289a..79aec4d3a 100644 --- a/daemon/worker.c +++ b/daemon/worker.c @@ -568,7 +568,7 @@ answer_from_cache(struct worker* worker, struct query_info* qinfo, if(rep->an_numrrsets > 0 && (rep->rrsets[0]->rk.type == htons(LDNS_RR_TYPE_CNAME) || rep->rrsets[0]->rk.type == htons(LDNS_RR_TYPE_DNAME))) { - if(!reply_check_cname_chain(rep)) { + if(!reply_check_cname_chain(qinfo, rep)) { /* cname chain invalid, redo iterator steps */ verbose(VERB_ALGO, "Cache reply: cname chain broken"); bail_out: diff --git a/doc/Changelog b/doc/Changelog index a9c50afbe..86c3b82fc 100644 --- a/doc/Changelog +++ b/doc/Changelog @@ -1,3 +1,7 @@ +26 June 2015: Wouter + - Fix #677 Fix DNAME responses from cache that failed internal chain + test. + 22 June 2015: Wouter - Fix #677 Fix CNAME corresponding to a DNAME was checked incorrectly and was therefore always synthesized (thanks to Valentin Dietrich). diff --git a/services/cache/dns.c b/services/cache/dns.c index 53127ce59..ba81afde4 100644 --- a/services/cache/dns.c +++ b/services/cache/dns.c @@ -505,7 +505,7 @@ tomsg(struct module_env* env, struct query_info* q, struct reply_info* r, return NULL; if(r->an_numrrsets > 0 && (r->rrsets[0]->rk.type == htons( LDNS_RR_TYPE_CNAME) || r->rrsets[0]->rk.type == htons( - LDNS_RR_TYPE_DNAME)) && !reply_check_cname_chain(r)) { + LDNS_RR_TYPE_DNAME)) && !reply_check_cname_chain(q, r)) { /* cname chain is now invalid, reconstruct msg */ rrset_array_unlock(r->ref, r->rrset_count); return NULL; diff --git a/testdata/val_dnametopos.rpl b/testdata/val_dnametopos.rpl index 6264a6d0e..a78d34ae7 100644 --- a/testdata/val_dnametopos.rpl +++ b/testdata/val_dnametopos.rpl @@ -231,4 +231,28 @@ SECTION AUTHORITY SECTION ADDITIONAL ENTRY_END +; Check cache response for DNAME +STEP 20 QUERY +ENTRY_BEGIN +REPLY RD DO +SECTION QUESTION +www.example.com. IN A +ENTRY_END + +STEP 30 CHECK_ANSWER +ENTRY_BEGIN +MATCH all +REPLY QR RD RA AD DO NOERROR +SECTION QUESTION +www.example.com. IN A +SECTION ANSWER +example.com. 3600 IN DNAME example.net. +example.com. 3600 IN RRSIG DNAME 3 2 3600 20070926134150 20070829134150 2854 example.com. MCwCFH1xw24Hswia3g10AVL1yFUHUPdFAhQDrA+qZJwqXRPg2C1oiNPk9fosGg== ;{id = 2854} +www.example.com. 0 IN CNAME www.example.net. +www.example.net. 3600 IN A 11.12.13.14 +www.example.net. 3600 IN RRSIG A 5 3 3600 20070926134150 20070829134150 30899 example.net. CPxF5hK9Kg5eT7W6LgZwr0ePYEm9HMcSY4vvqCS6gDWB4X9jvXLCfBkCLhsNybPBpGWlsLi5wM6MTdJXuPpsRA== ;{id = 30899} +SECTION AUTHORITY +SECTION ADDITIONAL +ENTRY_END + SCENARIO_END diff --git a/util/data/msgreply.c b/util/data/msgreply.c index b1d3df639..06593ffe1 100644 --- a/util/data/msgreply.c +++ b/util/data/msgreply.c @@ -822,13 +822,13 @@ log_query_info(enum verbosity_value v, const char* str, } int -reply_check_cname_chain(struct reply_info* rep) +reply_check_cname_chain(struct query_info* qinfo, struct reply_info* rep) { /* check only answer section rrs for matching cname chain. * the cache may return changed rdata, but owner names are untouched.*/ size_t i; - uint8_t* sname = rep->rrsets[0]->rk.dname; - size_t snamelen = rep->rrsets[0]->rk.dname_len; + uint8_t* sname = qinfo->qname; + size_t snamelen = qinfo->qname_len; for(i=0; ian_numrrsets; i++) { uint16_t t = ntohs(rep->rrsets[i]->rk.type); if(t == LDNS_RR_TYPE_DNAME) diff --git a/util/data/msgreply.h b/util/data/msgreply.h index e8d6d762e..708897950 100644 --- a/util/data/msgreply.h +++ b/util/data/msgreply.h @@ -359,10 +359,11 @@ uint8_t* reply_find_final_cname_target(struct query_info* qinfo, /** * Check if cname chain in cached reply is still valid. + * @param qinfo: query info with query name. * @param rep: reply to check. * @return: true if valid, false if invalid. */ -int reply_check_cname_chain(struct reply_info* rep); +int reply_check_cname_chain(struct query_info* qinfo, struct reply_info* rep); /** * Check security status of all RRs in the message.