From: Kees Monshouwer Date: Fri, 30 May 2014 18:54:10 +0000 (+0200) Subject: get NSECx direct from backend and use it for lmdb-backend X-Git-Tag: auth-3.4.0-rc1~106^2~5 X-Git-Url: http://git.ipfire.org/cgi-bin/gitweb.cgi?a=commitdiff_plain;h=d88babea9d3f081a704b8d36879864932f1e0046;p=thirdparty%2Fpdns.git get NSECx direct from backend and use it for lmdb-backend --- diff --git a/modules/lmdbbackend/lmdbbackend.cc b/modules/lmdbbackend/lmdbbackend.cc index 0a2e470cc0..68e9c8c5ef 100644 --- a/modules/lmdbbackend/lmdbbackend.cc +++ b/modules/lmdbbackend/lmdbbackend.cc @@ -21,6 +21,7 @@ #include #include "lmdbbackend.hh" #include +#include #if 0 #define DEBUGLOG(msg) L<& meta) +{ + if (kind == "PRESIGNED") { + meta.push_back("1"); + } else if (kind == "NSEC3PARAM") { + meta.push_back("1 0 1 abcd"); + } + return true; +} + +bool LMDBBackend::getDirectNSECx(uint32_t id, const string &hashed, string &before, DNSResourceRecord &rr) +{ + MDB_val key, data; + string key_str, cur_key, cur_value; + vector keyparts, valparts; + + key_str=itoa(id)+"\t"+toBase32Hex(bitFlip(hashed)); + key.mv_data = (char *)key_str.c_str(); + key.mv_size = key_str.length(); + + before.clear(); + if(!mdb_cursor_get(nsecx_cursor, &key, &data, MDB_SET_RANGE)) { + cur_key.assign((const char *)key.mv_data, key.mv_size); + cur_value.assign((const char *)data.mv_data, data.mv_size); + stringtok(keyparts,cur_key,"\t"); + stringtok(valparts,cur_value,"\t"); + + if( keyparts.size() != 2 || valparts.size() != 4 ) { + throw PDNSException("Invalid record in nsecx table: key: '" + cur_key + "'; value: "+ cur_value); + } + + // is the key a full match or does the id part match our zone? + // if it does we have a valid answer. + if (!key_str.compare(cur_key) || atoi(keyparts[0].c_str()) == (int) id) // FIXME need atoui + goto hasnsecx; + } + // no match, now we look for the last record in the NSECx chain. + key_str=itoa(id)+"\t"; + key.mv_data = (char *)key_str.c_str(); + key.mv_size = key_str.length(); + + if(!mdb_cursor_get(nsecx_cursor, &key, &data, MDB_SET_RANGE)) { + cur_key.assign((const char *)key.mv_data, key.mv_size); + cur_value.assign((const char *)data.mv_data, data.mv_size); + stringtok(keyparts,cur_key,"\t"); + stringtok(valparts,cur_value,"\t"); + + if( keyparts.size() != 2 || valparts.size() != 4 ) { + throw PDNSException("Invalid record in nsecx table: key: '" + cur_key + "'; value: "+ cur_value); + } + + if (!key_str.compare(cur_key) || atoi(keyparts[0].c_str()) == (int) id) // FIXME we need atoui + goto hasnsecx; + } + + DEBUGLOG("NSECx record for '"<& meta); + bool getDirectNSECx(uint32_t id, const string &hashed, string &before, DNSResourceRecord &rr); + bool getAuthZone( string &rev_zone ); bool getAuthData( SOAData &, DNSPacket *); }; diff --git a/pdns/dnsbackend.hh b/pdns/dnsbackend.hh index 0024925b54..b035d83e5a 100644 --- a/pdns/dnsbackend.hh +++ b/pdns/dnsbackend.hh @@ -363,6 +363,17 @@ public: return false; } + //! called to get a NSECx record from backend + virtual bool getDirectNSECx(uint32_t id, const string &hashed, string &before, DNSResourceRecord &rr) + { + return false; + } + //! called to get RRSIG record(s) from backend + virtual bool getDirectRRSIGs(uint32_t id, const string &qname, const QType &qtype, const vector&rrs) + { + return false; + } + protected: bool mustDo(const string &key); const string &getArg(const string &key); diff --git a/pdns/misc.cc b/pdns/misc.cc index 70f81170fb..a43030ba6f 100644 --- a/pdns/misc.cc +++ b/pdns/misc.cc @@ -434,6 +434,15 @@ string uitoa(unsigned int i) // MSVC 6 doesn't grok overloading (un)signed return o.str(); } +string bitFlip(const string &str) +{ + string::size_type pos=0, epos=str.size(); + string ret; + ret.reserve(epos); + for(;pos < epos; ++pos) + ret.append(1, ~str[pos]); + return ret; +} string stringerror() { diff --git a/pdns/misc.hh b/pdns/misc.hh index 4712e28ac1..a503f8da68 100644 --- a/pdns/misc.hh +++ b/pdns/misc.hh @@ -171,6 +171,7 @@ string stringerror(); string netstringerror(); string itoa(int i); string uitoa(unsigned int i); +string bitFlip(const string &str); void dropPrivs(int uid, int gid); int makeGidNumeric(const string &group); diff --git a/pdns/packethandler.cc b/pdns/packethandler.cc index 4f260df928..d08b90fbc9 100644 --- a/pdns/packethandler.cc +++ b/pdns/packethandler.cc @@ -633,6 +633,7 @@ void PacketHandler::addNSEC3(DNSPacket *p, DNSPacket *r, const string& target, c bool doNextcloser = false; string unhashed, hashed, before, after; string closest; + DNSResourceRecord rr; if (mode == 2 || mode == 3 || mode == 4) { closest=wildcard; @@ -648,7 +649,8 @@ void PacketHandler::addNSEC3(DNSPacket *p, DNSPacket *r, const string& target, c hashed=hashQNameWithSalt(ns3rc.d_iterations, ns3rc.d_salt, unhashed); DLOG(L<<"1 hash: "<addRecord(rr); } // add covering NSEC3 RR @@ -685,10 +691,12 @@ void PacketHandler::addNSEC3(DNSPacket *p, DNSPacket *r, const string& target, c hashed=hashQNameWithSalt(ns3rc.d_iterations, ns3rc.d_salt, unhashed); DLOG(L<<"2 hash: "<addRecord(rr); } // wildcard denial @@ -698,9 +706,12 @@ void PacketHandler::addNSEC3(DNSPacket *p, DNSPacket *r, const string& target, c hashed=hashQNameWithSalt(ns3rc.d_iterations, ns3rc.d_salt, unhashed); DLOG(L<<"3 hash: "<addRecord(rr); } } diff --git a/pdns/ueberbackend.cc b/pdns/ueberbackend.cc index 08bac7d5db..37098f2fe0 100644 --- a/pdns/ueberbackend.cc +++ b/pdns/ueberbackend.cc @@ -235,6 +235,24 @@ bool UeberBackend::getTSIGKeys(std::vector< struct TSIGKey > &keys) return true; } +bool UeberBackend::getDirectNSECx(uint32_t id, const string &hashed, string &before, DNSResourceRecord &rr) +{ + BOOST_FOREACH(DNSBackend* db, backends) { + if(db->getDirectNSECx(id, hashed, before, rr)) + return true; + } + return false; +} + +bool UeberBackend::getDirectRRSIGs(uint32_t id, const string &qname, const QType &qtype, const vector&rrs) +{ + BOOST_FOREACH(DNSBackend* db, backends) { + if(db->getDirectRRSIGs(id, qname, qtype, rrs)) + return true; + } + return false; +} + /* Called from anywhere to signal a reload of all backend databases */ void UeberBackend::reload_all() { diff --git a/pdns/ueberbackend.hh b/pdns/ueberbackend.hh index 53eef920ca..23bea196da 100644 --- a/pdns/ueberbackend.hh +++ b/pdns/ueberbackend.hh @@ -144,6 +144,9 @@ public: bool activateDomainKey(const string& name, unsigned int id); bool deactivateDomainKey(const string& name, unsigned int id); + bool getDirectNSECx(uint32_t id, const string &hashed, string &before, DNSResourceRecord &rr); + bool getDirectRRSIGs(uint32_t id, const string &qname, const QType &qtype, const vector&rrs); + bool getTSIGKey(const string& name, string* algorithm, string* content); bool setTSIGKey(const string& name, const string& algorithm, const string& content); bool deleteTSIGKey(const string& name); diff --git a/pdns/zone2lmdb.cc b/pdns/zone2lmdb.cc index 2741868527..a7d84c4e4f 100644 --- a/pdns/zone2lmdb.cc +++ b/pdns/zone2lmdb.cc @@ -42,6 +42,7 @@ #include #include #include +#include "base32.hh" StatBag S; int g_numZones=0; @@ -117,8 +118,11 @@ void emitData(string zone, ZoneParserTNG &zpt){ } if (rr.qtype == QType::NSEC || rr.qtype == QType::NSEC3) { - keyStr=stripDot(rr.qname)+"\t"+itoa(g_numZones+1); - dataStr=itoa(rr.ttl)+"\t"+rr.content; + if (rr.qtype == QType::NSEC) + keyStr=stripDot(rr.qname)+"\t"+itoa(g_numZones+1); + else + keyStr=itoa(g_numZones+1)+"\t"+toBase32Hex(bitFlip(fromBase32Hex(makeRelative(stripDot(rr.qname), zone)))); + dataStr=rr.qname+"\t"+itoa(rr.ttl)+"\t"+rr.qtype.getName()+"\t"+rr.content; key.mv_data = (char*)keyStr.c_str(); key.mv_size = keyStr.length();