[svn] commit: r1977 - in /branches/trac192/src/lib: datasrc/ datasrc/tests/ dns/ dns/tests/
BIND 10 source code commits
bind10-changes at lists.isc.org
Sat May 29 02:56:27 UTC 2010
Author: each
Date: Sat May 29 02:56:27 2010
New Revision: 1977
Log:
checkpoint: hooked hot cache into query logic.
Modified:
branches/trac192/src/lib/datasrc/TODO
branches/trac192/src/lib/datasrc/cache.cc
branches/trac192/src/lib/datasrc/cache.h
branches/trac192/src/lib/datasrc/data_source.cc
branches/trac192/src/lib/datasrc/data_source.h
branches/trac192/src/lib/datasrc/query.cc
branches/trac192/src/lib/datasrc/query.h
branches/trac192/src/lib/datasrc/tests/cache_unittest.cc
branches/trac192/src/lib/datasrc/tests/sqlite3_unittest.cc
branches/trac192/src/lib/datasrc/tests/static_unittest.cc
branches/trac192/src/lib/dns/rrsetlist.cc
branches/trac192/src/lib/dns/rrsetlist.h
branches/trac192/src/lib/dns/tests/rrsetlist_unittest.cc
Modified: branches/trac192/src/lib/datasrc/TODO
==============================================================================
--- branches/trac192/src/lib/datasrc/TODO (original)
+++ branches/trac192/src/lib/datasrc/TODO Sat May 29 02:56:27 2010
@@ -17,3 +17,12 @@
- add a fast lookup method (using a hash table or a std::map)
to HotCache so retrieval isn't linear.
+
+
+TESTS:
+ - ncache (also need to expand so that ncache returns appropriate status,
+ i.e., name not found or type not found)
+ - DS query
+ - make sure cache insert overwrites existing records
+
+- examine rdclass==ANY queries. do these make sense to support in any way?
Modified: branches/trac192/src/lib/datasrc/cache.cc
==============================================================================
--- branches/trac192/src/lib/datasrc/cache.cc (original)
+++ branches/trac192/src/lib/datasrc/cache.cc Sat May 29 02:56:27 2010
@@ -25,24 +25,34 @@
namespace datasrc {
// CacheNode constructors
-CacheNode::CacheNode(const isc::dns::RRsetPtr rrset, time_t interval) :
- qname(rrset->getName()), qclass(rrset->getClass()),
- qtype(rrset->getType()), rrset_(rrset)
+CacheNode::CacheNode(const isc::dns::RRsetPtr rrset, uint32_t flags,
+ time_t interval) :
+ qname(rrset->getName()), qclass(rrset->getClass()), qtype(rrset->getType())
{
time_t now = time(NULL);
expiry_ = now + interval;
+ entry_ = CacheEntryPtr(new CacheEntry);
+ entry_->rrset = rrset;
+ entry_->flags = flags;
+
prev = CacheNodePtr();
next = CacheNodePtr();
}
CacheNode::CacheNode(const isc::dns::Name& name,
const isc::dns::RRClass& rrclass,
- const isc::dns::RRType& rrtype, const time_t interval) :
- qname(name), qclass(rrclass), qtype(rrtype), rrset_(RRsetPtr())
+ const isc::dns::RRType& rrtype,
+ uint32_t flags,
+ const time_t interval) :
+ qname(name), qclass(rrclass), qtype(rrtype)
{
time_t now = time(NULL);
expiry_ = now + interval;
+
+ entry_ = CacheEntryPtr(new CacheEntry);
+ entry_->rrset = RRsetPtr();
+ entry_->flags = flags;
prev = CacheNodePtr();
next = CacheNodePtr();
@@ -71,29 +81,27 @@
head = tail = CacheNodePtr();
}
-RRsetPtr
-HotCache::retrieve(Name qname, RRClass qclass, RRType qtype) {
+
+CacheNodePtr
+HotCache::retrieve(Name n, RRClass c, RRType t) {
CacheNodePtr node;
- node = head;
- do {
- if (node->qtype == qtype && node->qclass == qclass &&
- node->qname == qname)
- {
+ for (node = head; node != CacheNodePtr(); node = node->next) {
+ if (node->qtype == t && node->qclass == c && node->qname == n) {
break;
}
- } while (node = node->next);
+ }
if (! node) {
- return (RRsetPtr());
+ return (CacheNodePtr());
}
if (node->isValid()) {
promote(node);
- return (node->getRRset());
+ return (node);
} else {
remove(node);
- return (RRsetPtr());
+ return (CacheNodePtr());
}
}
@@ -117,16 +125,22 @@
}
void
-HotCache::cache(RRsetPtr rrset, const time_t interval) {
- CacheNodePtr node(new CacheNode(rrset, interval));
- this->insert(node);
+HotCache::cache(RRsetPtr rrset, const uint32_t flags, const time_t interval) {
+ CacheNodePtr node(new CacheNode(rrset, flags, interval));
+ insert(node);
}
void
HotCache::ncache(const Name& name, const RRClass &rrclass,
- const RRType& rrtype, const time_t interval) {
- CacheNodePtr node(new CacheNode(name, rrclass, rrtype, interval));
- this->insert(node);
+ const RRType& rrtype, const uint32_t flags,
+ const time_t interval)
+{
+ if (rrtype == RRType::ANY() || rrclass == RRClass::ANY()) {
+ return;
+ }
+
+ CacheNodePtr node(new CacheNode(name, rrclass, rrtype, flags, interval));
+ insert(node);
}
void
Modified: branches/trac192/src/lib/datasrc/cache.h
==============================================================================
--- branches/trac192/src/lib/datasrc/cache.h (original)
+++ branches/trac192/src/lib/datasrc/cache.h Sat May 29 02:56:27 2010
@@ -31,23 +31,35 @@
namespace datasrc {
class CacheNode;
+typedef boost::shared_ptr<CacheNode> CacheNodePtr;
+class CacheEntry;
+typedef boost::shared_ptr<CacheEntry> CacheEntryPtr;
-typedef boost::shared_ptr<CacheNode> CacheNodePtr;
+class CacheEntry {
+public:
+ isc::dns::RRsetPtr rrset;
+ uint32_t flags;
+};
// A node in the data cache; keyed by qname/qclass/qtype, contains a
// pointer to a single RRset.
class CacheNode {
public:
// Constructors
- CacheNode(const isc::dns::RRsetPtr rrset, time_t interval);
- CacheNode(const isc::dns::Name& name, const isc::dns::RRClass& rrclass,
- const isc::dns::RRType& rrtype, const time_t interval);
+ CacheNode(const isc::dns::RRsetPtr rrset,
+ const uint32_t flags,
+ time_t interval);
+ CacheNode(const isc::dns::Name& name,
+ const isc::dns::RRClass& rrclass,
+ const isc::dns::RRType& rrtype,
+ const uint32_t flags,
+ const time_t interval);
// Destructor
~CacheNode();
- isc::dns::RRsetPtr getRRset() const { return (rrset_); }
-
+ isc::dns::RRsetPtr getRRset() const { return (entry_->rrset); }
+ uint32_t getFlags() const { return (entry_->flags); }
bool isValid() const;
// List pointers
@@ -62,7 +74,7 @@
private:
// The cached RRset data
- const isc::dns::RRsetPtr rrset_;
+ CacheEntryPtr entry_;
// When the record should be discarded
time_t expiry_;
@@ -78,16 +90,21 @@
~HotCache();
// Retrieve a record from the cache
- isc::dns::RRsetPtr retrieve(isc::dns::Name qname,
- isc::dns::RRClass qclass,
- isc::dns::RRType qtype);
+ CacheNodePtr retrieve(isc::dns::Name qname,
+ isc::dns::RRClass qclass,
+ isc::dns::RRType qtype);
// Positively cache an RRset
- void cache(isc::dns::RRsetPtr rrset, const time_t interval);
+ void cache(isc::dns::RRsetPtr rrset,
+ const uint32_t flags,
+ const time_t interval = 30);
// Negatively cache a name/class/type tuple
- void ncache(const isc::dns::Name& name, const isc::dns::RRClass& rrclass,
- const isc::dns::RRType& rrtype, const time_t interval);
+ void ncache(const isc::dns::Name& name,
+ const isc::dns::RRClass& rrclass,
+ const isc::dns::RRType& rrtype,
+ const uint32_t flags,
+ const time_t interval = 30);
void setSlots(int slots);
int getSlots() const;
Modified: branches/trac192/src/lib/datasrc/data_source.cc
==============================================================================
--- branches/trac192/src/lib/datasrc/data_source.cc (original)
+++ branches/trac192/src/lib/datasrc/data_source.cc Sat May 29 02:56:27 2010
@@ -24,6 +24,10 @@
#include <boost/shared_ptr.hpp>
#include <boost/foreach.hpp>
+#include <datasrc/cache.h>
+#include <datasrc/data_source.h>
+#include <datasrc/query.h>
+
#include <dns/base32.h>
#include <dns/buffer.h>
#include <dns/message.h>
@@ -34,9 +38,6 @@
#include <dns/sha1.h>
#include <cc/data.h>
-
-#include "data_source.h"
-#include "query.h"
#define RETERR(x) do { \
DataSrc::Result r = (x); \
@@ -125,6 +126,7 @@
return;
}
+ // Stop chasing CNAMES after 16 lookups, to prevent loops
if (q.tooMany()) {
return;
}
@@ -139,31 +141,306 @@
// Perform the query specified in a QueryTask object
DataSrc::Result
doQueryTask(QueryTask& task, NameMatch& zoneinfo, RRsetList& target) {
+ HotCache& cache = task.q.cache;
+ RRsetList rrsets;
+ RRsetPtr rrset;
+ CacheNodePtr cnode;
+ int count = 0;
+ uint32_t flags = 0;
+ bool found = false;
+
+ // First, we check the hot cache for the requested information.
+ switch (task.op) {
+ case QueryTask::SIMPLE_QUERY: // Find exact RRset
+ if (task.qtype == RRType::ANY() || task.qclass == RRClass::ANY()) {
+ // ANY queries must be handled by the low-level data source
+ // or the results won't be guaranteed to be complete
+ break;
+ }
+
+ cnode = cache.retrieve(task.qname, task.qclass, task.qtype);
+ if (!cnode) {
+ break;
+ }
+
+ rrset = cnode->getRRset();
+ flags = cnode->getFlags();
+
+ if (rrset) {
+ rrsets.addRRset(cnode->getRRset());
+ ++count;
+ } else {
+ ++count;
+ }
+
+ if (count == 1) {
+ task.flags = flags;
+ target.append(rrsets);
+ return (DataSrc::SUCCESS);
+ }
+ break;
+
+ case QueryTask::AUTH_QUERY: // Find exact RRset or CNAME
+ if (task.qtype == RRType::ANY() || task.qclass == RRClass::ANY()) {
+ break;
+ }
+
+ cnode = cache.retrieve(task.qname, task.qclass, task.qtype);
+ if (!cnode || !cnode->getRRset() != 0) {
+ CacheNodePtr cnamenode = cache.retrieve(task.qname, task.qclass,
+ RRType::CNAME());
+ if (cnamenode && cnamenode->getRRset()) {
+ cnode = cnamenode;
+ }
+ }
+ if (!cnode) {
+ break;
+ }
+
+ rrset = cnode->getRRset();
+ flags = cnode->getFlags();
+
+ if (rrset) {
+ rrsets.addRRset(rrset);
+ task.flags = flags;
+ ++count;
+ } else {
+ ++count;
+ }
+
+ if (count == 1) {
+ target.append(rrsets);
+ task.flags = flags;
+ return (DataSrc::SUCCESS);
+ }
+ break;
+
+ case QueryTask::GLUE_QUERY: // Find addresses
+ case QueryTask::NOGLUE_QUERY:
+ // (XXX: need to figure out how to deal with noglue case)
+ cnode = cache.retrieve(task.qname, task.qclass, RRType::A());
+ if (cnode) {
+ rrset = cnode->getRRset();
+ flags = cnode->getFlags();
+ if (rrset) {
+ rrsets.addRRset(rrset);
+ found = true;
+ ++count;
+ } else {
+ ++count;
+ }
+ }
+
+ cnode = cache.retrieve(task.qname, task.qclass, RRType::AAAA());
+ if (cnode) {
+ rrset = cnode->getRRset();
+ flags |= cnode->getFlags();
+ if (rrset) {
+ rrsets.addRRset(rrset);
+ found = true;
+ ++count;
+ } else {
+ ++count;
+ }
+ }
+
+ if (count == 2) {
+ if (found) {
+ flags &= ~DataSrc::TYPE_NOT_FOUND;
+ }
+ task.flags = flags;
+ target.append(rrsets);
+ return (DataSrc::SUCCESS);
+ }
+ break;
+
+
+ case QueryTask::REF_QUERY: // Find NS, DS and/or DNAME
+ cnode = cache.retrieve(task.qname, task.qclass, RRType::NS());
+ if (cnode) {
+ rrset = cnode->getRRset();
+ flags = cnode->getFlags();
+ if (rrset) {
+ rrsets.addRRset(rrset);
+ found = true;
+ ++count;
+ } else {
+ ++count;
+ }
+ }
+
+ cnode = cache.retrieve(task.qname, task.qclass, RRType::DS());
+ if (cnode) {
+ rrset = cnode->getRRset();
+ flags |= cnode->getFlags();
+ if (rrset) {
+ rrsets.addRRset(rrset);
+ found = true;
+ ++count;
+ } else {
+ ++count;
+ }
+ }
+
+ cnode = cache.retrieve(task.qname, task.qclass, RRType::DNAME());
+ if (cnode) {
+ rrset = cnode->getRRset();
+ flags |= cnode->getFlags();
+ if (rrset) {
+ rrsets.addRRset(rrset);
+ found = true;
+ ++count;
+ } else {
+ ++count;
+ }
+ }
+
+ if (count == 3) {
+ if (found) {
+ flags &= ~DataSrc::TYPE_NOT_FOUND;
+ flags &= DataSrc::REFERRAL;
+ }
+ task.flags = flags;
+ target.append(rrsets);
+ return (DataSrc::SUCCESS);
+ }
+ break;
+ }
+
+ // Requested data weren't in the cache (or were, but had expired),
+ // so now we proceed with the low-level data source lookup, and cache
+ // whatever we find.
const DataSrc* ds = zoneinfo.datasrc();
- Name* zonename = zoneinfo.zonename();
+ Name* zonename = zoneinfo.name();
if (ds == NULL) {
- task.flags = DataSrc::NO_SUCH_ZONE;
+ task.flags |= DataSrc::NO_SUCH_ZONE;
return (DataSrc::SUCCESS);
}
+ DataSrc::Result result;
switch (task.op) {
+ case QueryTask::SIMPLE_QUERY:
+ result = ds->findExactRRset(task.qname, task.qclass, task.qtype,
+ target, task.flags, zonename);
+
+ if (result != DataSrc::SUCCESS) {
+ return (result);
+ }
+
+ if (task.qclass == RRClass::ANY()) {
+ // XXX: Currently, RRsetList::findRRset() doesn't handle
+ // ANY queries, and without that we can't cache the results,
+ // so we just return in that case.
+ return (result);
+ }
+
+ if (task.flags == 0) {
+ rrset = target.findRRset(task.qtype, task.qclass);
+ assert(rrset);
+ cache.cache(rrset, task.flags);
+ } else {
+ cache.ncache(task.qname, task.qclass, task.qtype, task.flags);
+ }
+
+ return (result);
+
case QueryTask::AUTH_QUERY:
- return (ds->findRRset(task.qname, task.qclass, task.qtype,
- target, task.flags, zonename));
-
- case QueryTask::SIMPLE_QUERY:
- return (ds->findExactRRset(task.qname, task.qclass, task.qtype,
- target, task.flags, zonename));
+ result = ds->findRRset(task.qname, task.qclass, task.qtype,
+ target, task.flags, zonename);
+
+ if (result != DataSrc::SUCCESS) {
+ return (result);
+ }
+
+ if (task.qclass == RRClass::ANY()) {
+ return (result);
+ }
+
+ if (task.qtype == RRType::ANY()) {
+ BOOST_FOREACH(RRsetPtr rr, target) {
+ cache.cache(rr, task.flags);
+ }
+ } else if (task.flags == 0) {
+ if (task.qtype != RRType::CNAME()) {
+ cache.ncache(task.qname, task.qclass, RRType::CNAME(),
+ task.flags);
+ }
+ rrset = target.findRRset(task.qtype, task.qclass);
+ assert(rrset);
+ cache.cache(rrset, task.flags);
+ } else if ((task.flags & DataSrc::CNAME_FOUND) != 0) {
+ cache.ncache(task.qname, task.qclass, task.qtype, task.flags);
+ rrset = target.findRRset(RRType::CNAME(), task.qclass);
+ assert(rrset);
+ cache.cache(rrset, task.flags);
+ } else {
+ cache.ncache(task.qname, task.qclass, task.qtype, task.flags);
+ }
+
+ return (result);
case QueryTask::GLUE_QUERY:
case QueryTask::NOGLUE_QUERY:
- return (ds->findAddrs(task.qname, task.qclass, target,
- task.flags, zonename));
+ result = ds->findAddrs(task.qname, task.qclass, target,
+ task.flags, zonename);
+
+ if (result != DataSrc::SUCCESS) {
+ return (result);
+ }
+
+ if (task.qclass == RRClass::ANY()) {
+ return (result);
+ }
+
+ rrset = target.findRRset(RRType::A(), task.qclass);
+ if (rrset) {
+ cache.cache(rrset, task.flags);
+ } else {
+ cache.ncache(task.qname, task.qclass, RRType::A(), task.flags);
+ }
+
+ rrset = target.findRRset(RRType::AAAA(), task.qclass);
+ if (rrset) {
+ cache.cache(rrset, task.flags);
+ } else {
+ cache.ncache(task.qname, task.qclass, RRType::AAAA(), task.flags);
+ }
+
+ return (result);
case QueryTask::REF_QUERY:
- return (ds->findReferral(task.qname, task.qclass, target,
- task.flags, zonename));
+ result = ds->findReferral(task.qname, task.qclass, target,
+ task.flags, zonename);
+
+ if (result != DataSrc::SUCCESS) {
+ return (result);
+ }
+
+ if (task.qclass == RRClass::ANY()) {
+ return (result);
+ }
+
+ rrset = target.findRRset(RRType::NS(), task.qclass);
+ if (rrset) {
+ cache.cache(rrset, task.flags);
+ } else {
+ cache.ncache(task.qname, task.qclass, RRType::NS(), task.flags);
+ }
+ rrset = target.findRRset(RRType::DS(), task.qclass);
+ if (rrset) {
+ cache.cache(rrset, task.flags);
+ } else {
+ cache.ncache(task.qname, task.qclass, RRType::DS(), task.flags);
+ }
+ rrset = target.findRRset(RRType::DNAME(), task.qclass);
+ if (rrset) {
+ cache.cache(rrset, task.flags);
+ } else {
+ cache.ncache(task.qname, task.qclass, RRType::DNAME(), task.flags);
+ }
+
+ return (result);
}
// Not reached
@@ -209,7 +486,7 @@
// referrals.
inline bool
hasDelegation(Query& q, QueryTaskPtr task, NameMatch& zoneinfo) {
- Name* zonename = zoneinfo.zonename();
+ Name* zonename = zoneinfo.name();
if (zonename == NULL) {
if (task->state == QueryTask::GETANSWER) {
q.message().setRcode(Rcode::REFUSED());
@@ -277,7 +554,7 @@
Message& m = q.message();
RRsetList soa;
- Name* zonename = zoneinfo.zonename();
+ Name* zonename = zoneinfo.name();
QueryTask newtask(q, *zonename, RRType::SOA(), QueryTask::SIMPLE_QUERY);
RETERR(doQueryTask(newtask, zoneinfo, soa));
if (newtask.flags != 0) {
@@ -307,7 +584,7 @@
inline DataSrc::Result
getNsec3(Query& q, NameMatch& zoneinfo, string& hash, RRsetPtr& target) {
const DataSrc* ds = zoneinfo.datasrc();
- Name* zonename = zoneinfo.zonename();
+ Name* zonename = zoneinfo.name();
if (ds == NULL) {
q.message().setRcode(Rcode::SERVFAIL());
@@ -326,7 +603,7 @@
DataSrc::Result result;
RRsetList nsec3param;
- Name* zonename = zoneinfo.zonename();
+ Name* zonename = zoneinfo.name();
QueryTask newtask(q, *zonename, RRType::NSEC3PARAM(),
QueryTask::SIMPLE_QUERY);
result = doQueryTask(newtask, zoneinfo, nsec3param);
@@ -358,7 +635,7 @@
inline DataSrc::Result
proveNX(Query& q, QueryTaskPtr task, NameMatch& zoneinfo, const bool wildcard) {
Message& m = q.message();
- Name* zonename = zoneinfo.zonename();
+ Name* zonename = zoneinfo.name();
ConstNsec3ParamPtr nsec3 = getNsec3Param(q, zoneinfo);
if (nsec3 != NULL) {
@@ -452,7 +729,7 @@
return (DataSrc::SUCCESS);
}
- Name* zonename = zoneinfo.zonename();
+ Name* zonename = zoneinfo.name();
const int nlen = task->qname.getLabelCount();
const int diff = nlen - zonename->getLabelCount();
if (diff < 1) {
@@ -594,7 +871,7 @@
// Query found a referral; let's find out if that was expected--
// i.e., if an NS was at the zone apex, or if we were querying
// specifically for, and found, a DS, NSEC, or DNAME record.
- Name* zonename = zoneinfo.zonename();
+ Name* zonename = zoneinfo.name();
if ((task->flags & REFERRAL) != 0 &&
(zonename->getLabelCount() == task->qname.getLabelCount() ||
((task->qtype == RRType::NSEC() ||
Modified: branches/trac192/src/lib/datasrc/data_source.h
==============================================================================
--- branches/trac192/src/lib/datasrc/data_source.h (original)
+++ branches/trac192/src/lib/datasrc/data_source.h Sat May 29 02:56:27 2010
@@ -326,7 +326,7 @@
const isc::dns::RRClass& qclass() const { return (qclass_); }
const isc::dns::RRType& qtype() const { return (qtype_); }
- isc::dns::Name* zonename() {
+ isc::dns::Name* name() {
if (!closest_name_) {
top_source_->findClosestEnclosure(*this);
}
Modified: branches/trac192/src/lib/datasrc/query.cc
==============================================================================
--- branches/trac192/src/lib/datasrc/query.cc (original)
+++ branches/trac192/src/lib/datasrc/query.cc Sat May 29 02:56:27 2010
@@ -88,6 +88,14 @@
QueryTask::~QueryTask() {}
+// Initialize the static query cache, used by all instances of Query.
+//
+// NOTE: This object is guaranteed by the C++ specification to be
+// constructed before main() runs, but not necessarily before any
+// global variable's constructor. For safety, it should never be
+// accessed by any constructor, not even Query::Query().
+HotCache Query::cache(0);
+
Query::Query(Message& m, bool dnssec) :
status_(PENDING), qname_(NULL), qclass_(NULL), qtype_(NULL),
message_(&m), want_additional_(true), want_dnssec_(dnssec)
Modified: branches/trac192/src/lib/datasrc/query.h
==============================================================================
--- branches/trac192/src/lib/datasrc/query.h (original)
+++ branches/trac192/src/lib/datasrc/query.h Sat May 29 02:56:27 2010
@@ -19,6 +19,7 @@
#include <boost/shared_ptr.hpp>
+#include <datasrc/cache.h>
#include <datasrc/data_source.h>
#include <dns/name.h>
@@ -217,6 +218,10 @@
void setDatasrc(DataSrc* ds) { datasrc_ = ds; }
DataSrc* datasrc() const { return datasrc_; }
+ // Query cache. This is static; the same cache will be
+ // used by all instances of Query.
+ static HotCache cache;
+
private:
Status status_;
Modified: branches/trac192/src/lib/datasrc/tests/cache_unittest.cc
==============================================================================
--- branches/trac192/src/lib/datasrc/tests/cache_unittest.cc (original)
+++ branches/trac192/src/lib/datasrc/tests/cache_unittest.cc Sat May 29 02:56:27 2010
@@ -57,9 +57,9 @@
cache.setSlots(5);
- cache.cache(a, 30);
- cache.cache(b, 30);
- cache.cache(c, 30);
+ cache.cache(a, 0, 30);
+ cache.cache(b, 0, 30);
+ cache.cache(c, 0, 30);
}
Name test_name;
@@ -79,11 +79,12 @@
RRsetPtr aaaa(new RRset(Name("foo"), RRClass::IN(), RRType::AAAA(),
RRTTL(0)));
aaaa->addRdata(in::AAAA("001:4f8:3:bb::5"));
- cache.cache(aaaa, (time_t) 4);
+ cache.cache(aaaa, 0, (time_t) 4);
EXPECT_EQ(4, cache.getCount());
- RRsetPtr r = cache.retrieve(Name("foo"), RRClass::IN(), RRType::AAAA());
+ RRsetPtr r = cache.retrieve(Name("foo"), RRClass::IN(),
+ RRType::AAAA())->getRRset();
EXPECT_EQ(aaaa, r);
}
@@ -93,37 +94,39 @@
// Test repeatedly to ensure that all records remain accessible
// even after being promoted to the top of the cache
- r = cache.retrieve(test_name, RRClass::IN(), RRType::A());
+ r = cache.retrieve(test_name, RRClass::IN(), RRType::A())->getRRset();
EXPECT_EQ(test_name, r->getName());
EXPECT_EQ(RRClass::IN(), r->getClass());
EXPECT_EQ(RRType::A(), r->getType());
- r = cache.retrieve(test_nsname, RRClass::IN(), RRType::NS());
+ r = cache.retrieve(test_nsname, RRClass::IN(),
+ RRType::NS())->getRRset();
EXPECT_EQ(test_nsname, r->getName());
EXPECT_EQ(RRClass::IN(), r->getClass());
EXPECT_EQ(RRType::NS(), r->getType());
- r = cache.retrieve(test_ch, RRClass::CH(), RRType::TXT());
+ r = cache.retrieve(test_ch, RRClass::CH(), RRType::TXT())->getRRset();
EXPECT_EQ(test_ch, r->getName());
EXPECT_EQ(RRClass::CH(), r->getClass());
EXPECT_EQ(RRType::TXT(), r->getType());
- r = cache.retrieve(test_nsname, RRClass::IN(), RRType::NS());
+ r = cache.retrieve(test_nsname, RRClass::IN(),
+ RRType::NS())->getRRset();
EXPECT_EQ(test_nsname, r->getName());
EXPECT_EQ(RRClass::IN(), r->getClass());
EXPECT_EQ(RRType::NS(), r->getType());
- r = cache.retrieve(test_ch, RRClass::CH(), RRType::TXT());
+ r = cache.retrieve(test_ch, RRClass::CH(), RRType::TXT())->getRRset();
EXPECT_EQ(test_ch, r->getName());
EXPECT_EQ(RRClass::CH(), r->getClass());
EXPECT_EQ(RRType::TXT(), r->getType());
- r = cache.retrieve(test_name, RRClass::IN(), RRType::A());
+ r = cache.retrieve(test_name, RRClass::IN(), RRType::A())->getRRset();
EXPECT_EQ(test_name, r->getName());
EXPECT_EQ(RRClass::IN(), r->getClass());
EXPECT_EQ(RRType::A(), r->getType());
- r = cache.retrieve(test_name, RRClass::IN(), RRType::A());
+ r = cache.retrieve(test_name, RRClass::IN(), RRType::A())->getRRset();
EXPECT_EQ(test_name, r->getName());
EXPECT_EQ(RRClass::IN(), r->getClass());
EXPECT_EQ(RRType::A(), r->getType());
@@ -131,31 +134,33 @@
TEST_F(CacheTest, retrieveFail)
{
- RRsetPtr r;
-
- r = cache.retrieve(Name("fake"), RRClass::IN(), RRType::A());
- EXPECT_FALSE(r);
-
- r = cache.retrieve(test_name, RRClass::CH(), RRType::A());
- EXPECT_FALSE(r);
-
- r = cache.retrieve(test_name, RRClass::IN(), RRType::DNSKEY());
- EXPECT_FALSE(r);
+ CacheNodePtr c;
+
+ c = cache.retrieve(Name("fake"), RRClass::IN(), RRType::A());
+ EXPECT_FALSE(c);
+
+ c = cache.retrieve(test_name, RRClass::CH(), RRType::A());
+ EXPECT_FALSE(c);
+
+ c = cache.retrieve(test_name, RRClass::IN(), RRType::DNSKEY());
+ EXPECT_FALSE(c);
}
TEST_F(CacheTest, expire)
{
+
// Insert "foo" with a duration of 2 seconds; sleep 3. The
// record should not be returned from the cache even though it's
// at the top of the cache.
RRsetPtr aaaa(new RRset(Name("foo"), RRClass::IN(), RRType::AAAA(),
RRTTL(0)));
aaaa->addRdata(in::AAAA("001:4f8:3:bb::5"));
- cache.cache(aaaa, (time_t) 2);
+ cache.cache(aaaa, 0, (time_t) 2);
sleep(3);
- RRsetPtr r = cache.retrieve(Name("foo"), RRClass::IN(), RRType::AAAA());
- EXPECT_FALSE(r);
+ CacheNodePtr c = cache.retrieve(Name("foo"), RRClass::IN(),
+ RRType::AAAA());
+ EXPECT_FALSE(c);
};
TEST_F(CacheTest, LRU)
@@ -163,38 +168,39 @@
// Retrieve a record, cache four new records; with five slots
// in the LRU queue this should remove all the previous records
// except the last one retreived.
- RRsetPtr r = cache.retrieve(test_nsname, RRClass::IN(), RRType::NS());
+ RRsetPtr r = cache.retrieve(test_nsname, RRClass::IN(),
+ RRType::NS())->getRRset();
EXPECT_EQ(3, cache.getCount());
RRsetPtr one(new RRset(Name("one"), RRClass::IN(), RRType::TXT(),
RRTTL(0)));
one->addRdata(generic::TXT("one"));
- cache.cache(one, (time_t) 30);
+ cache.cache(one, 0, (time_t) 30);
EXPECT_EQ(4, cache.getCount());
RRsetPtr two(new RRset(Name("two"), RRClass::IN(), RRType::TXT(),
RRTTL(0)));
two->addRdata(generic::TXT("two"));
- cache.cache(two, (time_t) 30);
+ cache.cache(two, 0, (time_t) 30);
EXPECT_EQ(5, cache.getCount());
RRsetPtr three(new RRset(Name("three"), RRClass::IN(), RRType::TXT(),
RRTTL(0)));
three->addRdata(generic::TXT("three"));
- cache.cache(three, (time_t) 30);
+ cache.cache(three, 0, (time_t) 30);
EXPECT_EQ(5, cache.getCount());
RRsetPtr four(new RRset(Name("four"), RRClass::IN(), RRType::TXT(),
RRTTL(0)));
four->addRdata(generic::TXT("four"));
- cache.cache(four, (time_t) 30);
+ cache.cache(four, 0, (time_t) 30);
EXPECT_EQ(5, cache.getCount());
- r = cache.retrieve(test_name, RRClass::IN(), RRType::A());
- EXPECT_FALSE(r);
-
- r = cache.retrieve(test_ch, RRClass::CH(), RRType::TXT());
- EXPECT_FALSE(r);
-}
-
-}
+ CacheNodePtr c = cache.retrieve(test_name, RRClass::IN(), RRType::A());
+ EXPECT_FALSE(c);
+
+ c = cache.retrieve(test_ch, RRClass::CH(), RRType::TXT());
+ EXPECT_FALSE(c);
+}
+
+}
Modified: branches/trac192/src/lib/datasrc/tests/sqlite3_unittest.cc
==============================================================================
--- branches/trac192/src/lib/datasrc/tests/sqlite3_unittest.cc (original)
+++ branches/trac192/src/lib/datasrc/tests/sqlite3_unittest.cc Sat May 29 02:56:27 2010
@@ -375,7 +375,7 @@
EXPECT_EQ(DataSrc::SUCCESS, data_source.init(SQLITE_DBFILE_EXAMPLE2));
NameMatch name_match(&data_source, www_name, rrclass);
- EXPECT_EQ(NULL, name_match.zonename());
+ EXPECT_EQ(NULL, name_match.name());
EXPECT_EQ(NULL, name_match.datasrc());
}
@@ -413,7 +413,7 @@
TEST_F(Sqlite3DataSourceTest, findClosestEnclosure) {
NameMatch name_match(&data_source, www_name, rrclass);
- EXPECT_EQ(zone_name, *name_match.zonename());
+ EXPECT_EQ(zone_name, *name_match.name());
EXPECT_EQ(&data_source, name_match.datasrc());
}
@@ -422,7 +422,7 @@
EXPECT_EQ(DataSrc::SUCCESS, data_source.init(SQLITE_DBFILE_EXAMPLE_ROOT));
NameMatch name_match(&data_source, Name("org."), rrclass);
- EXPECT_EQ(Name("."), *name_match.zonename());
+ EXPECT_EQ(Name("."), *name_match.name());
EXPECT_EQ(&data_source, name_match.datasrc());
}
@@ -430,19 +430,19 @@
// The search name exists both in the parent and child zones, but
// child has a better match.
NameMatch name_match(&data_source, child_name, rrclass);
- EXPECT_EQ(child_name, *name_match.zonename());
+ EXPECT_EQ(child_name, *name_match.name());
EXPECT_EQ(&data_source, name_match.datasrc());
}
TEST_F(Sqlite3DataSourceTest, findClosestEnclosureNoMatch) {
NameMatch name_match(&data_source, nomatch_name, rrclass);
- EXPECT_EQ(NULL, name_match.zonename());
+ EXPECT_EQ(NULL, name_match.name());
EXPECT_EQ(NULL, name_match.datasrc());
}
TEST_F(Sqlite3DataSourceTest, findClosestClassMismatch) {
NameMatch name_match(&data_source, www_name, rrclass_notmatch);
- EXPECT_EQ(NULL, name_match.zonename());
+ EXPECT_EQ(NULL, name_match.name());
EXPECT_EQ(NULL, name_match.datasrc());
}
@@ -450,7 +450,7 @@
// the class exactly matches.
TEST_F(Sqlite3DataSourceTest, findClosestClassAny) {
NameMatch name_match(&data_source, www_name, RRClass::ANY());
- EXPECT_EQ(zone_name, *name_match.zonename());
+ EXPECT_EQ(zone_name, *name_match.name());
EXPECT_EQ(&data_source, name_match.datasrc());
}
Modified: branches/trac192/src/lib/datasrc/tests/static_unittest.cc
==============================================================================
--- branches/trac192/src/lib/datasrc/tests/static_unittest.cc (original)
+++ branches/trac192/src/lib/datasrc/tests/static_unittest.cc Sat May 29 02:56:27 2010
@@ -197,45 +197,45 @@
TEST_F(StaticDataSourceTest, findClosestEnclosureForVersion) {
NameMatch name_match(&data_source, version_name, rrclass);
- EXPECT_EQ(version_name, *name_match.zonename());
+ EXPECT_EQ(version_name, *name_match.name());
EXPECT_EQ(&data_source, name_match.datasrc());
}
// Class Any query should result in the same answer.
TEST_F(StaticDataSourceTest, findClosestEnclosureForVersionClassAny) {
NameMatch name_match(&data_source, version_name, RRClass::ANY());
- EXPECT_EQ(version_name, *name_match.zonename());
+ EXPECT_EQ(version_name, *name_match.name());
EXPECT_EQ(&data_source, name_match.datasrc());
}
// If class doesn't match the lookup should fail.
TEST_F(StaticDataSourceTest, findClosestEnclosureForVersionClassMismatch) {
NameMatch name_match(&data_source, version_name, RRClass::IN());
- EXPECT_EQ(NULL, name_match.zonename());
+ EXPECT_EQ(NULL, name_match.name());
EXPECT_EQ(NULL, name_match.datasrc());
}
TEST_F(StaticDataSourceTest, findClosestEnclosureForVersionPartial) {
NameMatch name_match(&data_source, Name("foo").concatenate(version_name), rrclass);
- EXPECT_EQ(version_name, *name_match.zonename());
+ EXPECT_EQ(version_name, *name_match.name());
EXPECT_EQ(&data_source, name_match.datasrc());
}
TEST_F(StaticDataSourceTest, findClosestEnclosureForAuthors) {
NameMatch name_match(&data_source, authors_name, rrclass);
- EXPECT_EQ(authors_name, *name_match.zonename());
+ EXPECT_EQ(authors_name, *name_match.name());
EXPECT_EQ(&data_source, name_match.datasrc());
}
TEST_F(StaticDataSourceTest, findClosestEnclosureForAuthorsPartial) {
NameMatch name_match(&data_source, Name("foo").concatenate(authors_name), rrclass);
- EXPECT_EQ(authors_name, *name_match.zonename());
+ EXPECT_EQ(authors_name, *name_match.name());
EXPECT_EQ(&data_source, name_match.datasrc());
}
TEST_F(StaticDataSourceTest, findClosestEnclosureNoMatch) {
NameMatch name_match(&data_source, nomatch_name, rrclass);
- EXPECT_EQ(NULL, name_match.zonename());
+ EXPECT_EQ(NULL, name_match.name());
EXPECT_EQ(NULL, name_match.datasrc());
}
Modified: branches/trac192/src/lib/dns/rrsetlist.cc
==============================================================================
--- branches/trac192/src/lib/dns/rrsetlist.cc (original)
+++ branches/trac192/src/lib/dns/rrsetlist.cc Sat May 29 02:56:27 2010
@@ -41,6 +41,14 @@
rrsets_.push_back(rrsetptr);
}
+void
+RRsetList::append(RRsetList& source)
+{
+ BOOST_FOREACH(RRsetPtr rrset, source) {
+ addRRset(rrset);
+ }
+}
+
RRsetPtr
RRsetList::findRRset(const RRType& rrtype, const RRClass& rrclass)
{
Modified: branches/trac192/src/lib/dns/rrsetlist.h
==============================================================================
--- branches/trac192/src/lib/dns/rrsetlist.h (original)
+++ branches/trac192/src/lib/dns/rrsetlist.h Sat May 29 02:56:27 2010
@@ -82,6 +82,7 @@
public:
RRsetList() {}
void addRRset(RRsetPtr new_rrsetptr);
+ void append(RRsetList& source);
RRsetPtr findRRset(const RRType& rrtype, const RRClass& rrclass);
typedef RRsetListIterator<std::vector<RRsetPtr>::iterator,
Modified: branches/trac192/src/lib/dns/tests/rrsetlist_unittest.cc
==============================================================================
--- branches/trac192/src/lib/dns/tests/rrsetlist_unittest.cc (original)
+++ branches/trac192/src/lib/dns/tests/rrsetlist_unittest.cc Sat May 29 02:56:27 2010
@@ -48,6 +48,7 @@
const generic::SOA rdata_soa(Name("ns.example.com"), Name("root.example.com"),
2010012601, 3600, 300, 3600000, 1200);
const generic::CNAME rdata_cname("target.example.com");
+const generic::DNAME rdata_dname("dtarget.example.com");
void
RRsetListTest::setupList(RRsetList& list) {
@@ -84,6 +85,24 @@
RRsetList list;
setupList(list);
EXPECT_EQ(list.size(), 5);
+}
+
+TEST_F(RRsetListTest, append) {
+ RRsetList list1;
+ setupList(list1);
+ RRsetList list2;
+ RRsetPtr dname(new RRset(Name("example.com"), RRClass::IN(),
+ RRType::DNAME(), example_ttl));
+ dname->addRdata(rdata_dname);
+ list2.addRRset(dname);
+ list1.append(list2);
+ EXPECT_EQ(list2.size(), 1);
+ EXPECT_EQ(list1.size(), 6);
+
+ RRsetPtr rrset = list1.findRRset(RRType::DNAME(), RRClass::IN());
+ EXPECT_EQ(RRType::DNAME(), rrset->getType());
+
+ EXPECT_THROW(list1.append(list2), DuplicateRRset);
}
TEST_F(RRsetListTest, extraRRset) {
More information about the bind10-changes
mailing list