]> git.ipfire.org Git - thirdparty/unbound.git/commitdiff
- max sent count. EDNS1480 only for rtt < 5000. No promiscuous
authorWouter Wijngaards <wouter@nlnetlabs.nl>
Fri, 16 Sep 2011 14:11:12 +0000 (14:11 +0000)
committerWouter Wijngaards <wouter@nlnetlabs.nl>
Fri, 16 Sep 2011 14:11:12 +0000 (14:11 +0000)
fetch if sentcount > 3, stop query if sentcount > 16.  Count is
reset when referral or CNAME happens.  This makes unbound better
at managing large NS sets, they are explored when there is continued
interest (in the form of queries).

git-svn-id: file:///svn/unbound/trunk@2499 be551aaa-1e26-0410-a405-d3ace91eadb9

doc/Changelog
iterator/iterator.c
iterator/iterator.h
services/outside_network.c

index f1b38fbc0fdaf13c31371e1cc8e7ef11ec1df1b3..26394c2377f4eeb37858e85ceff8ad4f15d6d746 100644 (file)
@@ -4,6 +4,11 @@
        - iana portlist updated.
        - fix EDNS1480 change memleak and TCP fallback.
        - fix various compiler warnings (reported by Paul Wouters).
+       - max sent count.  EDNS1480 only for rtt < 5000.  No promiscuous
+         fetch if sentcount > 3, stop query if sentcount > 16.  Count is
+         reset when referral or CNAME happens.  This makes unbound better
+         at managing large NS sets, they are explored when there is continued
+         interest (in the form of queries).
 
 15 September 2011: Wouter
        - release 1.4.13.
index 71682b23446e1d8faa15844418e92cb0fafd86de..cf35d0f324a5b2c7338ff4ef866c20abf98d5745 100644 (file)
@@ -117,6 +117,7 @@ iter_new(struct module_qstate* qstate, int id)
        iq->num_current_queries = 0;
        iq->query_restart_count = 0;
        iq->referral_count = 0;
+       iq->sent_count = 0;
        iq->wait_priming_stub = 0;
        iq->refetch_glue = 0;
        iq->dnssec_expected = 0;
@@ -1537,8 +1538,8 @@ processQueryTargets(struct module_qstate* qstate, struct iter_qstate* iq,
 
        log_query_info(VERB_QUERY, "processQueryTargets:", &qstate->qinfo);
        verbose(VERB_ALGO, "processQueryTargets: targetqueries %d, "
-               "currentqueries %d", iq->num_target_queries, 
-               iq->num_current_queries);
+               "currentqueries %d sentcount %d", iq->num_target_queries, 
+               iq->num_current_queries, iq->sent_count);
 
        /* Make sure that we haven't run away */
        /* FIXME: is this check even necessary? */
@@ -1547,6 +1548,11 @@ processQueryTargets(struct module_qstate* qstate, struct iter_qstate* iq,
                        "number of referrrals with %d", iq->referral_count);
                return error_response(qstate, id, LDNS_RCODE_SERVFAIL);
        }
+       if(iq->sent_count > MAX_SENT_COUNT) {
+               verbose(VERB_QUERY, "request has exceeded the maximum "
+                       "number of sends with %d", iq->sent_count);
+               return error_response(qstate, id, LDNS_RCODE_SERVFAIL);
+       }
        
        /* Make sure we have a delegation point, otherwise priming failed
         * or another failure occurred */
@@ -1573,7 +1579,8 @@ processQueryTargets(struct module_qstate* qstate, struct iter_qstate* iq,
        /* < not <=, because although the array is large enough for <=, the
         * generated query will immediately be discarded due to depth and
         * that servfail is cached, which is not good as opportunism goes. */
-       if(iq->depth < ie->max_dependency_depth) {
+       if(iq->depth < ie->max_dependency_depth
+               && iq->sent_count < TARGET_FETCH_STOP) {
                tf_policy = ie->target_fetch_policy[iq->depth];
        }
 
@@ -1596,7 +1603,8 @@ processQueryTargets(struct module_qstate* qstate, struct iter_qstate* iq,
                /* the current caps_server is the number of fallbacks sent.
                 * the original query is one that matched too, so we have
                 * caps_server+1 number of matching queries now */
-               if(iq->caps_server+1 >= naddr*3) {
+               if(iq->caps_server+1 >= naddr*3 ||
+                       iq->caps_server+1 >= MAX_SENT_COUNT) {
                        /* we're done, process the response */
                        verbose(VERB_ALGO, "0x20 fallback had %d responses "
                                "match for %d wanted, done.", 
@@ -1720,6 +1728,7 @@ processQueryTargets(struct module_qstate* qstate, struct iter_qstate* iq,
        }
        outbound_list_insert(&iq->outlist, outq);
        iq->num_current_queries++;
+       iq->sent_count++;
        qstate->ext_state[id] = module_wait_reply;
 
        return 0;
@@ -1896,6 +1905,7 @@ processQueryResponse(struct module_qstate* qstate, struct iter_qstate* iq,
                delegpt_log(VERB_ALGO, iq->dp);
                /* Count this as a referral. */
                iq->referral_count++;
+               iq->sent_count = 0;
                /* see if the next dp is a trust anchor, or a DS was sent
                 * along, indicating dnssec is expected for next zone */
                iq->dnssec_expected = iter_indicates_dnssec(qstate->env, 
@@ -1953,6 +1963,7 @@ processQueryResponse(struct module_qstate* qstate, struct iter_qstate* iq,
                iq->dp = NULL;
                /* Note the query restart. */
                iq->query_restart_count++;
+               iq->sent_count = 0;
 
                /* stop current outstanding queries. 
                 * FIXME: should the outstanding queries be waited for and
index 9137b404b3c9bd42173e8d050d44bec3988c1d7b..0272fe103d95cfe2cb5852a753c22c624ce57751 100644 (file)
@@ -56,6 +56,10 @@ struct iter_priv;
 #define MAX_RESTART_COUNT       8
 /** max number of referrals. Makes sure resolver does not run away */
 #define MAX_REFERRAL_COUNT     130
+/** max number of queries-sent-out.  Make sure large NS set does not loop */
+#define MAX_SENT_COUNT         16
+/** at what query-sent-count to stop target fetch policy */
+#define TARGET_FETCH_STOP      3
 /** how nice is a server without further information, in msec 
  * Equals rtt initial timeout value.
  */
@@ -252,6 +256,9 @@ struct iter_qstate {
        /** the number of times this query as followed a referral. */
        int referral_count;
 
+       /** number of queries fired off */
+       int sent_count;
+
        /**
         * The query must store NS records from referrals as parentside RRs
         * Enabled once it hits resolution problems, to throttle retries.
index 6c9664c9fac263cf9018827ee050e51c0db1b3f1..297e454ea75b1885d8b1ded908581750dfa91244 100644 (file)
@@ -1585,7 +1585,7 @@ serviced_udp_callback(struct comm_point* c, void* arg, int error,
                         * by EDNS. */
                        sq->status = serviced_query_UDP_EDNS;
                }
-               if(sq->status == serviced_query_UDP_EDNS) {
+               if(sq->status == serviced_query_UDP_EDNS && sq->last_rtt < 5000) {
                        /* fallback to 1480/1280 */
                        sq->status = serviced_query_UDP_EDNS_FRAG;
                        log_name_addr(VERB_ALGO, "try edns1xx0", sq->qbuf+10,