blob: ffda468f25d56675ec240d6d82d2b9e807857863 [file] [log] [blame]
Zhiyi Zhang23564c82017-03-01 10:22:22 -08001/* -*- Mode:C++; c-file-style:"gnu"; indent-tabs-mode:nil; -*- */
2/**
Zhiyi Zhangad9e04f2020-03-27 12:04:31 -07003 * Copyright (c) 2017-2020, Regents of the University of California.
Zhiyi Zhang23564c82017-03-01 10:22:22 -08004 *
5 * This file is part of ndncert, a certificate management system based on NDN.
6 *
7 * ndncert is free software: you can redistribute it and/or modify it under the terms
8 * of the GNU General Public License as published by the Free Software Foundation, either
9 * version 3 of the License, or (at your option) any later version.
10 *
11 * ndncert is distributed in the hope that it will be useful, but WITHOUT ANY
12 * WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A
13 * PARTICULAR PURPOSE. See the GNU General Public License for more details.
14 *
15 * You should have received copies of the GNU General Public License along with
16 * ndncert, e.g., in COPYING.md file. If not, see <http://www.gnu.org/licenses/>.
17 *
18 * See AUTHORS.md for complete list of ndncert authors and contributors.
19 */
20
21#include "client-module.hpp"
Zhiyi Zhang48f23782020-09-28 12:11:24 -070022
Zhiyi Zhang23564c82017-03-01 10:22:22 -080023#include <ndn-cxx/security/signing-helpers.hpp>
Zhiyi Zhangaf7c2902019-03-14 22:13:21 -070024#include <ndn-cxx/security/transform/base64-encode.hpp>
25#include <ndn-cxx/security/transform/buffer-source.hpp>
26#include <ndn-cxx/security/transform/stream-sink.hpp>
Zhiyi Zhang48f23782020-09-28 12:11:24 -070027#include <ndn-cxx/security/verification-helpers.hpp>
28#include <ndn-cxx/util/io.hpp>
29#include <ndn-cxx/util/random.hpp>
30
31#include "challenge-module.hpp"
32#include "crypto-support/enc-tlv.hpp"
Zhiyi Zhang48f23782020-09-28 12:11:24 -070033#include "protocol-detail/challenge.hpp"
34#include "protocol-detail/info.hpp"
tylerliu4889a782020-09-30 22:47:49 -070035#include "protocol-detail/new-renew-revoke.hpp"
Zhiyi Zhang48f23782020-09-28 12:11:24 -070036#include "protocol-detail/probe.hpp"
tylerliu36d97f52020-09-30 22:32:54 -070037#include "protocol-detail/error.hpp"
38#include "ndncert-common.hpp"
Zhiyi Zhang23564c82017-03-01 10:22:22 -080039
40namespace ndn {
41namespace ndncert {
42
43_LOG_INIT(ndncert.client);
44
Zhiyi Zhangaf7c2902019-03-14 22:13:21 -070045ClientModule::ClientModule(security::v2::KeyChain& keyChain)
Zhiyi Zhang48f23782020-09-28 12:11:24 -070046 : m_keyChain(keyChain)
Zhiyi Zhang23564c82017-03-01 10:22:22 -080047{
48}
49
Zhiyi Zhangad9e04f2020-03-27 12:04:31 -070050ClientModule::~ClientModule()
51{
52 endSession();
53}
Davide Pesavento08994782018-01-22 12:13:41 -050054
Zhiyi Zhangaf7c2902019-03-14 22:13:21 -070055shared_ptr<Interest>
swa77020643ac2020-03-26 02:24:45 -070056ClientModule::generateInfoInterest(const Name& caName)
Zhiyi Zhang1c0bd372017-12-18 18:32:55 +080057{
58 Name interestName = caName;
Zhiyi Zhangaf7c2902019-03-14 22:13:21 -070059 if (readString(caName.at(-1)) != "CA")
60 interestName.append("CA");
swa77020643ac2020-03-26 02:24:45 -070061 interestName.append("INFO");
Zhiyi Zhangaf7c2902019-03-14 22:13:21 -070062 auto interest = make_shared<Interest>(interestName);
63 interest->setMustBeFresh(true);
64 interest->setCanBePrefix(false);
65 return interest;
Zhiyi Zhang1c0bd372017-12-18 18:32:55 +080066}
67
Zhiyi Zhangcaab5462019-10-18 13:41:02 -070068bool
Suyong Won19fba4d2020-05-09 13:39:46 -070069ClientModule::verifyInfoResponse(const Data& reply)
Zhiyi Zhangcaab5462019-10-18 13:41:02 -070070{
71 // parse the ca item
Zhiyi Zhang3e8ca252020-09-30 17:18:38 -070072 auto caItem = INFO::decodeDataContent(reply.getContent());
Zhiyi Zhangcaab5462019-10-18 13:41:02 -070073
74 // verify the probe Data's sig
Zhiyi Zhang9829da92020-09-30 16:19:34 -070075 if (!security::verifySignature(reply, *caItem.m_cert)) {
Suyong Won256c9062020-05-11 02:45:56 -070076 _LOG_ERROR("Cannot verify data signature from " << m_ca.m_caPrefix.toUri());
Zhiyi Zhangcaab5462019-10-18 13:41:02 -070077 return false;
78 }
79 return true;
80}
81
Zhiyi Zhang1c0bd372017-12-18 18:32:55 +080082void
Suyong Won19fba4d2020-05-09 13:39:46 -070083ClientModule::addCaFromInfoResponse(const Data& reply)
Zhiyi Zhang1c0bd372017-12-18 18:32:55 +080084{
Suyong Won57462ca2020-05-05 22:20:09 -070085 const Block& contentBlock = reply.getContent();
86
Zhiyi Zhangaf7c2902019-03-14 22:13:21 -070087 // parse the ca item
Zhiyi Zhang3e8ca252020-09-30 17:18:38 -070088 auto caItem = INFO::decodeDataContent(contentBlock);
Zhiyi Zhang1c0bd372017-12-18 18:32:55 +080089
Zhiyi Zhangaf7c2902019-03-14 22:13:21 -070090 // update the local config
91 bool findItem = false;
92 for (auto& item : m_config.m_caItems) {
Suyong Won256c9062020-05-11 02:45:56 -070093 if (item.m_caPrefix == caItem.m_caPrefix) {
Zhiyi Zhangaf7c2902019-03-14 22:13:21 -070094 findItem = true;
95 item = caItem;
Zhiyi Zhang1c0bd372017-12-18 18:32:55 +080096 }
97 }
Zhiyi Zhangaf7c2902019-03-14 22:13:21 -070098 if (!findItem) {
99 m_config.m_caItems.push_back(caItem);
Zhiyi Zhang1c0bd372017-12-18 18:32:55 +0800100 }
Zhiyi Zhang23564c82017-03-01 10:22:22 -0800101}
102
Zhiyi Zhangaf7c2902019-03-14 22:13:21 -0700103shared_ptr<Interest>
Zhiyi Zhang9829da92020-09-30 16:19:34 -0700104ClientModule::generateProbeInterest(const CaConfigItem& ca,
105 std::vector<std::tuple<std::string, std::string>>&& probeInfo)
Zhiyi Zhang23564c82017-03-01 10:22:22 -0800106{
Suyong Won256c9062020-05-11 02:45:56 -0700107 Name interestName = ca.m_caPrefix;
swa770de007bc2020-03-24 21:26:21 -0700108 interestName.append("CA").append("PROBE");
Zhiyi Zhangaf7c2902019-03-14 22:13:21 -0700109 auto interest = make_shared<Interest>(interestName);
110 interest->setMustBeFresh(true);
111 interest->setCanBePrefix(false);
Zhiyi Zhang9829da92020-09-30 16:19:34 -0700112 interest->setApplicationParameters(PROBE::encodeApplicationParameters(std::move(probeInfo)));
Zhiyi Zhangaf7c2902019-03-14 22:13:21 -0700113
114 // update local state
115 m_ca = ca;
116 return interest;
117}
118
119void
120ClientModule::onProbeResponse(const Data& reply)
121{
Zhiyi Zhang9829da92020-09-30 16:19:34 -0700122 if (!security::verifySignature(reply, *m_ca.m_cert)) {
Suyong Won256c9062020-05-11 02:45:56 -0700123 _LOG_ERROR("Cannot verify data signature from " << m_ca.m_caPrefix.toUri());
Zhiyi Zhangaf7c2902019-03-14 22:13:21 -0700124 return;
125 }
Suyong Won19fba4d2020-05-09 13:39:46 -0700126
tylerliu36d97f52020-09-30 22:32:54 -0700127 // error handling
128 processIfError(reply);
129
Suyong Won19fba4d2020-05-09 13:39:46 -0700130 auto contentTLV = reply.getContent();
Suyong Won44d0cce2020-05-10 04:07:43 -0700131 contentTLV.parse();
Zhiyi Zhangaf7c2902019-03-14 22:13:21 -0700132
133 // read the available name and put it into the state
Suyong Won19fba4d2020-05-09 13:39:46 -0700134 if (contentTLV.get(tlv_probe_response).hasValue()) {
Suyong Wonb29e0da2020-05-12 01:59:15 -0700135 Block probeResponseBlock = contentTLV.get(tlv_probe_response);
136 probeResponseBlock.parse();
137 m_identityName.wireDecode(probeResponseBlock.get(tlv::Name));
Zhiyi Zhangaf7c2902019-03-14 22:13:21 -0700138 }
Zhiyi Zhang781a5602019-06-26 19:05:04 -0700139 else {
140 NDN_LOG_TRACE("The JSON_CA_NAME is empty.");
141 }
Zhiyi Zhangaf7c2902019-03-14 22:13:21 -0700142}
143
144shared_ptr<Interest>
145ClientModule::generateNewInterest(const time::system_clock::TimePoint& notBefore,
146 const time::system_clock::TimePoint& notAfter,
Zhiyi Zhangb8bbc642020-09-29 14:08:26 -0700147 const Name& identityName)
Zhiyi Zhangaf7c2902019-03-14 22:13:21 -0700148{
149 // Name requestedName = identityName;
Zhiyi Zhang48f23782020-09-28 12:11:24 -0700150 if (!identityName.empty()) { // if identityName is not empty, find the corresponding CA
Zhiyi Zhangaf7c2902019-03-14 22:13:21 -0700151 bool findCa = false;
152 for (const auto& caItem : m_config.m_caItems) {
Suyong Won256c9062020-05-11 02:45:56 -0700153 if (caItem.m_caPrefix.isPrefixOf(identityName)) {
Zhiyi Zhangaf7c2902019-03-14 22:13:21 -0700154 m_ca = caItem;
155 findCa = true;
156 }
157 }
Zhiyi Zhang48f23782020-09-28 12:11:24 -0700158 if (!findCa) { // if cannot find, cannot proceed
Zhiyi Zhangaf7c2902019-03-14 22:13:21 -0700159 return nullptr;
160 }
161 m_identityName = identityName;
162 }
Zhiyi Zhang48f23782020-09-28 12:11:24 -0700163 else { // if identityName is empty, check m_identityName or generate a random name
Zhiyi Zhangaf7c2902019-03-14 22:13:21 -0700164 if (!m_identityName.empty()) {
165 // do nothing
166 }
167 else {
Zhiyi Zhang781a5602019-06-26 19:05:04 -0700168 NDN_LOG_TRACE("Randomly create a new name because m_identityName is empty and the param is empty.");
Zhiyi Zhangaf7c2902019-03-14 22:13:21 -0700169 auto id = std::to_string(random::generateSecureWord64());
Suyong Won256c9062020-05-11 02:45:56 -0700170 m_identityName = m_ca.m_caPrefix;
Zhiyi Zhangaf7c2902019-03-14 22:13:21 -0700171 m_identityName.append(id);
172 }
173 }
174
175 // generate a newly key pair or use an existing key
Zhiyi Zhang10130782018-02-01 18:28:49 -0800176 const auto& pib = m_keyChain.getPib();
Zhiyi Zhangad9e04f2020-03-27 12:04:31 -0700177 security::pib::Identity identity;
Zhiyi Zhang10130782018-02-01 18:28:49 -0800178 try {
Zhiyi Zhangad9e04f2020-03-27 12:04:31 -0700179 identity = pib.getIdentity(m_identityName);
Zhiyi Zhang10130782018-02-01 18:28:49 -0800180 }
181 catch (const security::Pib::Error& e) {
Zhiyi Zhangad9e04f2020-03-27 12:04:31 -0700182 identity = m_keyChain.createIdentity(m_identityName);
183 m_isNewlyCreatedIdentity = true;
184 m_isNewlyCreatedKey = true;
185 }
186 try {
Zhiyi Zhangaf7c2902019-03-14 22:13:21 -0700187 m_key = identity.getDefaultKey();
Zhiyi Zhang10130782018-02-01 18:28:49 -0800188 }
Zhiyi Zhangad9e04f2020-03-27 12:04:31 -0700189 catch (const security::Pib::Error& e) {
190 m_key = m_keyChain.createKey(identity);
191 m_isNewlyCreatedKey = true;
192 }
Zhiyi Zhang23564c82017-03-01 10:22:22 -0800193
194 // generate certificate request
195 security::v2::Certificate certRequest;
Zhiyi Zhangaf7c2902019-03-14 22:13:21 -0700196 certRequest.setName(Name(m_key.getName()).append("cert-request").appendVersion());
Zhiyi Zhang23564c82017-03-01 10:22:22 -0800197 certRequest.setContentType(tlv::ContentType_Key);
Zhiyi Zhangaf7c2902019-03-14 22:13:21 -0700198 certRequest.setContent(m_key.getPublicKey().data(), m_key.getPublicKey().size());
Zhiyi Zhang23564c82017-03-01 10:22:22 -0800199 SignatureInfo signatureInfo;
Zhiyi Zhangaf7c2902019-03-14 22:13:21 -0700200 signatureInfo.setValidityPeriod(security::ValidityPeriod(notBefore, notAfter));
201 m_keyChain.sign(certRequest, signingByKey(m_key.getName()).setSignatureInfo(signatureInfo));
Zhiyi Zhang23564c82017-03-01 10:22:22 -0800202
Zhiyi Zhangaf7c2902019-03-14 22:13:21 -0700203 // generate Interest packet
Suyong Won256c9062020-05-11 02:45:56 -0700204 Name interestName = m_ca.m_caPrefix;
swa770de007bc2020-03-24 21:26:21 -0700205 interestName.append("CA").append("NEW");
Zhiyi Zhangaf7c2902019-03-14 22:13:21 -0700206 auto interest = make_shared<Interest>(interestName);
207 interest->setMustBeFresh(true);
208 interest->setCanBePrefix(false);
Suyong Won19fba4d2020-05-09 13:39:46 -0700209 interest->setApplicationParameters(
tylerliu4889a782020-09-30 22:47:49 -0700210 NEW_RENEW_REVOKE::encodeApplicationParameters(RequestType::NEW, m_ecdh.getBase64PubKey(), certRequest));
Zhiyi Zhang23564c82017-03-01 10:22:22 -0800211
Zhiyi Zhangaf7c2902019-03-14 22:13:21 -0700212 // sign the Interest packet
213 m_keyChain.sign(*interest, signingByKey(m_key.getName()));
214 return interest;
Zhiyi Zhang23564c82017-03-01 10:22:22 -0800215}
216
Zhiyi Zhangaf7c2902019-03-14 22:13:21 -0700217std::list<std::string>
tylerliu0e176c32020-09-29 11:39:46 -0700218ClientModule::onNewRenewRevokeResponse(const Data& reply)
tylerliu4a00aad2020-09-26 02:03:17 -0700219{
Zhiyi Zhang9829da92020-09-30 16:19:34 -0700220 if (!security::verifySignature(reply, *m_ca.m_cert)) {
Suyong Won256c9062020-05-11 02:45:56 -0700221 _LOG_ERROR("Cannot verify data signature from " << m_ca.m_caPrefix.toUri());
Zhiyi Zhangaf7c2902019-03-14 22:13:21 -0700222 return std::list<std::string>();
Zhiyi Zhang23564c82017-03-01 10:22:22 -0800223 }
tylerliu36d97f52020-09-30 22:32:54 -0700224
225 // error handling
226 processIfError(reply);
227
Suyong Won19fba4d2020-05-09 13:39:46 -0700228 auto contentTLV = reply.getContent();
Suyong Won44d0cce2020-05-10 04:07:43 -0700229 contentTLV.parse();
Zhiyi Zhang23564c82017-03-01 10:22:22 -0800230
Zhiyi Zhangaf7c2902019-03-14 22:13:21 -0700231 // ECDH
Zhiyi Zhang48f23782020-09-28 12:11:24 -0700232 const auto& peerKeyBase64Str = readString(contentTLV.get(tlv_ecdh_pub));
Suyong Won19fba4d2020-05-09 13:39:46 -0700233 const auto& saltStr = readString(contentTLV.get(tlv_salt));
Zhiyi Zhangaf7c2902019-03-14 22:13:21 -0700234 uint64_t saltInt = std::stoull(saltStr);
Zhiyi Zhangaf7c2902019-03-14 22:13:21 -0700235 m_ecdh.deriveSecret(peerKeyBase64Str);
Zhiyi Zhang23564c82017-03-01 10:22:22 -0800236
Zhiyi Zhangaf7c2902019-03-14 22:13:21 -0700237 // HKDF
Zhiyi Zhang36706832019-07-04 21:33:03 -0700238 hkdf(m_ecdh.context->sharedSecret, m_ecdh.context->sharedSecretLen,
239 (uint8_t*)&saltInt, sizeof(saltInt), m_aesKey, sizeof(m_aesKey));
Zhiyi Zhang23564c82017-03-01 10:22:22 -0800240
Zhiyi Zhangaf7c2902019-03-14 22:13:21 -0700241 // update state
Zhiyi Zhang48f23782020-09-28 12:11:24 -0700242 m_status = static_cast<Status>(readNonNegativeInteger(contentTLV.get(tlv_status)));
Suyong Won19fba4d2020-05-09 13:39:46 -0700243 m_requestId = readString(contentTLV.get(tlv_request_id));
Zhiyi Zhangaf7c2902019-03-14 22:13:21 -0700244 m_challengeList.clear();
Suyong Won19fba4d2020-05-09 13:39:46 -0700245 for (auto const& element : contentTLV.elements()) {
246 if (element.type() == tlv_challenge) {
247 m_challengeList.push_back(readString(element));
248 }
Zhiyi Zhang23564c82017-03-01 10:22:22 -0800249 }
Zhiyi Zhangaf7c2902019-03-14 22:13:21 -0700250 return m_challengeList;
251}
Zhiyi Zhang23564c82017-03-01 10:22:22 -0800252
Zhiyi Zhangaf7c2902019-03-14 22:13:21 -0700253shared_ptr<Interest>
tylerliu182bc532020-09-25 01:54:45 -0700254ClientModule::generateRevokeInterest(const security::v2::Certificate& certificate)
255{
Zhiyi Zhang48f23782020-09-28 12:11:24 -0700256 // Name requestedName = identityName;
257 bool findCa = false;
258 for (const auto& caItem : m_config.m_caItems) {
Zhiyi Zhang9829da92020-09-30 16:19:34 -0700259 if (caItem.m_caPrefix.isPrefixOf(certificate.getName())) {
Zhiyi Zhang48f23782020-09-28 12:11:24 -0700260 m_ca = caItem;
261 findCa = true;
tylerliu182bc532020-09-25 01:54:45 -0700262 }
Zhiyi Zhang48f23782020-09-28 12:11:24 -0700263 }
264 if (!findCa) { // if cannot find, cannot proceed
265 _LOG_TRACE("Cannot find corresponding CA for the certificate.");
266 return nullptr;
267 }
tylerliu182bc532020-09-25 01:54:45 -0700268
Zhiyi Zhang48f23782020-09-28 12:11:24 -0700269 // generate Interest packet
270 Name interestName = m_ca.m_caPrefix;
271 interestName.append("CA").append("REVOKE");
272 auto interest = make_shared<Interest>(interestName);
273 interest->setMustBeFresh(true);
274 interest->setCanBePrefix(false);
275 interest->setApplicationParameters(
tylerliu4889a782020-09-30 22:47:49 -0700276 NEW_RENEW_REVOKE::encodeApplicationParameters(RequestType::REVOKE, m_ecdh.getBase64PubKey(), certificate));
tylerliu182bc532020-09-25 01:54:45 -0700277
Zhiyi Zhang48f23782020-09-28 12:11:24 -0700278 // return the Interest packet
279 return interest;
tylerliu182bc532020-09-25 01:54:45 -0700280}
281
tylerliu182bc532020-09-25 01:54:45 -0700282shared_ptr<Interest>
Suyong Won19fba4d2020-05-09 13:39:46 -0700283ClientModule::generateChallengeInterest(const Block& challengeRequest)
Zhiyi Zhangaf7c2902019-03-14 22:13:21 -0700284{
Suyong Won44d0cce2020-05-10 04:07:43 -0700285 challengeRequest.parse();
Suyong Won19fba4d2020-05-09 13:39:46 -0700286 m_challengeType = readString(challengeRequest.get(tlv_selected_challenge));
Suyong Won44d0cce2020-05-10 04:07:43 -0700287
Suyong Won256c9062020-05-11 02:45:56 -0700288 Name interestName = m_ca.m_caPrefix;
swa770de007bc2020-03-24 21:26:21 -0700289 interestName.append("CA").append("CHALLENGE").append(m_requestId);
Zhiyi Zhangaf7c2902019-03-14 22:13:21 -0700290 auto interest = make_shared<Interest>(interestName);
291 interest->setMustBeFresh(true);
292 interest->setCanBePrefix(false);
293
294 // encrypt the Interest parameters
Suyong Won7968f7a2020-05-12 01:01:25 -0700295 auto paramBlock = encodeBlockWithAesGcm128(tlv::ApplicationParameters, m_aesKey,
Zhiyi Zhang48f23782020-09-28 12:11:24 -0700296 challengeRequest.value(), challengeRequest.value_size(),
297 (const uint8_t*)"test", strlen("test"));
Zhiyi Zhangaf7c2902019-03-14 22:13:21 -0700298 interest->setApplicationParameters(paramBlock);
299
300 m_keyChain.sign(*interest, signingByKey(m_key.getName()));
301 return interest;
Zhiyi Zhang23564c82017-03-01 10:22:22 -0800302}
303
304void
Zhiyi Zhangaf7c2902019-03-14 22:13:21 -0700305ClientModule::onChallengeResponse(const Data& reply)
Zhiyi Zhang23564c82017-03-01 10:22:22 -0800306{
Zhiyi Zhang9829da92020-09-30 16:19:34 -0700307 if (!security::verifySignature(reply, *m_ca.m_cert)) {
Suyong Won256c9062020-05-11 02:45:56 -0700308 _LOG_ERROR("Cannot verify data signature from " << m_ca.m_caPrefix.toUri());
Zhiyi Zhang23564c82017-03-01 10:22:22 -0800309 return;
310 }
tylerliu36d97f52020-09-30 22:32:54 -0700311
312 // error handling
313 processIfError(reply);
314
Zhiyi Zhangb8cb0472020-05-05 20:55:05 -0700315 auto result = decodeBlockWithAesGcm128(reply.getContent(), m_aesKey, (const uint8_t*)"test", strlen("test"));
Suyong Won19fba4d2020-05-09 13:39:46 -0700316
Suyong Won44d0cce2020-05-10 04:07:43 -0700317 Block contentTLV = makeBinaryBlock(tlv_encrypted_payload, result.data(), result.size());
318 contentTLV.parse();
Zhiyi Zhang23564c82017-03-01 10:22:22 -0800319
Zhiyi Zhangaf7c2902019-03-14 22:13:21 -0700320 // update state
Zhiyi Zhang48f23782020-09-28 12:11:24 -0700321 m_status = static_cast<Status>(readNonNegativeInteger(contentTLV.get(tlv_status)));
Suyong Won19fba4d2020-05-09 13:39:46 -0700322 m_challengeStatus = readString(contentTLV.get(tlv_challenge_status));
323 m_remainingTries = readNonNegativeInteger(contentTLV.get(tlv_remaining_tries));
324 m_freshBefore = time::system_clock::now() +
325 time::seconds(readNonNegativeInteger(contentTLV.get(tlv_remaining_time)));
326
Suyong Won7968f7a2020-05-12 01:01:25 -0700327 if (contentTLV.find(tlv_issued_cert_name) != contentTLV.elements_end()) {
328 Block issuedCertNameBlock = contentTLV.get(tlv_issued_cert_name);
329 issuedCertNameBlock.parse();
330 m_issuedCertName.wireDecode(issuedCertNameBlock.get(tlv::Name));
331 }
Zhiyi Zhangaf7c2902019-03-14 22:13:21 -0700332}
Zhiyi Zhange30eb352017-04-13 15:26:14 -0700333
Zhiyi Zhangaf7c2902019-03-14 22:13:21 -0700334shared_ptr<Interest>
335ClientModule::generateDownloadInterest()
336{
Suyong Won256c9062020-05-11 02:45:56 -0700337 Name interestName = m_ca.m_caPrefix;
swa770de007bc2020-03-24 21:26:21 -0700338 interestName.append("CA").append("DOWNLOAD").append(m_requestId);
Zhiyi Zhangaf7c2902019-03-14 22:13:21 -0700339 auto interest = make_shared<Interest>(interestName);
340 interest->setMustBeFresh(true);
341 interest->setCanBePrefix(false);
342 return interest;
343}
Zhiyi Zhange30eb352017-04-13 15:26:14 -0700344
Zhiyi Zhangaf7c2902019-03-14 22:13:21 -0700345shared_ptr<Interest>
346ClientModule::generateCertFetchInterest()
347{
swa770cf1d8f72020-04-21 23:12:39 -0700348 Name interestName = m_issuedCertName;
Zhiyi Zhangaf7c2902019-03-14 22:13:21 -0700349 auto interest = make_shared<Interest>(interestName);
350 interest->setMustBeFresh(true);
351 interest->setCanBePrefix(false);
352 return interest;
Zhiyi Zhang23564c82017-03-01 10:22:22 -0800353}
354
swa770cf1d8f72020-04-21 23:12:39 -0700355void
356ClientModule::onCertFetchResponse(const Data& reply)
Zhiyi Zhang23564c82017-03-01 10:22:22 -0800357{
Zhiyi Zhang23564c82017-03-01 10:22:22 -0800358 try {
359 security::v2::Certificate cert(reply.getContent().blockFromValue());
Zhiyi Zhangaf7c2902019-03-14 22:13:21 -0700360 m_keyChain.addCertificate(m_key, cert);
swa770cf1d8f72020-04-21 23:12:39 -0700361 _LOG_TRACE("Fetched and installed the cert " << cert.getName());
Zhiyi Zhang23564c82017-03-01 10:22:22 -0800362 }
363 catch (const std::exception& e) {
Zhiyi Zhangaf7c2902019-03-14 22:13:21 -0700364 _LOG_ERROR("Cannot add replied certificate into the keychain " << e.what());
Zhiyi Zhangef6b36a2020-09-22 21:20:59 -0700365 return;
Zhiyi Zhang23564c82017-03-01 10:22:22 -0800366 }
Zhiyi Zhang23564c82017-03-01 10:22:22 -0800367}
368
Zhiyi Zhangef6b36a2020-09-22 21:20:59 -0700369void
370ClientModule::endSession()
Zhiyi Zhang23564c82017-03-01 10:22:22 -0800371{
Zhiyi Zhang48f23782020-09-28 12:11:24 -0700372 if (getApplicationStatus() == Status::SUCCESS || getApplicationStatus() == Status::ENDED) {
Zhiyi Zhangef6b36a2020-09-22 21:20:59 -0700373 return;
374 }
375 if (m_isNewlyCreatedIdentity) {
376 // put the identity into the if scope is because it may cause an error
377 // outside since when endSession is called, identity may not have been created yet.
378 auto identity = m_keyChain.getPib().getIdentity(m_identityName);
379 m_keyChain.deleteIdentity(identity);
380 }
381 else if (m_isNewlyCreatedKey) {
382 auto identity = m_keyChain.getPib().getIdentity(m_identityName);
383 m_keyChain.deleteKey(identity, m_key);
384 }
Zhiyi Zhang48f23782020-09-28 12:11:24 -0700385 m_status = Status::ENDED;
Zhiyi Zhang23564c82017-03-01 10:22:22 -0800386}
387
tylerliu36d97f52020-09-30 22:32:54 -0700388void
389ClientModule::processIfError(const Data& data)
390{
391 auto contentTLV = data.getContent();
392 if (ErrorTLV::isErrorContent(contentTLV)) {
393 try {
394 auto error = ErrorTLV::decodefromDataContent(contentTLV);
395 _LOG_ERROR("Error data returned for " << data.getName() << ": " << std::endl <<
396 "Code: " << errorCodeToString(std::get<0>(error)) << std::endl <<
397 "Info: " << std::get<1>(error) << std::endl);
398 } catch (const std::exception& e) {
399 _LOG_ERROR("Cannot parse error data content for " << data.getName());
400 return;
401 }
402 }
403}
404
Zhiyi Zhang48f23782020-09-28 12:11:24 -0700405} // namespace ndncert
406} // namespace ndn