From 9b1454721525b27e97c27c5bdce29c98a6db25bb Mon Sep 17 00:00:00 2001 From: Bert Hubert Date: Mon, 14 Feb 2005 13:40:31 +0000 Subject: [PATCH] partial commit for backup purposes: bind2backend is getting coooool! non-functional now though git-svn-id: svn://svn.powerdns.com/pdns/trunk/pdns@320 d19b8d6e-7fed-0310-83ef-9ca221ded41b --- pdns/backends/bind/bindbackend2.cc | 65 +++++++++++----- pdns/backends/bind/bindbackend2.hh | 120 +++++------------------------ pdns/qtype.cc | 2 +- pdns/qtype.hh | 2 +- 4 files changed, 70 insertions(+), 119 deletions(-) diff --git a/pdns/backends/bind/bindbackend2.cc b/pdns/backends/bind/bindbackend2.cc index 9e883ca49..0d248808a 100644 --- a/pdns/backends/bind/bindbackend2.cc +++ b/pdns/backends/bind/bindbackend2.cc @@ -292,18 +292,31 @@ static string canonic(string ret) return ret; } + +set > contents; map nbbds; /** This function adds a record to a domain with a certain id. */ void Bind2Backend::insert(int id, const string &qnameu, const string &qtype, const string &content, int ttl=300, int prio=25) { - DNSResourceRecord rr; - rr.domain_id=id; - rr.qname=canonic(qnameu); - rr.qtype=qtype; - rr.content=canonic(content); // I think this is wrong, the zoneparser should not come up with . terminated stuff XXX FIXME - rr.ttl=ttl; - rr.priority=prio; - nbbds[id]->d_records->push_back(rr); + Bind2DNSRecord bdr; + + // rr.domain_id=id; + bdr.qname=canonic(qnameu); + + if(bdr.qname==nbbds[id]->d_name) + bdr.qname.clear(); + else if(bdr.qname.length() > nbbds[id]->d_name.length()) + bdr.qname.resize(bdr.qname.length() - (nbbds[id]->d_name.length() + 1)); + else + throw AhuException("Trying to insert non-zone data, name='"+bdr.qname+"', zone='"+nbbds[id]->d_name+"'"); + + bdr.qname.swap(bdr.qname); + bdr.qtype=QType(qtype.c_str()).getCode(); + // rr.content=canonic(content); // I think this is wrong, the zoneparser should not come up with . terminated stuff XXX FIXME + bdr.ttl=ttl; + + // cout<<"Adding rr.qname: '"<d_records->push_back(bdr); } @@ -487,7 +500,7 @@ void Bind2Backend::loadConfig(string* status) } if(j==s_id_zone_map.end()) { // entirely new bbd=new BB2DomainInfo; - bbd->d_records=new vector; + bbd->d_records=new vector; bbd->d_id=domain_id++; s_name_id_map[i->name]=bbd->d_id; @@ -506,10 +519,12 @@ void Bind2Backend::loadConfig(string* status) try { ZP.parse(i->filename,i->name,bbd->d_id); // calls callback for us + L<name<d_id]->d_records->begin(), nbbds[bbd->d_id]->d_records->end()); nbbds[bbd->d_id]->setCtime(); nbbds[bbd->d_id]->d_loaded=true; // does this perform locking for us? nbbds[bbd->d_id]->d_status="parsed into memory at "+nowTime(); - + } catch(AhuException &ae) { ostringstream msg; @@ -620,6 +635,17 @@ void Bind2Backend::queueReload(BB2DomainInfo *bbd) } } +bool operator<(const Bind2DNSRecord &a, const string &b) +{ + return a.qname < b; +} + +bool operator<(const string &a, const Bind2DNSRecord &b) +{ + return a < b.qname; +} + + void Bind2Backend::lookup(const QType &qtype,const string &qname, DNSPacket *pkt_p, int zoneId ) { d_handle=new Bind2Backend::handle; @@ -644,7 +670,9 @@ void Bind2Backend::lookup(const QType &qtype,const string &qname, DNSPacket *pkt DLOG(L<<"Bind2Backend constructing handle for search for "<qname=qname; + + d_handle->qname=qname.substr(0,qname.size()-domain.length()-1); // strip domain name + // cout<<"Reduced to '"<qname<<"'"<parent=this; d_handle->qtype=qtype; @@ -672,7 +700,7 @@ void Bind2Backend::lookup(const QType &qtype,const string &qname, DNSPacket *pkt else { DLOG(L<<"Query with no results"<d_iter=d_handle->d_records->begin(); + d_handle->d_iter=equal_range(d_handle->d_records->begin(), d_handle->d_records->end(), d_handle->qname).first; d_handle->d_list=false; } @@ -716,7 +744,8 @@ bool Bind2Backend::handle::get_normal(DNSResourceRecord &r) qname<<"- "<size()<<" available!"<end() && (strcasecmp(d_iter->qname.c_str(),qname.c_str()) || !(qtype=="ANY" || (d_iter)->qtype==qtype))) { + + while(d_iter!=d_records->end() && (strcasecmp(d_iter->qname.c_str(),qname.c_str()) || !(qtype.getCode()==QType::ANY || (d_iter)->qtype==qtype))) { DLOG(L<qtype).getName()<<": '"<content<<"'"<content; - r.domain_id=(d_iter)->domain_id; + //r.content=(d_iter)->content; + // r.domain_id=(d_iter)->domain_id; r.qtype=(d_iter)->qtype; r.ttl=(d_iter)->ttl; - r.priority=(d_iter)->priority; + // r.priority=(d_iter)->priority; d_iter++; return true; @@ -763,7 +792,7 @@ bool Bind2Backend::list(const string &target, int id) bool Bind2Backend::handle::get_list(DNSResourceRecord &r) { if(d_qname_iter!=d_qname_end) { - r=*d_qname_iter; + // r=*d_qname_iter; // XXX FIXME WRONG WRONG WRONG d_qname_iter++; return true; } @@ -843,7 +872,7 @@ bool Bind2Backend::createSlaveDomain(const string &ip, const string &domain, con BB2DomainInfo *bbd = new BB2DomainInfo; - bbd->d_records = new vector; + bbd->d_records = new vector; bbd->d_name = domain; bbd->setCheckInterval(getArgAsNum("check-interval")); bbd->d_master = ip; diff --git a/pdns/backends/bind/bindbackend2.hh b/pdns/backends/bind/bindbackend2.hh index 086305d2e..24ee9666c 100644 --- a/pdns/backends/bind/bindbackend2.hh +++ b/pdns/backends/bind/bindbackend2.hh @@ -22,18 +22,23 @@ #include #include #include - +#include #include "huffman.hh" +using namespace boost; +using namespace std; -#if __GNUC__ >= 3 -# include -using namespace __gnu_cxx; -#else -# include -#endif - +struct Bind2DNSRecord +{ + string qname; + QType qtype; + uint32_t ttl; + shared_ptr content; -using namespace std; + bool operator<(const Bind2DNSRecord& rhs) const + { + return qname < rhs.qname; + } +}; class BB2DomainInfo { @@ -76,97 +81,14 @@ public: } void setCheckInterval(time_t seconds); - vector * d_records; + vector * d_records; private: time_t getCtime(); time_t d_checkinterval; time_t d_lastcheck; pthread_rwlock_t *d_rwlock; }; - - - -class BBResourceRecord -{ -public: - bool operator==(const BBResourceRecord &o) const - { - return (o.domain_id==domain_id && o.qtype==qtype && o.content==content && - o.ttl==ttl && o.priority==priority); - } - - const string *qnameptr; // 4 - unsigned int domain_id; // 4 - unsigned short int qtype; // 2 - unsigned short int priority; // 2 - const string *content; // 4 - unsigned int ttl; // 4 - -}; - -struct compare_string -{ - bool operator()(const string& s1, const string& s2) const - { - return s1 == s2; - } -}; -struct hash_string -{ - size_t operator()(const string& s) const - { - return __stl_hash_string(s.c_str()); - } -}; - -typedef hash_map, hash_string, compare_string> cmap_t; - - - -/** The Bind2Backend is a DNSBackend that can answer DNS related questions. It looks up data - in a Bind-style zone file - - How this all works is quite complex and prone to change. There are a number of containers involved which, - together, contain everything we need to know about a domain or a record. - - A domain consists of records. So, 'example.com' has 'www.example.com' as a record. - - All record names are stored in the hash_map d_qnames, with their name as index. Attached to that index - is a vector of BBResourceRecords ('Bind2Backend') belonging to that qname. Each record contains a d_domainid, - which is the ID of the domain it belongs to. - - Then there is the map called d_bbds which has as its key the Domain ID, and attached a BB2DomainInfo object, which - tells us domain metadata (place on disk, if it is a master or a slave etc). - - To allow for AXFRs, there is yet another container, the d_zone_id_map, which contains per domain_id a vector - of pointers to vectors of BBResourceRecords. When read in sequence, these deliver all records of a domain_id. - - As there is huge repitition in the right hand side of records, many records point to the same thing (IP address, nameserver), - a list of these is kept in s_contents, and each BBResourceRecord only contains a pointer to a record in s_contents. - - So, summarizing: - - class BBResourceRecord: - Everything you need to know about a record. In this context we call the name of a BBResourceRecord 'qname' - - class BB2DomainInfo: - Domain metadata, like location on disk, last time zone was checked - - d_qnames >: - If you know the qname of a record, this gives you all records under that name. - - sets_contents: - Set of all 'contents' of records, the right hand sides. - - map* > > d_zone_id_map: - If you know the zone_id, this has a vector of pointers to vectors in d_qnames, for AXFR - - mapd_bbds: - Map of all domains we know about and metadata about them. - - -*/ class Bind2Backend : public DNSBackend { public: @@ -213,13 +135,13 @@ private: Bind2Backend *parent; - vector* d_records; - vector::const_iterator d_iter; + vector* d_records; + vector::const_iterator d_iter; - vector::const_iterator d_rend; + vector::const_iterator d_rend; - vector::const_iterator d_qname_iter; - vector::const_iterator d_qname_end; + vector::const_iterator d_qname_iter; + vector::const_iterator d_qname_end; bool d_list; int id; @@ -247,7 +169,7 @@ private: ofstream *d_of; handle *d_handle; void queueReload(BB2DomainInfo *bbd); - BBResourceRecord resourceMaker(int id, const string &qtype, const string &content, int ttl, int prio); + void reload(); static string DLDomStatusHandler(const vector&parts, Utility::pid_t ppid); static string DLListRejectsHandler(const vector&parts, Utility::pid_t ppid); diff --git a/pdns/qtype.cc b/pdns/qtype.cc index 795d3b62f..f2c9121bf 100644 --- a/pdns/qtype.cc +++ b/pdns/qtype.cc @@ -120,7 +120,7 @@ QType::QType(int n) code=n; } -QType::QType(char *p) +QType::QType(const char *p) { QType(); code=chartocode(p); diff --git a/pdns/qtype.hh b/pdns/qtype.hh index 0833a8c72..dd81ae3f2 100644 --- a/pdns/qtype.hh +++ b/pdns/qtype.hh @@ -47,7 +47,7 @@ class QType public: QType(); //!< Naked constructor explicit QType(int); //!< convert from an integer to a QType - QType(char *p); //!< convert from a char* to a QType + QType(const char *p); //!< convert from a char* to a QType QType &operator=(int); //!< Assigns integers to us QType &operator=(const char *); //!< Assings strings to us -- 2.50.0