]> granicus.if.org Git - pdns/commitdiff
improve SOA caching for DS queries
authorKees Monshouwer <mind04@monshouwer.org>
Fri, 18 Sep 2015 11:52:44 +0000 (13:52 +0200)
committerPieter Lexis <pieter.lexis@powerdns.com>
Tue, 15 Dec 2015 08:45:21 +0000 (09:45 +0100)
pdns/dnsbackend.cc
pdns/ueberbackend.cc

index d4e78d168e0d6a8ef5c1d08b953df4cc1db24711..a072133c035aadcee8b88f27368f959c6e9fe34e 100644 (file)
@@ -38,7 +38,7 @@ bool DNSBackend::getAuth(DNSPacket *p, SOAData *sd, const DNSName &target, const
   bool found=false;
   DNSName subdomain(target);
   do {
-    if( best_match_len >= (int)subdomain.toString().length() )
+    if( best_match_len >= (int)subdomain.toString().length() && p->qtype != QType::DS )
       break;
 
     map<DNSName,int>::iterator it = negCacheMap.find(subdomain);
@@ -46,14 +46,17 @@ bool DNSBackend::getAuth(DNSPacket *p, SOAData *sd, const DNSName &target, const
 
     if(! negCached && this->getSOA( subdomain, *sd, p ) ) {
       sd->qname = subdomain;
+      if (found) // Second SOA found, we are done
+        return true;
 
       if(p->qtype.getCode() == QType::DS && subdomain==target) {
         // Found authoritative zone but look for parent zone with 'DS' record.
-        negCacheMap[subdomain]=2;
         found=true;
       } else
         return true;
     }
+    if (found)
+      negCacheMap[subdomain]=2; // don't cache SOA's during our quest for a parent zone
   }
   while( subdomain.chopOff() );   // 'www.powerdns.org' -> 'powerdns.org' -> 'org' -> ''
 
index 1d10c456531a04b915a08f1d2302079a7c0ef119..d91c7c81620ffc1935c0e9fd7151bd937be165ef 100644 (file)
@@ -256,7 +256,7 @@ bool UeberBackend::getAuth(DNSPacket *p, SOAData *sd, const DNSName &target)
   // If not special case of caching explicitly disabled (sd->db = -1), first
   // find the best match from the cache. If DS then we need to find parent so
   // dont bother with caching as it confuses matters.
-  if( sd->db != (DNSBackend *)-1 && d_cache_ttl && p->qtype != QType::DS ) {
+  if( sd->db != (DNSBackend *)-1 && d_cache_ttl ) {
       DNSName subdomain(target);
       int cstat, loops = 0;
       do {
@@ -275,13 +275,14 @@ bool UeberBackend::getAuth(DNSPacket *p, SOAData *sd, const DNSName &target)
           //L<<Logger::Error<<"Best cache match: " << sd->qname << " itteration " << loops <<endl;
 
           // Found first time round this must be the best match
-          if( loops == 0 )
+          if( loops == 0  && p->qtype != QType::DS)
             return true;
 
           from_cache = true;
           best_match_len = sd->qname.countLabels();
 
-          break;
+          if ( p->qtype != QType::DS || best_match_len < (int)target.countLabels())
+            break;
         } else if (cstat==0) {
           negCacheMap[subdomain]=1;
         } else
@@ -292,14 +293,14 @@ bool UeberBackend::getAuth(DNSPacket *p, SOAData *sd, const DNSName &target)
   }
 
   for(vector<DNSBackend *>::const_iterator i=backends.begin(); i!=backends.end();++i) {
+    // Shortcut for the case that we got a direct hit - no need to go
+    // through the other backends then.
+    if( best_match_len == (int)target.countLabels() && p->qtype != QType::DS )
+      goto auth_found;
+
     if((*i)->getAuth(p, sd, target, best_match_len, negCacheMap)) {
         best_match_len = sd->qname.countLabels(); // FIXME400
         from_cache = false;
-
-        // Shortcut for the case that we got a direct hit - no need to go
-        // through the other backends then.
-        if( best_match_len == (int)target.countLabels() )
-            goto auth_found;
     }
   }