]> git.ipfire.org Git - thirdparty/pdns.git/commitdiff
I think this continues the merge and conflict resolution. Endofunctors.
authorbert hubert <bert.hubert@netherlabs.nl>
Sun, 12 Apr 2015 10:42:07 +0000 (12:42 +0200)
committerbert hubert <bert.hubert@netherlabs.nl>
Sun, 12 Apr 2015 10:42:07 +0000 (12:42 +0200)
pdns/.gitignore
pdns/dnsname.cc
pdns/dnsname.hh

index 9fd51934f0850b9284e56689c9bf09c8f68c16af..5d54f52b677db0b324e5bfda6dc6ba731a5e3ad5 100644 (file)
@@ -47,4 +47,7 @@ version_generated.h
 /test-suite.log
 /testrunner.log
 /testrunner.trs
-/pubsuffix.cc
\ No newline at end of file
+/pubsuffix.cc
+/calidns
+/dumresp
+/htmlfiles.h
index 7dc051e0ca57528a8d7b6088cd96b91a1b42745f..4c723005c3e28a5d521bdafaef6bd3f92832b070 100644 (file)
@@ -2,7 +2,6 @@
 #include <boost/format.hpp>
 #include <string>
 #include "dnswriter.hh"
-#include "misc.hh"
 
 /* raw storage
    in DNS label format, without trailing 0. So the root is of length 0.
 DNSName::DNSName(const char* p)
 {
   auto labels = segmentDNSName(p);
-  for(const auto& e : labels) {
-    if(e.size() > 63)
-      throw std::range_error("label too long");
-    d_storage.append(1, (char)e.size());
-    d_storage.append(e.c_str(), e.length());
-  }
+  for(const auto& e : labels)
+    appendRawLabel(e);
 }
 
-// this should be the __only__ dns name parser in PowerDNS. 
 DNSName::DNSName(const char* pos, int len, int offset, bool uncompress, uint16_t* qtype, uint16_t* qclass, unsigned int* consumed)
 {
+  packetParser(pos, len, offset, uncompress, qtype, qclass, consumed);
+}
+
+// this should be the __only__ dns name parser in PowerDNS.
+void DNSName::packetParser(const char* pos, int len, int offset, bool uncompress, uint16_t* qtype, uint16_t* qclass, unsigned int* consumed)
+{
+  bool labelAdded = false;
   unsigned char labellen;
   const char *opos = pos;
   pos += offset;
@@ -33,16 +34,21 @@ DNSName::DNSName(const char* pos, int len, int offset, bool uncompress, uint16_t
   while((labellen=*pos++) && pos < end) { // "scan and copy"
     if(labellen & 0xc0) {
       if(!uncompress)
-       throw std::range_error("Found compressed label, instructed not to follow");
+        throw std::range_error("Found compressed label, instructed not to follow");
 
       labellen &= (~0xc0);
       int newpos = (labellen << 8) + *(const unsigned char*)pos;
 
-      (*this) += DNSName(opos, len, newpos, false);
+      packetParser(opos, len, newpos, labelAdded);
       pos++;
       break;
     }
-    appendRawLabel(string(pos, labellen));
+    if (pos + labellen < end) {
+      labelAdded = true;
+      appendRawLabel(string(pos, labellen));
+    }
+    else
+      throw std::range_error("Found an invalid label length in qname");
     pos+=labellen;
   }
   if(consumed)
@@ -102,6 +108,9 @@ void DNSName::appendRawLabel(const std::string& label)
     throw std::range_error("no such thing as an empty label");
   if(label.size() > 63)
     throw std::range_error("label too long");
+  if(d_storage.size() + label.size() > 253) // reserve two bytes, one for length and one for the root label
+    throw std::range_error("name too long");
+
   d_storage.append(1, (char)label.size());
   d_storage.append(label.c_str(), label.length());
 }
@@ -110,9 +119,10 @@ void DNSName::prependRawLabel(const std::string& label)
 {
   if(label.empty())
     throw std::range_error("no such thing as an empty label");
-
   if(label.size() > 63)
     throw std::range_error("label too long");
+  if(d_storage.size() + label.size() > 253) // reserve two bytes, one for length and one for the root label
+    throw std::range_error("name too long");
 
   string_t prep(1, (char)label.size());
   prep.append(label.c_str(), label.size());
@@ -124,9 +134,8 @@ vector<string> DNSName::getRawLabels() const
   vector<string> ret;
 
   // 3www4ds9a2nl
-  for(const char* p = d_storage.c_str(); p < d_storage.c_str() + d_storage.size(); p+=*p+1) {
+  for(const char* p = d_storage.c_str(); p < d_storage.c_str() + d_storage.size(); p+=*p+1)
     ret.push_back({p+1, (unsigned int)*p}); // XXX FIXME
-  }
   return ret;
 }
 
@@ -141,7 +150,7 @@ bool DNSName::chopOff()
 unsigned int DNSName::countLabels() const
 {
   unsigned int count=0;
-  for(const char* p = d_storage.c_str(); p < d_storage.c_str() + d_storage.size(); p+= 1+*(unsigned char*)p) 
+  for(const char* p = d_storage.c_str(); p < d_storage.c_str() + d_storage.size(); p+=*p+1)
     ++count;
   return count;
 }
index ea99a6389d2f63eeb81fc824becfcae117ca888e..f2b83a6d67beb75b4d6102d7490fd06d1fbf7fb5 100644 (file)
@@ -4,6 +4,7 @@
 #include <set>
 #include <deque>
 #include <strings.h>
+#include "misc.hh"
 
 // #include <ext/vstring.h>
 
@@ -39,6 +40,9 @@ public:
   void trimToLabels(unsigned int);
   DNSName& operator+=(const DNSName& rhs)
   {
+    if(d_storage.size() + rhs.d_storage.size() > 254) // reserve one byte for the root label
+      throw std::range_error("name too long");
+
     d_storage+=rhs.d_storage;
     return *this;
   }
@@ -57,6 +61,7 @@ private:
   typedef std::string string_t;
   string_t d_storage;
 
+  void packetParser(const char* p, int len, int offset, bool uncompress, uint16_t* qtype=0, uint16_t* qclass=0, unsigned int* consumed=0);
   static std::string escapeLabel(const std::string& orig);
   static std::string unescapeLabel(const std::string& orig);
 };