security: improve pretty-printing of certificates
Change-Id: Ib81a39bab35f3537df086d47d185907daaa1f426
diff --git a/tests/unit/security/certificate.t.cpp b/tests/unit/security/certificate.t.cpp
index 63b29a6..d0633f0 100644
--- a/tests/unit/security/certificate.t.cpp
+++ b/tests/unit/security/certificate.t.cpp
@@ -22,6 +22,8 @@
*/
#include "ndn-cxx/security/certificate.hpp"
+#include "ndn-cxx/encoding/block-helpers.hpp"
+#include "ndn-cxx/util/io.hpp"
#include "tests/boost-test.hpp"
#include "tests/unit/clock-fixture.hpp"
@@ -145,12 +147,11 @@
BOOST_CHECK_EQUAL(certificate.getIdentity(), "/ndn/site1");
BOOST_CHECK_EQUAL(certificate.getIssuerId(), name::Component("0123"));
BOOST_CHECK_EQUAL(certificate.getKeyId(), name::Component("ksk-1416425377094"));
- BOOST_REQUIRE_EQUAL(certificate.getKeyLocator().has_value(), true);
- BOOST_CHECK_EQUAL(certificate.getKeyLocator()->getName(), "/ndn/site1/KEY/ksk-2516425377094");
+ BOOST_CHECK_EQUAL(certificate.getKeyLocator().value().getName(), "/ndn/site1/KEY/ksk-2516425377094");
BOOST_CHECK_EQUAL(boost::lexical_cast<std::string>(certificate.getValidityPeriod()),
"(20150814T223739, 20150818T223738)");
- BOOST_CHECK_THROW(certificate.getExtension(12345), ndn::Data::Error);
+ BOOST_CHECK_THROW(certificate.getExtension(12345), Data::Error);
BOOST_CHECK_NO_THROW(certificate.getPublicKey());
Data data(block);
@@ -171,12 +172,11 @@
BOOST_CHECK_EQUAL(certificate.getIdentity(), "/ndn/site1");
BOOST_CHECK_EQUAL(certificate.getIssuerId(), name::Component("0123"));
BOOST_CHECK_EQUAL(certificate.getKeyId(), name::Component("ksk-1416425377094"));
- BOOST_REQUIRE_EQUAL(certificate.getKeyLocator().has_value(), true);
- BOOST_CHECK_EQUAL(certificate.getKeyLocator()->getName(), "/ndn/site1/KEY/ksk-2516425377094");
+ BOOST_CHECK_EQUAL(certificate.getKeyLocator().value().getName(), "/ndn/site1/KEY/ksk-2516425377094");
BOOST_CHECK_EQUAL(boost::lexical_cast<std::string>(certificate.getValidityPeriod()),
"(20141111T050000, 20141111T060000)");
- BOOST_CHECK_THROW(certificate.getExtension(12345), ndn::Data::Error);
+ BOOST_CHECK_THROW(certificate.getExtension(12345), Data::Error);
BOOST_CHECK_NO_THROW(certificate.getPublicKey());
}
@@ -202,15 +202,13 @@
InvalidCertFixture()
{
Certificate certBase(Block{CERT});
- BOOST_CHECK_NO_THROW((Certificate(certBase)));
-
m_certBase = Data(certBase);
generateFakeSignature(m_certBase);
- BOOST_CHECK_NO_THROW((Certificate(m_certBase)));
+ BOOST_REQUIRE_NO_THROW(Certificate{m_certBase});
}
-public:
+protected:
Data m_certBase;
};
@@ -249,28 +247,129 @@
BOOST_CHECK_THROW(cert.getPublicKey(), Certificate::Error);
}
-BOOST_AUTO_TEST_CASE(PrintCertificateInfo)
+BOOST_AUTO_TEST_CASE(Print)
{
- const std::string expectedCertificateInfo = std::string(R"INFO(
-Certificate name:
+ const std::string expected1(
+R"TXT(Certificate Name:
+ /
+Public Key:
+ Key Type: Unknown (0 bytes)
+Signature Information:
+ Signature Type: Unknown(65535)
+)TXT");
+
+ Certificate cert1;
+ BOOST_CHECK_EQUAL(boost::lexical_cast<std::string>(cert1), expected1);
+
+ const std::string expected2(
+R"TXT(Certificate Name:
/ndn/site1/KEY/ksk-1416425377094/0123/%FD%00%00%01I%C9%8B
-Validity:
- NotBefore: 20150814T223739
- NotAfter: 20150818T223738
-Public key bits:
+Public Key:
+ Key Type: 1024-bit RSA
MIGdMA0GCSqGSIb3DQEBAQUAA4GLADCBhwKBgQCeBj5HhbI0N6qFR6wDJIO1nKgF
OiQe64kBu+mbssMirGjj8GwCzmimxNCnBpCcqhsIHYtDmjNnRG0hoxuImpdeWcQV
C9ksvVEHYYKtwbjXv5vPfSTCY/OXF+v+YiW6W02Kwnq9Q4qPuPLxxWow01CMyJrf
7+0153pi6nZ8uwgmxwIBEQ==
+Validity:
+ Not Before: 2015-08-14T22:37:39
+ Not After: 2015-08-18T22:37:38
Signature Information:
Signature Type: SignatureSha256WithRsa
Key Locator: Name=/ndn/site1/KEY/ksk-2516425377094
-)INFO").substr(1);
+)TXT");
- Certificate certificate(Block{CERT});
- BOOST_CHECK_EQUAL(boost::lexical_cast<std::string>(certificate), expectedCertificateInfo);
+ Certificate cert2(Block{CERT});
+ BOOST_CHECK_EQUAL(boost::lexical_cast<std::string>(cert2), expected2);
- // TODO: Check output formats of other certificates
+ const std::string expected3(
+R"TXT(Certificate Name:
+ /ndn/test/identity/KEY/%C7G%3A%D6%12P%B5%F0/self/v=1650251820652
+Public Key:
+ Key Type: 256-bit EC
+ MFkwEwYHKoZIzj0CAQYIKoZIzj0DAQcDQgAEnoGVuhO+9JnIRo6QSgJin8RgA8Gh
+ RN9oVbnXi2rAJa4jq1yuCKaLeOt2sdXlkW6uBByOhbTuDdovlbIUsJ8bhg==
+Validity:
+ Not Before: 1970-01-01T00:00:00
+ Not After: 2042-04-13T03:17:00
+Signature Information:
+ Signature Type: SignatureSha256WithEcdsa
+ Key Locator: Name=/ndn/test/identity/KEY/%C7G%3A%D6%12P%B5%F0
+ Self-Signed: yes
+)TXT");
+
+ std::istringstream is(
+R"BASE64(Bv0BPgc0CANuZG4IBHRlc3QICGlkZW50aXR5CANLRVkICMdHOtYSULXwCARzZWxm
+NggAAAGAOqxubBQJGAECGQQANu6AFVswWTATBgcqhkjOPQIBBggqhkjOPQMBBwNC
+AASegZW6E770mchGjpBKAmKfxGADwaFE32hVudeLasAlriOrXK4Ipot463ax1eWR
+bq4EHI6FtO4N2i+VshSwnxuGFlUbAQMcJgckCANuZG4IBHRlc3QICGlkZW50aXR5
+CANLRVkICMdHOtYSULXw/QD9Jv0A/g8xOTcwMDEwMVQwMDAwMDD9AP8PMjA0MjA0
+MTNUMDMxNzAwF0cwRQIgFRnwthtzKdqRgO3cZMNA1hfT3QcNu/+xjo7hUy+UvdsC
+IQCz3DHoRtKl7uZoJOgQsZP1/CGkNjlGZE3EQ+Ylwiprrw==)BASE64");
+ Certificate cert3 = io::loadTlv<Certificate>(is, io::BASE64);
+ BOOST_CHECK_EQUAL(boost::lexical_cast<std::string>(cert3), expected3);
+
+ const std::string expected4(
+R"TXT(Certificate Name:
+ /ndn/test/identity/KEY/%C7G%3A%D6%12P%B5%F0/self/v=1650251820652
+Public Key:
+ Key Type: Unknown (23 bytes)
+ bm90IGEgdmFsaWQgcHVibGljIGtleQA=
+Validity:
+ Not Before: 1970-01-01T00:00:00
+ Not After: 2042-04-13T03:17:00
+Signature Information:
+ Signature Type: SignatureSha256WithEcdsa
+ Key Locator: Name=/ndn/test/identity/KEY/%C7G%3A%D6%12P%B5%F0
+ Self-Signed: yes
+)TXT");
+
+ const uint8_t notAKey[] = "not a valid public key";
+ Certificate cert4(cert3);
+ cert4.setContent(notAKey);
+ BOOST_CHECK_EQUAL(boost::lexical_cast<std::string>(cert4), expected4);
+
+ const std::string expected5(
+R"TXT(Certificate Name:
+ /ndn/test/identity/KEY/%C7G%3A%D6%12P%B5%F0/self/v=1650251820652
+Additional Description:
+ bWFsZm9ybWVk
+Public Key:
+ Key Type: 256-bit EC
+ MFkwEwYHKoZIzj0CAQYIKoZIzj0DAQcDQgAEnoGVuhO+9JnIRo6QSgJin8RgA8Gh
+ RN9oVbnXi2rAJa4jq1yuCKaLeOt2sdXlkW6uBByOhbTuDdovlbIUsJ8bhg==
+Validity:
+ Not Before: 1970-01-01T00:00:00
+ Not After: 2042-04-13T03:17:00
+Signature Information:
+ Signature Type: SignatureSha256WithEcdsa
+ Key Locator: KeyDigest=0000000000000000
+)TXT");
+
+ auto sigInfo = cert3.getSignatureInfo();
+ sigInfo.addCustomTlv(makeStringBlock(tlv::AdditionalDescription, "malformed"));
+ sigInfo.setKeyLocator(KeyLocator().setKeyDigest(std::make_shared<Buffer>(8)));
+ Certificate cert5(cert3);
+ cert5.setSignatureInfo(sigInfo);
+ BOOST_CHECK_EQUAL(boost::lexical_cast<std::string>(cert5), expected5);
+
+ const std::string expected6(
+R"TXT(Certificate Name:
+ /ndn/test/identity/KEY/%C7G%3A%D6%12P%B5%F0/self/v=1650251820652
+Public Key:
+ Key Type: 256-bit EC
+ MFkwEwYHKoZIzj0CAQYIKoZIzj0DAQcDQgAEnoGVuhO+9JnIRo6QSgJin8RgA8Gh
+ RN9oVbnXi2rAJa4jq1yuCKaLeOt2sdXlkW6uBByOhbTuDdovlbIUsJ8bhg==
+Signature Information:
+ Signature Type: DigestSha256
+)TXT");
+
+ sigInfo.removeCustomTlv(tlv::AdditionalDescription);
+ sigInfo.addCustomTlv(makeStringBlock(tlv::ValidityPeriod, "malformed"));
+ sigInfo.setSignatureType(tlv::DigestSha256);
+ sigInfo.setKeyLocator(nullopt);
+ Certificate cert6(cert3);
+ cert6.setSignatureInfo(sigInfo);
+ BOOST_CHECK_EQUAL(boost::lexical_cast<std::string>(cert6), expected6);
}
BOOST_AUTO_TEST_SUITE_END() // TestCertificate
diff --git a/tests/unit/security/transform/public-key.t.cpp b/tests/unit/security/transform/public-key.t.cpp
index c888482..e844293 100644
--- a/tests/unit/security/transform/public-key.t.cpp
+++ b/tests/unit/security/transform/public-key.t.cpp
@@ -43,7 +43,9 @@
struct RsaKeyTestData
{
- const std::string publicKeyPkcs8 =
+ static constexpr KeyType type = KeyType::RSA;
+ static constexpr size_t size = 2048;
+ const std::string pkcs8Base64 =
"MIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEAw0WM1/WhAxyLtEqsiAJg\n"
"WDZWuzkYpeYVdeeZcqRZzzfRgBQTsNozS5t4HnwTZhwwXbH7k3QN0kRTV826Xobw\n"
"s3iigohnM9yTK+KKiayPhIAm/+5HGT6SgFJhYhqo1/upWdueojil6RP4/AgavHho\n"
@@ -52,10 +54,14 @@
"9rH58ynaAix0tcR/nBMRLUX+e3rURHg6UbSjJbdb9qmKM1fTGHKUzL/5pMG6uBU0\n"
"ywIDAQAB\n";
};
+constexpr KeyType RsaKeyTestData::type;
+constexpr size_t RsaKeyTestData::size;
struct EcKeyTestData
{
- const std::string publicKeyPkcs8 =
+ static constexpr KeyType type = KeyType::EC;
+ static constexpr size_t size = 256;
+ const std::string pkcs8Base64 =
"MIIBSzCCAQMGByqGSM49AgEwgfcCAQEwLAYHKoZIzj0BAQIhAP////8AAAABAAAA\n"
"AAAAAAAAAAAA////////////////MFsEIP////8AAAABAAAAAAAAAAAAAAAA////\n"
"///////////8BCBaxjXYqjqT57PrvVV2mIa8ZR0GsMxTsPY7zjw+J9JgSwMVAMSd\n"
@@ -64,23 +70,28 @@
"//////////+85vqtpxeehPO5ysL8YyVRAgEBA0IABGhuFibgwLdEJBDOLdvSg1Hc\n"
"5EJTDxq6ls5FoYLfThp8HOjuwGSz0qw8ocMqyku1y0V5peQ4rEPd0bwcpZd9svA=\n";
};
+constexpr KeyType EcKeyTestData::type;
+constexpr size_t EcKeyTestData::size;
using KeyTestDataSets = boost::mpl::vector<RsaKeyTestData, EcKeyTestData>;
-BOOST_AUTO_TEST_CASE_TEMPLATE(SaveLoad, T, KeyTestDataSets)
+BOOST_AUTO_TEST_CASE_TEMPLATE(LoadAndSave, T, KeyTestDataSets)
{
T dataSet;
- auto pKeyPkcs8Base64 = make_span(reinterpret_cast<const uint8_t*>(dataSet.publicKeyPkcs8.data()),
- dataSet.publicKeyPkcs8.size());
+ auto pKeyPkcs8Base64 = make_span(reinterpret_cast<const uint8_t*>(dataSet.pkcs8Base64.data()),
+ dataSet.pkcs8Base64.size());
OBufferStream os;
bufferSource(pKeyPkcs8Base64) >> base64Decode() >> streamSink(os);
auto pKeyPkcs8 = os.buf();
+ // Load
PublicKey pKey1;
BOOST_CHECK_NO_THROW(pKey1.loadPkcs8Base64(pKeyPkcs8Base64));
+ BOOST_TEST(pKey1.getKeyType() == T::type);
+ BOOST_TEST(pKey1.getKeySize() == T::size);
- std::stringstream ss2(dataSet.publicKeyPkcs8);
+ std::stringstream ss2(dataSet.pkcs8Base64);
PublicKey pKey2;
BOOST_CHECK_NO_THROW(pKey2.loadPkcs8Base64(ss2));
@@ -92,15 +103,14 @@
PublicKey pKey4;
BOOST_CHECK_NO_THROW(pKey4.loadPkcs8(ss4));
+ // Save
OBufferStream os5;
BOOST_REQUIRE_NO_THROW(pKey1.savePkcs8Base64(os5));
- BOOST_CHECK_EQUAL_COLLECTIONS(pKeyPkcs8Base64.begin(), pKeyPkcs8Base64.end(),
- os5.buf()->begin(), os5.buf()->end());
+ BOOST_TEST(*os5.buf() == pKeyPkcs8Base64, boost::test_tools::per_element());
OBufferStream os6;
BOOST_REQUIRE_NO_THROW(pKey1.savePkcs8(os6));
- BOOST_CHECK_EQUAL_COLLECTIONS(pKeyPkcs8->begin(), pKeyPkcs8->end(),
- os6.buf()->begin(), os6.buf()->end());
+ BOOST_TEST(*os6.buf() == *pKeyPkcs8, boost::test_tools::per_element());
}
// NOTE: We cannot test RSA encryption by comparing the computed ciphertext to
@@ -113,9 +123,8 @@
EcKeyTestData dataSet;
PublicKey pKey;
- pKey.loadPkcs8Base64({reinterpret_cast<const uint8_t*>(dataSet.publicKeyPkcs8.data()),
- dataSet.publicKeyPkcs8.size()});
- BOOST_CHECK_EQUAL(pKey.getKeyType(), KeyType::EC);
+ pKey.loadPkcs8Base64({reinterpret_cast<const uint8_t*>(dataSet.pkcs8Base64.data()),
+ dataSet.pkcs8Base64.size()});
OBufferStream os;
bufferSource("Y2lhbyFob2xhIWhlbGxvIQ==") >> base64Decode() >> streamSink(os);