blob: a5a8af114127fbbdc4eae7fc8814f10ab733292c [file] [log] [blame]
Yingdi Yu48e8c0c2014-03-19 12:01:55 -07001/* -*- Mode:C++; c-file-style:"gnu"; indent-tabs-mode:nil -*- */
2/**
Alexander Afanasyevdfa52c42014-04-24 21:10:11 -07003 * Copyright (c) 2013-2014, Regents of the University of California.
4 * All rights reserved.
5 *
6 * This file is part of ndn-cxx library (NDN C++ library with eXperimental eXtensions).
7 * See AUTHORS.md for complete list of ndn-cxx authors and contributors.
8 *
9 * This file licensed under New BSD License. See COPYING for detailed information about
10 * ndn-cxx library copyright, permissions, and redistribution restrictions.
11 *
12 * @author Yingdi Yu <http://irl.cs.ucla.edu/~yingdi/>
Yingdi Yu48e8c0c2014-03-19 12:01:55 -070013 */
14
15#ifndef NDN_SECURITY_VALIDATOR_CONFIG_HPP
16#define NDN_SECURITY_VALIDATOR_CONFIG_HPP
17
18#include "validator.hpp"
19#include "certificate-cache.hpp"
20#include "conf/rule.hpp"
21#include "conf/common.hpp"
22
23namespace ndn {
24
25class ValidatorConfig : public Validator
26{
27public:
28 class Error : public Validator::Error
29 {
30 public:
31 explicit
32 Error(const std::string& what)
33 : Validator::Error(what)
34 {
35 }
36 };
37
38 static const shared_ptr<CertificateCache> DEFAULT_CERTIFICATE_CACHE;
39
Yingdi Yu96e64062014-04-15 19:57:33 -070040 explicit
41 ValidatorConfig(Face& face,
42 const shared_ptr<CertificateCache>& certificateCache = DEFAULT_CERTIFICATE_CACHE,
43 const int stepLimit = 10);
44
Yingdi Yu48e8c0c2014-03-19 12:01:55 -070045 virtual
46 ~ValidatorConfig()
47 {
48 }
49
50 void
51 load(const std::string& filename);
52
53 void
54 load(const std::string& input, const std::string& filename);
55
56 void
57 load(std::istream& input, const std::string& filename);
58
Yingdi Yudfa9d732014-04-09 09:53:01 -070059 void
60 load(const security::conf::ConfigSection& configSection,
61 const std::string& filename);
62
Yingdi Yu48e8c0c2014-03-19 12:01:55 -070063protected:
64 virtual void
65 checkPolicy(const Data& data,
Yingdi Yu4b8c6a22014-04-15 23:00:54 -070066 int nSteps,
Yingdi Yu48e8c0c2014-03-19 12:01:55 -070067 const OnDataValidated& onValidated,
68 const OnDataValidationFailed& onValidationFailed,
69 std::vector<shared_ptr<ValidationRequest> >& nextSteps);
70
71 virtual void
72 checkPolicy(const Interest& interest,
Yingdi Yu4b8c6a22014-04-15 23:00:54 -070073 int nSteps,
Yingdi Yu48e8c0c2014-03-19 12:01:55 -070074 const OnInterestValidated& onValidated,
75 const OnInterestValidationFailed& onValidationFailed,
76 std::vector<shared_ptr<ValidationRequest> >& nextSteps);
77
78private:
79 template<class Packet, class OnValidated, class OnFailed>
80 void
81 checkSignature(const Packet& packet,
82 const Signature& signature,
Yingdi Yu4b8c6a22014-04-15 23:00:54 -070083 int nSteps,
Yingdi Yu48e8c0c2014-03-19 12:01:55 -070084 const OnValidated& onValidated,
85 const OnFailed& onValidationFailed,
86 std::vector<shared_ptr<ValidationRequest> >& nextSteps);
87
88 template<class Packet, class OnValidated, class OnFailed>
89 void
90 onCertValidated(const shared_ptr<const Data>& signCertificate,
91 const shared_ptr<const Packet>& packet,
92 const OnValidated& onValidated,
93 const OnFailed& onValidationFailed);
94
95 template<class Packet, class OnFailed>
96 void
97 onCertFailed(const shared_ptr<const Data>& signCertificate,
98 const std::string& failureInfo,
99 const shared_ptr<const Packet>& packet,
100 const OnFailed& onValidationFailed);
101
102 void
Yingdi Yu48e8c0c2014-03-19 12:01:55 -0700103 onConfigRule(const security::conf::ConfigSection& section,
104 const std::string& filename);
105
106 void
107 onConfigTrustAnchor(const security::conf::ConfigSection& section,
108 const std::string& filename);
109
110private:
111 typedef security::conf::Rule<Interest> InterestRule;
112 typedef security::conf::Rule<Data> DataRule;
113 typedef std::vector<shared_ptr<InterestRule> > InterestRuleList;
114 typedef std::vector<shared_ptr<DataRule> > DataRuleList;
115 typedef std::map<Name, shared_ptr<IdentityCertificate> > AnchorList;
116
117 int m_stepLimit;
118 shared_ptr<CertificateCache> m_certificateCache;
119
120 InterestRuleList m_interestRules;
121 DataRuleList m_dataRules;
122 AnchorList m_anchors;
123};
124
125template<class Packet, class OnValidated, class OnFailed>
126void
127ValidatorConfig::checkSignature(const Packet& packet,
128 const Signature& signature,
Yingdi Yu4b8c6a22014-04-15 23:00:54 -0700129 int nSteps,
Yingdi Yu48e8c0c2014-03-19 12:01:55 -0700130 const OnValidated& onValidated,
131 const OnFailed& onValidationFailed,
132 std::vector<shared_ptr<ValidationRequest> >& nextSteps)
133{
134 if (signature.getType() == Signature::Sha256)
135 {
136 SignatureSha256 sigSha256(signature);
137
138 if (verifySignature(packet, sigSha256))
139 return onValidated(packet.shared_from_this());
140 else
141 return onValidationFailed(packet.shared_from_this(),
142 "Sha256 Signature cannot be verified!");
143 }
144
145 if (signature.getType() == Signature::Sha256WithRsa)
146 {
147 SignatureSha256WithRsa sigSha256Rsa(signature);
148 Name keyLocatorName = sigSha256Rsa.getKeyLocator().getName();
149
150 shared_ptr<const Certificate> trustedCert;
151
152 AnchorList::const_iterator it = m_anchors.find(keyLocatorName);
153 if (m_anchors.end() == it)
154 trustedCert = m_certificateCache->getCertificate(keyLocatorName);
155 else
156 trustedCert = it->second;
157
158 if (static_cast<bool>(trustedCert))
159 {
160 if (verifySignature(packet, sigSha256Rsa, trustedCert->getPublicKeyInfo()))
161 return onValidated(packet.shared_from_this());
162 else
163 return onValidationFailed(packet.shared_from_this(),
164 "Cannot verify signature");
165 }
166 else
167 {
168 OnDataValidated onCertValidated =
169 bind(&ValidatorConfig::onCertValidated<Packet, OnValidated, OnFailed>,
170 this, _1, packet.shared_from_this(), onValidated, onValidationFailed);
171
172 OnDataValidationFailed onCertValidationFailed =
173 bind(&ValidatorConfig::onCertFailed<Packet, OnFailed>,
174 this, _1, _2, packet.shared_from_this(), onValidationFailed);
175
176 Interest certInterest(keyLocatorName);
177
178 shared_ptr<ValidationRequest> nextStep =
179 make_shared<ValidationRequest>(boost::cref(certInterest),
180 onCertValidated,
181 onCertValidationFailed,
Yingdi Yu4b8c6a22014-04-15 23:00:54 -0700182 1, nSteps + 1);
Yingdi Yu48e8c0c2014-03-19 12:01:55 -0700183
184 nextSteps.push_back(nextStep);
185 return;
186 }
187 }
188 return onValidationFailed(packet.shared_from_this(), "Unsupported Signature Type!");
189}
190
191template<class Packet, class OnValidated, class OnFailed>
192void
193ValidatorConfig::onCertValidated(const shared_ptr<const Data>& signCertificate,
194 const shared_ptr<const Packet>& packet,
195 const OnValidated& onValidated,
196 const OnFailed& onValidationFailed)
197{
198 shared_ptr<IdentityCertificate> certificate =
199 make_shared<IdentityCertificate>(boost::cref(*signCertificate));
200
201 if (!certificate->isTooLate() && !certificate->isTooEarly())
202 {
203 m_certificateCache->insertCertificate(certificate);
204
205 if (verifySignature(*packet, certificate->getPublicKeyInfo()))
206 return onValidated(packet);
207 else
208 return onValidationFailed(packet,
209 "Cannot verify signature: " +
210 packet->getName().toUri());
211 }
212 else
213 {
214 return onValidationFailed(packet,
215 "Signing certificate " +
216 signCertificate->getName().toUri() +
217 " is no longer valid.");
218 }
219}
220
221template<class Packet, class OnFailed>
222void
223ValidatorConfig::onCertFailed(const shared_ptr<const Data>& signCertificate,
224 const std::string& failureInfo,
225 const shared_ptr<const Packet>& packet,
226 const OnFailed& onValidationFailed)
227{
228 onValidationFailed(packet, failureInfo);
229}
230
231} // namespace ndn
232
233#endif // NDN_SECURITY_VALIDATOR_CONFIG_HPP