place encoding for NEW/REVOKE/CHALLENGE in protocol detail file
Change-Id: I37d421bf256564c2acf9246983001a525c510e1f
diff --git a/src/ca-module.cpp b/src/ca-module.cpp
index 70aa887..b2d0176 100644
--- a/src/ca-module.cpp
+++ b/src/ca-module.cpp
@@ -224,18 +224,25 @@
// REVOKE Naming Convention: /<CA-prefix>/CA/REVOKE/[SignedInterestParameters_Digest]
// get ECDH pub key and cert request
const auto& parameterTLV = request.getApplicationParameters();
- parameterTLV.parse();
+ std::string ecdhPub;
+ shared_ptr<security::v2::Certificate> clientCert;
+ try {
+ NEW_RENEW_REVOKE::decodeApplicationParameters(parameterTLV, requestType, ecdhPub, clientCert);
+ } catch (const std::exception& e) {
+ if (!parameterTLV.hasValue()) {
+ _LOG_ERROR("Empty TLV obtained from the Interest parameter.");
+ m_face.put(generateErrorDataPacket(request.getName(), ErrorCode::INVALID_PARAMETER,
+ "Empty TLV obtained from the Interest parameter."));
+ return;
+ }
- if (!parameterTLV.hasValue()) {
- _LOG_ERROR("Empty TLV obtained from the Interest parameter.");
+ _LOG_ERROR("Unrecognized self-signed certificate: " << e.what());
m_face.put(generateErrorDataPacket(request.getName(), ErrorCode::INVALID_PARAMETER,
- "Empty TLV obtained from the Interest parameter."));
+ "Unrecognized self-signed certificate."));
return;
}
- std::string peerKeyBase64 = readString(parameterTLV.get(tlv_ecdh_pub));
-
- if (peerKeyBase64 == "") {
+ if (ecdhPub == "") {
_LOG_ERROR("Empty ECDH PUB obtained from the Interest parameter.");
m_face.put(generateErrorDataPacket(request.getName(), ErrorCode::INVALID_PARAMETER,
"Empty ECDH PUB obtained from the Interest parameter."));
@@ -246,7 +253,7 @@
ECDHState ecdh;
auto myEcdhPubKeyBase64 = ecdh.getBase64PubKey();
try {
- ecdh.deriveSecret(peerKeyBase64);
+ ecdh.deriveSecret(ecdhPub);
}
catch (const std::exception& e) {
_LOG_ERROR("Cannot derive a shared secret using the provided ECDH key: " << e.what());
@@ -261,27 +268,6 @@
hkdf(ecdh.context->sharedSecret, ecdh.context->sharedSecretLen,
(uint8_t*)&saltInt, sizeof(saltInt), aesKey, sizeof(aesKey));
- shared_ptr<security::v2::Certificate> clientCert = nullptr;
- // parse certificate request
- Block requestPayload;
- if (requestType == RequestType::NEW) {
- requestPayload = parameterTLV.get(tlv_cert_request);
- }
- else if (requestType == RequestType::REVOKE) {
- requestPayload = parameterTLV.get(tlv_cert_to_revoke);
- }
- requestPayload.parse();
- try {
- security::v2::Certificate cert = security::v2::Certificate(requestPayload.get(tlv::Data));
- clientCert = make_shared<security::v2::Certificate>(cert);
- }
- catch (const std::exception& e) {
- _LOG_ERROR("Unrecognized self-signed certificate: " << e.what());
- m_face.put(generateErrorDataPacket(request.getName(), ErrorCode::INVALID_PARAMETER,
- "Unrecognized self-signed certificate."));
- return;
- }
-
// verify identity name
if (!m_config.m_caItem.m_caPrefix.isPrefixOf(clientCert->getIdentity())
|| !security::v2::Certificate::isValidName(clientCert->getName())
diff --git a/src/protocol-detail/challenge.cpp b/src/protocol-detail/challenge.cpp
index 85875fd..847f7db 100644
--- a/src/protocol-detail/challenge.cpp
+++ b/src/protocol-detail/challenge.cpp
@@ -35,6 +35,23 @@
return response;
}
+CHALLENGE::DecodedData
+CHALLENGE::decodeDataPayload(const Block& data){
+ data.parse();
+ Status status = static_cast<Status>(readNonNegativeInteger(data.get(tlv_status)));
+ std::string challengeStatus = readString(data.get(tlv_challenge_status));
+ size_t remainingTries = readNonNegativeInteger(data.get(tlv_remaining_tries));
+ time::seconds remainingTime = time::seconds(readNonNegativeInteger(data.get(tlv_remaining_time)));
+
+ if (data.find(tlv_issued_cert_name) != data.elements_end()) {
+ Block issuedCertNameBlock = data.get(tlv_issued_cert_name);
+ issuedCertNameBlock.parse();
+ return DecodedData{status, challengeStatus, remainingTries, remainingTime, Name(issuedCertNameBlock.get(tlv::Name))};
+ }
+
+ return DecodedData{status, challengeStatus, remainingTries, remainingTime, nullopt};
+}
+
} // namespace ndncert
} // namespace ndn
diff --git a/src/protocol-detail/challenge.hpp b/src/protocol-detail/challenge.hpp
index aafcd42..8078237 100644
--- a/src/protocol-detail/challenge.hpp
+++ b/src/protocol-detail/challenge.hpp
@@ -30,6 +30,17 @@
public:
static Block
encodeDataPayload(const RequestState& request);
+
+ struct DecodedData{
+ Status status;
+ std::string challengeStatus;
+ size_t remainingTries;
+ time::seconds remainingTime;
+ optional<Name> issuedCertName;
+ };
+
+ static DecodedData
+ decodeDataPayload(const Block& data);
};
} // namespace ndncert
diff --git a/src/protocol-detail/new-renew-revoke.cpp b/src/protocol-detail/new-renew-revoke.cpp
index 0a941b1..6cae7ff 100644
--- a/src/protocol-detail/new-renew-revoke.cpp
+++ b/src/protocol-detail/new-renew-revoke.cpp
@@ -28,7 +28,7 @@
namespace ndn {
namespace ndncert {
-_LOG_INIT(ndncert.client);
+_LOG_INIT(ndncert.encoding.new_renew_revoke);
Block
NEW_RENEW_REVOKE::encodeApplicationParameters(RequestType requestType, const std::string& ecdhPub, const security::v2::Certificate& certRequest)
@@ -55,6 +55,25 @@
return request;
}
+void
+NEW_RENEW_REVOKE::decodeApplicationParameters(const Block& payload, RequestType requestType, std::string& ecdhPub,
+ shared_ptr<security::v2::Certificate>& clientCert) {
+ payload.parse();
+
+ ecdhPub = readString(payload.get(tlv_ecdh_pub));
+ Block requestPayload;
+ if (requestType == RequestType::NEW) {
+ requestPayload = payload.get(tlv_cert_request);
+ }
+ else if (requestType == RequestType::REVOKE) {
+ requestPayload = payload.get(tlv_cert_to_revoke);
+ }
+ requestPayload.parse();
+
+ security::v2::Certificate cert = security::v2::Certificate(requestPayload.get(tlv::Data));
+ clientCert = make_shared<security::v2::Certificate>(cert);
+}
+
Block
NEW_RENEW_REVOKE::encodeDataContent(const std::string& ecdhKey, const std::string& salt,
const RequestState& request,
@@ -72,5 +91,22 @@
return response;
}
+NEW_RENEW_REVOKE::DecodedData
+NEW_RENEW_REVOKE::decodeDataContent(const Block& content)
+{
+ content.parse();
+ const auto& ecdhKey = readString(content.get(tlv_ecdh_pub));
+ const auto& salt = readString(content.get(tlv_salt));
+ const auto& requestStatus = static_cast<Status>(readNonNegativeInteger(content.get(tlv_status)));
+ const auto& requestId = readString(content.get(tlv_request_id));
+ std::list<std::string> challenges;
+ for (auto const& element : content.elements()) {
+ if (element.type() == tlv_challenge) {
+ challenges.push_back(readString(element));
+ }
+ }
+ return DecodedData{ecdhKey, salt, requestId, requestStatus, challenges};
+}
+
} // namespace ndncert
} // namespace ndn
\ No newline at end of file
diff --git a/src/protocol-detail/new-renew-revoke.hpp b/src/protocol-detail/new-renew-revoke.hpp
index aac51d2..4c9cb18 100644
--- a/src/protocol-detail/new-renew-revoke.hpp
+++ b/src/protocol-detail/new-renew-revoke.hpp
@@ -31,10 +31,22 @@
static Block
encodeApplicationParameters(RequestType requestType, const std::string& ecdhPub, const security::v2::Certificate& certRequest);
+ static void
+ decodeApplicationParameters(const Block& block, RequestType requestType, std::string& ecdhPub, shared_ptr<security::v2::Certificate>& certRequest);
+
static Block
encodeDataContent(const std::string& ecdhKey, const std::string& salt,
const RequestState& request,
const std::list<std::string>& challenges);
+ struct DecodedData {
+ std::string ecdhKey;
+ std::string salt;
+ std::string requestId;
+ Status requestStatus;
+ std::list<std::string> challenges;
+ };
+ static DecodedData
+ decodeDataContent(const Block& content);
};
} // namespace ndncert
diff --git a/src/requester.cpp b/src/requester.cpp
index 7bf9594..165ad93 100644
--- a/src/requester.cpp
+++ b/src/requester.cpp
@@ -181,28 +181,21 @@
processIfError(reply);
auto contentTLV = reply.getContent();
- contentTLV.parse();
+ const auto content = NEW_RENEW_REVOKE::decodeDataContent(contentTLV);
// ECDH
- const auto& peerKeyBase64Str = readString(contentTLV.get(tlv_ecdh_pub));
- const auto& saltStr = readString(contentTLV.get(tlv_salt));
- uint64_t saltInt = std::stoull(saltStr);
- state.m_ecdh.deriveSecret(peerKeyBase64Str);
+ uint64_t saltInt = std::stoull(content.salt);
+ state.m_ecdh.deriveSecret(content.ecdhKey);
// HKDF
hkdf(state.m_ecdh.context->sharedSecret, state.m_ecdh.context->sharedSecretLen,
(uint8_t*)&saltInt, sizeof(saltInt), state.m_aesKey, sizeof(state.m_aesKey));
// update state
- state.m_status = static_cast<Status>(readNonNegativeInteger(contentTLV.get(tlv_status)));
- state.m_requestId = readString(contentTLV.get(tlv_request_id));
- std::list<std::string> challengeList;
- for (auto const& element : contentTLV.elements()) {
- if (element.type() == tlv_challenge) {
- challengeList.push_back(readString(element));
- }
- }
- return challengeList;
+ state.m_status = content.requestStatus;
+ state.m_requestId = content.requestId;
+
+ return content.challenges;
}
std::vector<std::tuple<std::string, std::string>>
@@ -254,19 +247,16 @@
processIfError(reply);
auto result = decodeBlockWithAesGcm128(reply.getContent(), state.m_aesKey, (const uint8_t*)"test", strlen("test"));
Block contentTLV = makeBinaryBlock(tlv_encrypted_payload, result.data(), result.size());
- contentTLV.parse();
+ auto decoded = CHALLENGE::decodeDataPayload(contentTLV);
// update state
- state.m_status = static_cast<Status>(readNonNegativeInteger(contentTLV.get(tlv_status)));
- state.m_challengeStatus = readString(contentTLV.get(tlv_challenge_status));
- state.m_remainingTries = readNonNegativeInteger(contentTLV.get(tlv_remaining_tries));
- state.m_freshBefore = time::system_clock::now() +
- time::seconds(readNonNegativeInteger(contentTLV.get(tlv_remaining_time)));
+ state.m_status = decoded.status;
+ state.m_challengeStatus = decoded.challengeStatus;
+ state.m_remainingTries = decoded.remainingTries;
+ state.m_freshBefore = time::system_clock::now() + decoded.remainingTime;
- if (contentTLV.find(tlv_issued_cert_name) != contentTLV.elements_end()) {
- Block issuedCertNameBlock = contentTLV.get(tlv_issued_cert_name);
- issuedCertNameBlock.parse();
- state.m_issuedCertName.wireDecode(issuedCertNameBlock.get(tlv::Name));
+ if (decoded.issuedCertName) {
+ state.m_issuedCertName = *decoded.issuedCertName;
}
}