From: Wouter Wijngaards Date: Fri, 11 Jun 2010 14:09:56 +0000 (+0000) Subject: - When retry to parent the retrycount is not wiped, so failed X-Git-Tag: release-1.4.5~1 X-Git-Url: http://git.ipfire.org/cgi-bin/gitweb.cgi?a=commitdiff_plain;h=1f0f85b59a7979aab5bfd95b522492ebd38a77ac;p=thirdparty%2Funbound.git - When retry to parent the retrycount is not wiped, so failed nameservers are not tried again. - iana portlist updated. git-svn-id: file:///svn/unbound/trunk@2145 be551aaa-1e26-0410-a405-d3ace91eadb9 --- diff --git a/doc/Changelog b/doc/Changelog index e29eff2f4..90c8df01d 100644 --- a/doc/Changelog +++ b/doc/Changelog @@ -1,3 +1,8 @@ +11 June 2010: Wouter + - When retry to parent the retrycount is not wiped, so failed + nameservers are not tried again. + - iana portlist updated. + 10 June 2010: Wouter - Fix bug where a long loop could be entered, now cycle detection has a loop-counter and maximum search amount. diff --git a/iterator/iter_utils.c b/iterator/iter_utils.c index 7b946b88e..d33db3f53 100644 --- a/iterator/iter_utils.c +++ b/iterator/iter_utils.c @@ -933,3 +933,31 @@ void iter_dec_attempts(struct delegpt* dp, int d) else a->attempts = 0; } } + +void iter_merge_retry_counts(struct delegpt* dp, struct delegpt* old) +{ + struct delegpt_addr* a, *o, *prev; + for(a=dp->target_list; a; a = a->next_target) { + o = delegpt_find_addr(old, &a->addr, a->addrlen); + if(o) { + log_addr(VERB_ALGO, "copy attempt count previous dp", + &a->addr, a->addrlen); + a->attempts = o->attempts; + } + } + prev = NULL; + a = dp->result_list; + while(a) { + if(a->attempts >= OUTBOUND_MSG_RETRY) { + /* remove from result list */ + if(prev) + prev->next_result = a->next_result; + else dp->result_list = a->next_result; + /* prev stays the same */ + a = a->next_result; + continue; + } + prev = a; + a = a->next_result; + } +} diff --git a/iterator/iter_utils.h b/iterator/iter_utils.h index e8c5d04f2..58ba5a920 100644 --- a/iterator/iter_utils.h +++ b/iterator/iter_utils.h @@ -298,4 +298,12 @@ void iter_scrub_ds(struct dns_msg* msg, struct ub_packed_rrset_key* ns, */ void iter_dec_attempts(struct delegpt* dp, int d); +/** + * Add retry counts from older delegpt to newer delegpt. + * Does not waste time on timeout'd (or other failing) addresses. + * @param dp: new delegationpoint. + * @param old: old delegationpoint. + */ +void iter_merge_retry_counts(struct delegpt* dp, struct delegpt* old); + #endif /* ITERATOR_ITER_UTILS_H */ diff --git a/iterator/iterator.c b/iterator/iterator.c index f28891a9e..10c078803 100644 --- a/iterator/iterator.c +++ b/iterator/iterator.c @@ -1807,6 +1807,7 @@ processQueryResponse(struct module_qstate* qstate, struct iter_qstate* iq, qstate->region); return final_state(iq); } else if(type == RESPONSE_TYPE_REFERRAL) { + struct delegpt* old_dp = iq->dp; /* REFERRAL type responses get a reset of the * delegation point, and back to the QUERYTARGETS_STATE. */ verbose(VERB_DETAIL, "query response was REFERRAL"); @@ -1863,6 +1864,9 @@ processQueryResponse(struct module_qstate* qstate, struct iter_qstate* iq, if(!cache_fill_missing(qstate->env, iq->qchase.qclass, qstate->region, iq->dp)) return error_response(qstate, id, LDNS_RCODE_SERVFAIL); + if(iq->store_parent_NS && query_dname_compare(iq->dp->name, + old_dp->name) == 0) + iter_merge_retry_counts(iq->dp, old_dp); delegpt_log(VERB_ALGO, iq->dp); /* Count this as a referral. */ iq->referral_count++; diff --git a/util/iana_ports.inc b/util/iana_ports.inc index f7b9e847d..6ca787996 100644 --- a/util/iana_ports.inc +++ b/util/iana_ports.inc @@ -4256,6 +4256,7 @@ 5679, 5680, 5681, +5682, 5688, 5689, 5713,