From: Paul Selkirk Date: Mon, 8 Apr 2013 17:42:38 +0000 (-0400) Subject: [2521] add MasterLexer constructor for RRSIG X-Git-Tag: bind10-1.2.0beta1-release~473^2~23 X-Git-Url: http://git.ipfire.org/gitweb.cgi?a=commitdiff_plain;h=fdb992f0a2699cdad3bcaef79c2ca35f8e700c16;p=thirdparty%2Fkea.git [2521] add MasterLexer constructor for RRSIG --- diff --git a/src/lib/dns/gen-rdatacode.py.in b/src/lib/dns/gen-rdatacode.py.in index 827fe9f0f0..28644570e4 100755 --- a/src/lib/dns/gen-rdatacode.py.in +++ b/src/lib/dns/gen-rdatacode.py.in @@ -1,6 +1,6 @@ #!@PYTHON@ -# Copyright (C) 2010 Internet Systems Consortium, Inc. ("ISC") +# Copyright (C) 2010-2013 Internet Systems Consortium, Inc. ("ISC") # # Permission to use, copy, modify, and/or distribute this software for any # purpose with or without fee is hereby granted, provided that the above @@ -46,6 +46,7 @@ new_rdata_factory_users = [('a', 'in'), ('nsec', 'generic'), ('opt', 'generic'), ('ptr', 'generic'), + ('rrsig', 'generic'), ('soa', 'generic'), ('spf', 'generic'), ('srv', 'in'), diff --git a/src/lib/dns/rdata/generic/rrsig_46.cc b/src/lib/dns/rdata/generic/rrsig_46.cc index e0137b9fc6..86d666312f 100644 --- a/src/lib/dns/rdata/generic/rrsig_46.cc +++ b/src/lib/dns/rdata/generic/rrsig_46.cc @@ -1,4 +1,4 @@ -// Copyright (C) 2010 Internet Systems Consortium, Inc. ("ISC") +// Copyright (C) 2010-2013 Internet Systems Consortium, Inc. ("ISC") // // Permission to use, copy, modify, and/or distribute this software for any // purpose with or without fee is hereby granted, provided that the above @@ -29,6 +29,7 @@ #include #include #include +#include #include #include @@ -36,6 +37,7 @@ using namespace std; using namespace isc::util; using namespace isc::util::encode; +using isc::dns::rdata::generic::detail::createNameFromLexer; // BEGIN_ISC_NAMESPACE // BEGIN_RDATA_NAMESPACE @@ -72,38 +74,106 @@ struct RRSIGImpl { const vector signature_; }; -RRSIG::RRSIG(const std::string& rrsig_str) : - impl_(NULL) +namespace { +// helper function for string and lexer constructors +RRSIGImpl* createFromLexer(MasterLexer& lexer, const Name* origin) { - istringstream iss(rrsig_str); - string covered_txt, signer_txt, expire_txt, inception_txt; - unsigned int algorithm, labels; + string covered_txt, expire_txt, inception_txt, signature_txt; + unsigned int algorithm, labels, tag; uint32_t originalttl; - uint16_t tag; - stringbuf signaturebuf; - iss >> covered_txt >> algorithm >> labels >> originalttl - >> expire_txt >> inception_txt >> tag >> signer_txt - >> &signaturebuf; - if (iss.bad() || iss.fail()) { - isc_throw(InvalidRdataText, "Invalid RRSIG text"); - } + covered_txt = lexer.getNextToken(MasterToken::STRING).getString(); + algorithm = lexer.getNextToken(MasterToken::NUMBER).getNumber(); + labels = lexer.getNextToken(MasterToken::NUMBER).getNumber(); + originalttl = RRTTL(lexer.getNextToken(MasterToken::STRING).getString()).getValue(); + expire_txt = lexer.getNextToken(MasterToken::STRING).getString(); + inception_txt = lexer.getNextToken(MasterToken::STRING).getString(); + tag = lexer.getNextToken(MasterToken::NUMBER).getNumber(); + Name signer = createNameFromLexer(lexer, origin); + signature_txt = lexer.getNextToken(MasterToken::STRING).getString(); + if (algorithm > 0xff) { isc_throw(InvalidRdataText, "RRSIG algorithm out of range"); } if (labels > 0xff) { isc_throw(InvalidRdataText, "RRSIG labels out of range"); } + if (tag > 0xffff) { + isc_throw(InvalidRdataText, "RRSIG key tag out of range"); + } const uint32_t timeexpire = timeFromText32(expire_txt); const uint32_t timeinception = timeFromText32(inception_txt); vector signature; - decodeBase64(signaturebuf.str(), signature); + decodeBase64(signature_txt, signature); - impl_ = new RRSIGImpl(RRType(covered_txt), algorithm, labels, - originalttl, timeexpire, timeinception, tag, - Name(signer_txt), signature); + return new RRSIGImpl(RRType(covered_txt), algorithm, labels, + originalttl, timeexpire, timeinception, + static_cast(tag), signer, signature); +} +} + +/// \brief Constructor from string. +/// +/// The given string must represent a valid RRSIG RDATA. There can be extra +/// space characters at the beginning or end of the text (which are simply +/// ignored), but other extra text, including a new line, will make the +/// construction fail with an exception. +/// +/// The Signer's Name must be absolute since there's no parameter that +/// specifies the origin name; if this is not absolute, \c MissingNameOrigin +/// exception will be thrown. This must not be represented as a quoted +/// string. +/// +/// See the construction that takes \c MasterLexer for other fields. +/// +/// \throw Others Exception from the Name and RRTTL constructors. +/// \throw InvalidRdataText Other general syntax errors. +RRSIG::RRSIG(const std::string& rrsig_str) : + impl_(NULL) +{ + try { + istringstream iss(rrsig_str); + MasterLexer lexer; + lexer.pushSource(iss); + + impl_ = createFromLexer(lexer, NULL); + + if (lexer.getNextToken().getType() != MasterToken::END_OF_FILE) { + isc_throw(InvalidRdataText, "extra input text for RRSIG: " + << rrsig_str); + } + } catch (const MasterLexer::LexerError& ex) { + isc_throw(InvalidRdataText, "Failed to construct RRSIG from '" << + rrsig_str << "': " << ex.what()); + } +} + +/// \brief Constructor with a context of MasterLexer. +/// +/// The \c lexer should point to the beginning of valid textual representation +/// of an RRSIG RDATA. The Signer's Name fields can be non absolute if \c +/// origin is non NULL, in which case \c origin is used to make it absolute. +/// This must not be represented as a quoted string. +/// +/// The Original TTL field can be either a valid decimal representation of an +/// unsigned 32-bit integer or other valid textual representation of \c RRTTL +/// such as "1H" (which means 3600). +/// +/// \throw MasterLexer::LexerError General parsing error such as missing field. +/// \throw Other Exceptions from the Name and RRTTL constructors if +/// construction of textual fields as these objects fail. +/// +/// \param lexer A \c MasterLexer object parsing a master file for the +/// RDATA to be created +/// \param origin If non NULL, specifies the origin of Signer's Name when +/// it is non absolute. +RRSIG::RRSIG(MasterLexer& lexer, const Name* origin, + MasterLoader::Options, MasterLoaderCallbacks&) : + impl_(NULL) +{ + impl_ = createFromLexer(lexer, origin); } RRSIG::RRSIG(InputBuffer& buffer, size_t rdata_len) { diff --git a/src/lib/dns/tests/message_unittest.cc b/src/lib/dns/tests/message_unittest.cc index 835aa4825e..8aaebaa183 100644 --- a/src/lib/dns/tests/message_unittest.cc +++ b/src/lib/dns/tests/message_unittest.cc @@ -1,4 +1,4 @@ -// Copyright (C) 2010 Internet Systems Consortium, Inc. ("ISC") +// Copyright (C) 2010-2013 Internet Systems Consortium, Inc. ("ISC") // // Permission to use, copy, modify, and/or distribute this software for any // purpose with or without fee is hereby granted, provided that the above @@ -98,7 +98,7 @@ protected: rrset_rrsig = RRsetPtr(new RRset(test_name, RRClass::IN(), RRType::RRSIG(), RRTTL(3600))); rrset_rrsig->addRdata(generic::RRSIG("AAAA 5 3 7200 20100322084538 " - "20100220084538 1 example.com " + "20100220084538 1 example.com. " "FAKEFAKEFAKEFAKE")); rrset_aaaa->addRRsig(rrset_rrsig); } diff --git a/src/lib/dns/tests/rdata_rrsig_unittest.cc b/src/lib/dns/tests/rdata_rrsig_unittest.cc index d758ff390b..b521a94ad1 100644 --- a/src/lib/dns/tests/rdata_rrsig_unittest.cc +++ b/src/lib/dns/tests/rdata_rrsig_unittest.cc @@ -1,4 +1,4 @@ -// Copyright (C) 2010 Internet Systems Consortium, Inc. ("ISC") +// Copyright (C) 2010-2013 Internet Systems Consortium, Inc. ("ISC") // // Permission to use, copy, modify, and/or distribute this software for any // purpose with or without fee is hereby granted, provided that the above @@ -56,42 +56,49 @@ TEST_F(Rdata_RRSIG_Test, fromText) { } TEST_F(Rdata_RRSIG_Test, badText) { + // missing fields EXPECT_THROW(const generic::RRSIG sig("SPORK"), InvalidRdataText); + // bad algorithm EXPECT_THROW(const generic::RRSIG sig("A 555 4 43200 " "20100223214617 20100222214617 8496 isc.org. " "evxhlGx13mpKLVkKsjpGzycS5twtIoxOmlN14w9t5AgzGBmz" "diGdLIrFabqr72af2rUq+UDBKMWXujwZTZUTws32sVldDPk/" "NbuacJM25fQXfv5mO3Af7TOoow3AjMaVG9icjCW0V55WcWQU" "f49t+sXKPzbipN9g+s1ZPiIyofc="), InvalidRdataText); + // bad labels EXPECT_THROW(const generic::RRSIG sig("A 5 4444 43200 " "20100223214617 20100222214617 8496 isc.org. " "evxhlGx13mpKLVkKsjpGzycS5twtIoxOmlN14w9t5AgzGBmz" "diGdLIrFabqr72af2rUq+UDBKMWXujwZTZUTws32sVldDPk/" "NbuacJM25fQXfv5mO3Af7TOoow3AjMaVG9icjCW0V55WcWQU" "f49t+sXKPzbipN9g+s1ZPiIyofc="), InvalidRdataText); + // bad original ttl EXPECT_THROW(const generic::RRSIG sig("A 5 4 999999999999 " "20100223214617 20100222214617 8496 isc.org. " "evxhlGx13mpKLVkKsjpGzycS5twtIoxOmlN14w9t5AgzGBmz" "diGdLIrFabqr72af2rUq+UDBKMWXujwZTZUTws32sVldDPk/" "NbuacJM25fQXfv5mO3Af7TOoow3AjMaVG9icjCW0V55WcWQU" - "f49t+sXKPzbipN9g+s1ZPiIyofc="), InvalidRdataText); + "f49t+sXKPzbipN9g+s1ZPiIyofc="), InvalidRRTTL); + // bad signature expiration, inception EXPECT_THROW(const generic::RRSIG sig("A 5 4 43200 " "20100223 20100227 8496 isc.org. " "evxhlGx13mpKLVkKsjpGzycS5twtIoxOmlN14w9t5AgzGBmz" "diGdLIrFabqr72af2rUq+UDBKMWXujwZTZUTws32sVldDPk/" "NbuacJM25fQXfv5mO3Af7TOoow3AjMaVG9icjCW0V55WcWQU" "f49t+sXKPzbipN9g+s1ZPiIyofc="), InvalidTime); + // bad key tag EXPECT_THROW(const generic::RRSIG sig("A 5 4 43200 " "20100223214617 20100222214617 999999 isc.org. " "evxhlGx13mpKLVkKsjpGzycS5twtIoxOmlN14w9t5AgzGBmz" "diGdLIrFabqr72af2rUq+UDBKMWXujwZTZUTws32sVldDPk/" "NbuacJM25fQXfv5mO3Af7TOoow3AjMaVG9icjCW0V55WcWQU" "f49t+sXKPzbipN9g+s1ZPiIyofc="), InvalidRdataText); + // bad signature EXPECT_THROW(const generic::RRSIG sig( "A 5 4 43200 " "20100223214617 20100222214617 8496 isc.org. " "EEeeeeeeEEEeeeeeeGaaahAAAAAAAAHHHHHHHHHHH!="), - BadValue); // bad base64 input + BadValue); } TEST_F(Rdata_RRSIG_Test, DISABLED_badText) { diff --git a/src/lib/dns/tests/rrcollator_unittest.cc b/src/lib/dns/tests/rrcollator_unittest.cc index e66f87c03a..f59c77c1f4 100644 --- a/src/lib/dns/tests/rrcollator_unittest.cc +++ b/src/lib/dns/tests/rrcollator_unittest.cc @@ -1,4 +1,4 @@ -// Copyright (C) 2012 Internet Systems Consortium, Inc. ("ISC") +// Copyright (C) 2012-2013 Internet Systems Consortium, Inc. ("ISC") // // Permission to use, copy, modify, and/or distribute this software for any // purpose with or without fee is hereby granted, provided that the above @@ -59,10 +59,10 @@ protected: txt_rdata_(createRdata(RRType::TXT(), rrclass_, "test")), sig_rdata1_(createRdata(RRType::RRSIG(), rrclass_, "A 5 3 3600 20000101000000 20000201000000 " - "12345 example.com. FAKE\n")), + "12345 example.com. FAKE ")), sig_rdata2_(createRdata(RRType::RRSIG(), rrclass_, "NS 5 3 3600 20000101000000 20000201000000 " - "12345 example.com. FAKE\n")) + "12345 example.com. FAKE ")) {} void checkRRset(const Name& expected_name, const RRClass& expected_class, diff --git a/src/lib/dns/tests/rrset_unittest.cc b/src/lib/dns/tests/rrset_unittest.cc index d16ce3c15b..a605caf62b 100644 --- a/src/lib/dns/tests/rrset_unittest.cc +++ b/src/lib/dns/tests/rrset_unittest.cc @@ -1,4 +1,4 @@ -// Copyright (C) 2010 Internet Systems Consortium, Inc. ("ISC") +// Copyright (C) 2010-2013 Internet Systems Consortium, Inc. ("ISC") // // Permission to use, copy, modify, and/or distribute this software for any // purpose with or without fee is hereby granted, provided that the above @@ -289,7 +289,7 @@ protected: rrset_rrsig = RRsetPtr(new RRset(test_name, RRClass::IN(), RRType::RRSIG(), RRTTL(3600))); rrset_rrsig->addRdata(generic::RRSIG("AAAA 5 3 7200 20100322084538 " - "20100220084538 1 example.com " + "20100220084538 1 example.com. " "FAKEFAKEFAKEFAKE")); rrset_aaaa->addRRsig(rrset_rrsig); }