From: Wouter Wijngaards Date: Fri, 4 May 2007 13:48:24 +0000 (+0000) Subject: Update rrset. X-Git-Tag: release-0.3~18 X-Git-Url: http://git.ipfire.org/cgi-bin/gitweb.cgi?a=commitdiff_plain;h=072e0e973a1c86a5c2bed6efe56c6b71f37d8d7f;p=thirdparty%2Funbound.git Update rrset. git-svn-id: file:///svn/unbound/trunk@285 be551aaa-1e26-0410-a405-d3ace91eadb9 --- diff --git a/daemon/worker.c b/daemon/worker.c index 09fe3b945..8a0591613 100644 --- a/daemon/worker.c +++ b/daemon/worker.c @@ -135,8 +135,16 @@ static int need_to_update_rrset(struct packed_rrset_data* newd, struct packed_rrset_data* cached) { + /* o if current RRset is more trustworthy - insert it */ if( newd->trust > cached->trust ) return 1; + /* o same trust, but different in data - insert it */ + if( newd->trust == cached->trust && + !rrsetdata_equal(newd, cached)) + return 1; + /* o see if TTL is better than TTL in cache. */ + /* if so, see if rrset+rdata is the same */ + /* if so, update TTL in cache, even if trust is worse. */ if( newd->ttl > cached->ttl && rrsetdata_equal(newd, cached)) return 1; @@ -150,11 +158,7 @@ worker_store_rrsets(struct worker* worker, struct reply_info* rep) struct lruhash_entry* e; size_t i; /* see if rrset already exists in cache, if not insert it. */ - /* if it does exist: */ - /* o if current RRset is more trustworthy - insert it */ - /* o see if TTL is better than TTL in cache. */ - /* if so, see if rrset+rdata is (exactly!) the same */ - /* if so, update TTL in cache. */ + /* if it does exist: check to insert it */ for(i=0; irrset_count; i++) { rep->ref[i].key = rep->rrsets[i]; rep->ref[i].id = rep->rrsets[i]->id; @@ -359,6 +363,8 @@ answer_from_cache(struct worker* worker, struct lruhash_entry* e, uint16_t id, } /* check rrsets */ for(i=0; irrset_count; i++) { + if(i>0 && rep->ref[i].key == rep->ref[i-1].key) + continue; /* only lock items once */ lock_rw_rdlock(&rep->ref[i].key->entry.lock); if(rep->ref[i].id != rep->ref[i].key->id || rep->ttl <= timenow) { @@ -376,8 +382,11 @@ answer_from_cache(struct worker* worker, struct lruhash_entry* e, uint16_t id, flags, &mrentry->key); } /* unlock */ - for(i=0; irrset_count; i++) + for(i=0; irrset_count; i++) { + if(i>0 && rep->ref[i].key == rep->ref[i-1].key) + continue; /* only unlock items once */ lock_rw_unlock(&rep->ref[i].key->entry.lock); + } region_free_all(worker->scratchpad); /* go and return this buffer to the client */ return 1; diff --git a/doc/Changelog b/doc/Changelog index a5f2e4dc3..55244f47a 100644 --- a/doc/Changelog +++ b/doc/Changelog @@ -8,6 +8,7 @@ - thread keeps a scratchpad region for handling messages. - writev used in netevent to write tcp length and data after another. This saves a roundtrip on tcp replies. + - test for one rrset updated in the cache. 3 May 2007: Wouter - fill refs. Use new parse and encode to answer queries. diff --git a/testdata/rrset_updated.rpl b/testdata/rrset_updated.rpl new file mode 100644 index 000000000..f40b69f77 --- /dev/null +++ b/testdata/rrset_updated.rpl @@ -0,0 +1,124 @@ +; This is a comment. +; config options go here. +CONFIG_END + +SCENARIO_BEGIN Query receives answer from the cache + +STEP 1 QUERY +ENTRY_BEGIN + REPLY RD + SECTION QUESTION + www.example.com. IN A +ENTRY_END +; the query is sent to the forwarder - no cache yet. +STEP 2 CHECK_OUT_QUERY +ENTRY_BEGIN + MATCH qname qtype opcode + SECTION QUESTION + www.example.com. IN A +ENTRY_END +STEP 3 REPLY +ENTRY_BEGIN + MATCH opcode qtype qname + ADJUST copy_id + ; authoritative answer + REPLY QR AA RD RA NOERROR + SECTION QUESTION + www.example.com. IN A + SECTION ANSWER + www.example.com. IN A 10.20.30.40 + SECTION AUTHORITY + example.com. IN NS ns.example.com. + SECTION ADDITIONAL + ns.example.com. IN A 10.20.30.50 +ENTRY_END +STEP 4 CHECK_ANSWER +ENTRY_BEGIN + MATCH all + ; first reply, have AA set. + REPLY QR AA RD RA + SECTION QUESTION + www.example.com. IN A + SECTION ANSWER + www.example.com. IN A 10.20.30.40 + SECTION AUTHORITY + example.com. IN NS ns.example.com. + SECTION ADDITIONAL + ns.example.com. IN A 10.20.30.50 +ENTRY_END + +; another query passes along +STEP 6 QUERY +ENTRY_BEGIN + REPLY RD + SECTION QUESTION + bla.example.com. IN A +ENTRY_END +STEP 7 CHECK_OUT_QUERY +ENTRY_BEGIN + MATCH qname qtype opcode + SECTION QUESTION + bla.example.com. IN A +ENTRY_END +STEP 8 REPLY +; This answer has updated information on ns2.example.com. +ENTRY_BEGIN + MATCH opcode qtype qname + ADJUST copy_id + ; authoritative answer + REPLY QR AA RD RA NOERROR + SECTION QUESTION + bla.example.com. IN A + SECTION ANSWER + bla.example.com. IN A 10.20.30.140 + SECTION AUTHORITY + example.com. IN NS ns.example.com. + example.com. IN NS ns2.example.com. + SECTION ADDITIONAL + ns.example.com. IN A 10.20.30.50 + ns2.example.com. IN A 10.20.30.53 +ENTRY_END +STEP 9 CHECK_ANSWER +ENTRY_BEGIN + MATCH all + ; first reply, have AA set. + REPLY QR AA RD RA + SECTION QUESTION + bla.example.com. IN A + SECTION ANSWER + bla.example.com. IN A 10.20.30.140 + SECTION AUTHORITY + example.com. IN NS ns.example.com. + example.com. IN NS ns2.example.com. + SECTION ADDITIONAL + ns.example.com. IN A 10.20.30.50 + ns2.example.com. IN A 10.20.30.53 +ENTRY_END + + +; original www.example.com query +STEP 10 QUERY +ENTRY_BEGIN + REPLY RD + SECTION QUESTION + www.example.com. IN A +ENTRY_END +; immediate answer without an OUT_QUERY happening (checked on exit) +; also, the answer does not have AA set +; NS rrset has been updated. +STEP 11 CHECK_ANSWER +ENTRY_BEGIN + MATCH all + REPLY QR RD RA + SECTION QUESTION + www.example.com. IN A + SECTION ANSWER + www.example.com. IN A 10.20.30.40 + SECTION AUTHORITY + example.com. IN NS ns.example.com. + example.com. IN NS ns2.example.com. + SECTION ADDITIONAL + ns.example.com. IN A 10.20.30.50 +ENTRY_END + +SCENARIO_END