Commit 0d1406f7 authored by JINMEI Tatuya's avatar JINMEI Tatuya
Browse files

[1570] supported the case of DS query at child. dsBelowDelegation now passed.

added a couple of more related tests.
parent 32d9c527
......@@ -283,6 +283,9 @@ Query::process() {
// https://lists.isc.org/mailman/htdig/bind10-dev/2010-December/001633.html
if (result.code != result::SUCCESS &&
result.code != result::PARTIALMATCH) {
if (qtype_ == RRType::DS() && processDSAtChild()) {
return;
}
response_.setHeaderFlag(Message::HEADERFLAG_AA, false);
response_.setRcode(Rcode::REFUSED());
return;
......@@ -436,5 +439,37 @@ Query::process() {
}
}
bool
Query::processDSAtChild() {
const DataSourceClient::FindResult zresult =
datasrc_client_.findZone(qname_);
if (zresult.code != result::SUCCESS) {
return (false);
}
// We are receiving a DS query at the child side of the owner name,
// where the DS isn't supposed to belong. We should return a "no data"
// response as described in Section 3.1.4.1 of RFC4035 and Section
// 2.2.1.1 of RFC 3658. find(DS) should result in NXRRSET, in which
// case (and if DNSSEC is required) we also add the proof for that,
// but even if find() returns an unexpected result, we don't bother.
// The important point in this case is to return SOA so that the resolver
// that happens to contact us can hunt for the appropriate parent zone
// by seeing the SOA.
response_.setHeaderFlag(Message::HEADERFLAG_AA);
response_.setRcode(Rcode::NOERROR());
addSOA(*zresult.zone_finder);
const ZoneFinder::FindResult ds_result =
zresult.zone_finder->find(qname_, RRType::DS(), dnssec_opt_);
if (ds_result.code == ZoneFinder::NXRRSET) {
if (dnssec_) {
addNXRRsetProof(*zresult.zone_finder, ds_result);
}
}
return (true);
}
}
}
......@@ -178,6 +178,9 @@ private:
/// data for the query are to be found.
void addAuthAdditional(isc::datasrc::ZoneFinder& finder);
/// TBD
bool processDSAtChild();
public:
/// Constructor from query parameters.
///
......
......@@ -57,7 +57,6 @@ const char* const zone_ns_txt =
"example.com. 3600 IN NS glue.delegation.example.com.\n"
"example.com. 3600 IN NS noglue.example.com.\n"
"example.com. 3600 IN NS example.net.\n";
// TBD: CHECK IF IT IS REALLY USED
const char* const zone_ds_txt =
"example.com. 3600 IN DS 57855 5 1 "
"B6DCD485719ADCA18E5F3D48A2331627FDD3 636B\n";
......@@ -302,10 +301,20 @@ public:
// answers when DNSSEC is required.
void setNSEC3Flag(bool on) { use_nsec3_ = on; }
Name findPreviousName(const Name&) const {
virtual Name findPreviousName(const Name&) const {
isc_throw(isc::NotImplemented, "Mock doesn't support previous name");
}
// This method allows tests to insert new record in the middle of the test.
//
// \param record_txt textual RR representation of RR (such as soa_txt, etc)
void addRecord(const string& record_txt) {
stringstream record_stream;
record_stream << record_txt;
masterLoad(record_stream, origin_, rrclass_,
boost::bind(&MockZoneFinder::loadRRset, this, _1));
}
public:
// We allow the tests to use these for convenience
ConstRRsetPtr dname_rrset_; // could be used as an arbitrary bogus RRset
......@@ -1662,21 +1671,44 @@ TEST_F(QueryTest, dsAboveDelegation) {
getCommonRRSIGText("A")).c_str());
}
// This one checks a DS record at the apex is not returned even if it exists,
// as it is authoritative above the delegation and does not exist below it,
// This one checks a DS record at the apex is not returned, as it is
// authoritative above the delegation and does not exist below it,
// as described in RFC 4035, section 3.1.4.1. The example is inspired by the
// B.8. example from the RFC.
TEST_F(QueryTest, DISABLED_dsBelowDelegation) {
TEST_F(QueryTest, dsBelowDelegation) {
EXPECT_NO_THROW(Query(memory_client, Name("example.com"),
RRType::DS(), response, true).process());
responseCheck(response, Rcode::NOERROR(), AA_FLAG, 0, 4, 0, NULL,
(string(soa_txt) + string("example.com. 3600 IN RRSIG ") +
getCommonRRSIGText("SOA") + "\n" +
string(nsec_www_txt) + "\n" +
string("www.example.com. 3600 IN RRSIG ") +
getCommonRRSIGText("NSEC")).c_str(),
NULL, mock_finder->getOrigin());
string(nsec_apex_txt) + "\n" +
string("example.com. 3600 IN RRSIG ") +
getCommonRRSIGText("NSEC")).c_str(), NULL,
mock_finder->getOrigin());
}
// Similar to the previous case, but even more pathological: the DS somehow
// exists in the child zone. The Query module should still return SOA.
// In our implementation NSEC/NSEC3 isn't attached in this case.
TEST_F(QueryTest, dsBelowDelegationWithDS) {
mock_finder->addRecord(zone_ds_txt); // add the DS to the child's apex
EXPECT_NO_THROW(Query(memory_client, Name("example.com"),
RRType::DS(), response, true).process());
responseCheck(response, Rcode::NOERROR(), AA_FLAG, 0, 2, 0, NULL,
(string(soa_txt) + string("example.com. 3600 IN RRSIG ") +
getCommonRRSIGText("SOA")).c_str(), NULL,
mock_finder->getOrigin());
}
// DS query received at a completely irrelevant (neither parent nor child)
// server. It should just like the "noZone" test case, but DS query involves
// special processing, so we test it explicitly.
TEST_F(QueryTest, dsNoZone) {
Query(memory_client, Name("example"), RRType::DS(), response,
true).process();
responseCheck(response, Rcode::REFUSED(), 0, 0, 0, 0, NULL, NULL, NULL);
}
// The following are tentative tests until we really add tests for the
......
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment