blob: 7c8c300d3b9811138c4ae16a3a51b23850c22026 [file] [log] [blame]
Alexander Afanasyev8722d872014-07-02 13:00:29 -07001/* -*- Mode: C++; c-file-style: "gnu"; indent-tabs-mode:nil -*- */
Yingdi Yu0eee6002014-02-11 15:54:17 -08002/*
Alexander Afanasyev8722d872014-07-02 13:00:29 -07003 * Copyright (c) 2012-2014 University of California, Los Angeles
4 *
5 * This file is part of ChronoSync, synchronization library for distributed realtime
6 * applications for NDN.
7 *
8 * ChronoSync is free software: you can redistribute it and/or modify it under the terms
9 * of the GNU General Public License as published by the Free Software Foundation, either
10 * version 3 of the License, or (at your option) any later version.
11 *
12 * ChronoSync is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
13 * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR
14 * PURPOSE. See the GNU General Public License for more details.
15 *
16 * You should have received a copy of the GNU General Public License along with
17 * ChronoSync, e.g., in COPYING.md file. If not, see <http://www.gnu.org/licenses/>.
Yingdi Yu0eee6002014-02-11 15:54:17 -080018 */
19
20#include <boost/test/unit_test.hpp>
21#include "sync-validator.h"
22
Alexander Afanasyev7fe59832014-07-02 12:17:46 -070023#include <boost/lexical_cast.hpp>
24#include <boost/asio.hpp>
25#include <ndn-cxx/util/scheduler.hpp>
26
Yingdi Yu0eee6002014-02-11 15:54:17 -080027BOOST_AUTO_TEST_SUITE(TestSyncValidator)
28
Yingdi Yua873d642014-04-15 21:31:33 -070029void
Yingdi Yu3da10fe2014-02-27 16:37:34 -080030onValidated(const ndn::shared_ptr<const ndn::Data>& data)
Yingdi Yu0eee6002014-02-11 15:54:17 -080031{
32 BOOST_CHECK(true);
33}
34
Yingdi Yua873d642014-04-15 21:31:33 -070035void
Yingdi Yu3da10fe2014-02-27 16:37:34 -080036onValidationFailed(const ndn::shared_ptr<const ndn::Data>& data,
37 const std::string& failureInfo)
Yingdi Yu0eee6002014-02-11 15:54:17 -080038{
39 BOOST_CHECK(false);
40}
41
Yingdi Yua873d642014-04-15 21:31:33 -070042void
Yingdi Yu3da10fe2014-02-27 16:37:34 -080043onValidated2(const ndn::shared_ptr<const ndn::Data>& data)
Yingdi Yu0eee6002014-02-11 15:54:17 -080044{
45 BOOST_CHECK(false);
46}
47
Yingdi Yua873d642014-04-15 21:31:33 -070048void
Yingdi Yu3da10fe2014-02-27 16:37:34 -080049onValidationFailed2(const ndn::shared_ptr<const ndn::Data>& data,
50 const std::string& failureInfo)
Yingdi Yu0eee6002014-02-11 15:54:17 -080051{
52 BOOST_CHECK(true);
53}
54
Yingdi Yua873d642014-04-15 21:31:33 -070055void
Yingdi Yu3da10fe2014-02-27 16:37:34 -080056publishData(const uint8_t* buf, size_t len, int freshness)
57{
58}
59
Yingdi Yu0eee6002014-02-11 15:54:17 -080060BOOST_AUTO_TEST_CASE (Graph)
61{
62 using namespace Sync;
63 using namespace ndn;
64
65 Name prefix("/Sync/TestSyncValidator/AddEdge");
66 KeyChain keychain;
67
Yingdi Yu6e1c9cd2014-03-25 10:26:54 -070068 Name identity1("/TestSyncValidator/AddEdge-1/" + boost::lexical_cast<std::string>(ndn::time::toUnixTimestamp(ndn::time::system_clock::now()).count()));
Yingdi Yu0eee6002014-02-11 15:54:17 -080069 Name certName1 = keychain.createIdentity(identity1);
70 shared_ptr<IdentityCertificate> anchor = keychain.getCertificate(certName1);
71
Yingdi Yu6e1c9cd2014-03-25 10:26:54 -070072 Name identity2("/TestSyncValidator/AddEdge-2/" + boost::lexical_cast<std::string>(ndn::time::toUnixTimestamp(ndn::time::system_clock::now()).count()));
Yingdi Yu0eee6002014-02-11 15:54:17 -080073 Name certName2 = keychain.createIdentity(identity2);
74 shared_ptr<IdentityCertificate> introducer = keychain.getCertificate(certName2);
75
Yingdi Yu6e1c9cd2014-03-25 10:26:54 -070076 Name identity3("/TestSyncValidator/AddEdge-3/" + boost::lexical_cast<std::string>(ndn::time::toUnixTimestamp(ndn::time::system_clock::now()).count()));
Yingdi Yu0eee6002014-02-11 15:54:17 -080077 Name certName3 = keychain.createIdentity(identity3);
78 shared_ptr<IdentityCertificate> introducee = keychain.getCertificate(certName3);
79
Yingdi Yu6e1c9cd2014-03-25 10:26:54 -070080 Name identity4("/TestSyncValidator/AddEdge-4/" + boost::lexical_cast<std::string>(ndn::time::toUnixTimestamp(ndn::time::system_clock::now()).count()));
Yingdi Yu0eee6002014-02-11 15:54:17 -080081 Name certName4 = keychain.createIdentity(identity4);
82 shared_ptr<IdentityCertificate> introducer2 = keychain.getCertificate(certName4);
83
Yingdi Yu6e1c9cd2014-03-25 10:26:54 -070084 Name identity5("/TestSyncValidator/AddEdge-5/" + boost::lexical_cast<std::string>(ndn::time::toUnixTimestamp(ndn::time::system_clock::now()).count()));
Yingdi Yu0eee6002014-02-11 15:54:17 -080085 Name certName5 = keychain.createIdentity(identity5);
86 shared_ptr<IdentityCertificate> introducee2 = keychain.getCertificate(certName5);
87
88 shared_ptr<boost::asio::io_service> ioService = make_shared<boost::asio::io_service>();
Alexander Afanasyev7fe59832014-07-02 12:17:46 -070089 shared_ptr<Face> face = make_shared<Face>(ref(*ioService));
Yingdi Yu3da10fe2014-02-27 16:37:34 -080090 shared_ptr<SecRuleRelative> rule;
Yingdi Yua873d642014-04-15 21:31:33 -070091 SyncValidator validator(prefix, *anchor, *face,
Yingdi Yu3da10fe2014-02-27 16:37:34 -080092 bind(&publishData, _1, _2, _3),
93 rule);
Yingdi Yu0eee6002014-02-11 15:54:17 -080094
95 validator.addParticipant(*introducer);
96 BOOST_CHECK(validator.canTrust(certName2));
Yingdi Yua873d642014-04-15 21:31:33 -070097
Yingdi Yu0eee6002014-02-11 15:54:17 -080098 IntroCertificate introCert(prefix, *introducee, certName2.getPrefix(-1));
99 keychain.sign(introCert, certName2);
100 validator.addParticipant(introCert);
101 BOOST_CHECK(validator.canTrust(certName3));
102
103 IntroCertificate introCert1(prefix, *anchor, certName3.getPrefix(-1));
104 keychain.sign(introCert1, certName3);
105 validator.addParticipant(introCert1);
106 validator.setAnchor(*introducer);
107 BOOST_CHECK(validator.canTrust(certName2));
108 BOOST_CHECK(validator.canTrust(certName3));
109 BOOST_CHECK(validator.canTrust(certName1));
110
111 IntroCertificate introCert2(prefix, *introducee2, certName4.getPrefix(-1));
112 keychain.sign(introCert2, certName4);
113 validator.addParticipant(introCert2);
114 BOOST_CHECK(validator.canTrust(certName5) == false);
115 BOOST_CHECK(validator.canTrust(certName4) == false);
116
117 IntroCertificate introCert3(prefix, *introducee, certName5.getPrefix(-1));
118 keychain.sign(introCert3, certName5);
119 validator.addParticipant(introCert3);
120 BOOST_CHECK(validator.canTrust(certName5) == false);
121 BOOST_CHECK(validator.canTrust(certName4) == false);
122
123 validator.setAnchor(*introducee2);
124 BOOST_CHECK(validator.canTrust(certName1));
125 BOOST_CHECK(validator.canTrust(certName2));
126 BOOST_CHECK(validator.canTrust(certName3));
127 BOOST_CHECK(validator.canTrust(certName4) == false);
128 BOOST_CHECK(validator.canTrust(certName5));
Yingdi Yua873d642014-04-15 21:31:33 -0700129
Yingdi Yu0eee6002014-02-11 15:54:17 -0800130
131 keychain.deleteIdentity(identity1);
132 keychain.deleteIdentity(identity2);
133 keychain.deleteIdentity(identity3);
134 keychain.deleteIdentity(identity4);
135 keychain.deleteIdentity(identity5);
136}
137
138BOOST_AUTO_TEST_CASE (OfflineValidate)
139{
140 using namespace Sync;
141 using namespace ndn;
142
143 Name prefix("/Sync/TestSyncValidator/OfflineValidate");
144 KeyChain keychain;
145
Yingdi Yu6e1c9cd2014-03-25 10:26:54 -0700146 Name identity1("/TestSyncValidator/OfflineValidate-1/"
147 + boost::lexical_cast<std::string>(ndn::time::toUnixTimestamp(ndn::time::system_clock::now()).count()));
Yingdi Yu0eee6002014-02-11 15:54:17 -0800148 Name certName1 = keychain.createIdentity(identity1);
149 shared_ptr<IdentityCertificate> anchor = keychain.getCertificate(certName1);
150
Yingdi Yu6e1c9cd2014-03-25 10:26:54 -0700151 Name identity2("/TestSyncValidator/OfflineValidate-2/"
152 + boost::lexical_cast<std::string>(ndn::time::toUnixTimestamp(ndn::time::system_clock::now()).count()));
Yingdi Yu0eee6002014-02-11 15:54:17 -0800153 Name certName2 = keychain.createIdentity(identity2);
154 shared_ptr<IdentityCertificate> introducer = keychain.getCertificate(certName2);
155
Yingdi Yu6e1c9cd2014-03-25 10:26:54 -0700156 Name identity3("/TestSyncValidator/OfflineValidate-3/"
157 + boost::lexical_cast<std::string>(ndn::time::toUnixTimestamp(ndn::time::system_clock::now()).count()));
Yingdi Yu0eee6002014-02-11 15:54:17 -0800158 Name certName3 = keychain.createIdentity(identity3);
159 shared_ptr<IdentityCertificate> introducee = keychain.getCertificate(certName3);
160
Yingdi Yu6e1c9cd2014-03-25 10:26:54 -0700161 Name identity4("/TestSyncValidator/OfflineValidate-4/"
162 + boost::lexical_cast<std::string>(ndn::time::toUnixTimestamp(ndn::time::system_clock::now()).count()));
Yingdi Yu0eee6002014-02-11 15:54:17 -0800163 Name certName4 = keychain.createIdentity(identity4);
164 shared_ptr<IdentityCertificate> introducer2 = keychain.getCertificate(certName4);
165
Yingdi Yu6e1c9cd2014-03-25 10:26:54 -0700166 Name identity5("/TestSyncValidator/OfflineValidate-5/"
167 + boost::lexical_cast<std::string>(ndn::time::toUnixTimestamp(ndn::time::system_clock::now()).count()));
Yingdi Yu0eee6002014-02-11 15:54:17 -0800168 Name certName5 = keychain.createIdentity(identity5);
169 shared_ptr<IdentityCertificate> introducee2 = keychain.getCertificate(certName5);
170
171 shared_ptr<boost::asio::io_service> ioService = make_shared<boost::asio::io_service>();
Alexander Afanasyev7fe59832014-07-02 12:17:46 -0700172 shared_ptr<Face> face = make_shared<Face>(ref(*ioService));
Yingdi Yu3da10fe2014-02-27 16:37:34 -0800173 shared_ptr<SecRuleRelative> rule;
Yingdi Yua873d642014-04-15 21:31:33 -0700174 SyncValidator validator(prefix, *anchor, *face,
Yingdi Yu3da10fe2014-02-27 16:37:34 -0800175 bind(&publishData, _1, _2, _3),
176 rule);
Yingdi Yu0eee6002014-02-11 15:54:17 -0800177
178 validator.addParticipant(*introducer);
179 BOOST_CHECK(validator.canTrust(certName2));
Yingdi Yua873d642014-04-15 21:31:33 -0700180
Yingdi Yu0eee6002014-02-11 15:54:17 -0800181 IntroCertificate introCert(prefix, *introducee, certName2.getPrefix(-1));
182 keychain.sign(introCert, certName2);
183 validator.addParticipant(introCert);
184 BOOST_CHECK(validator.canTrust(certName3));
185
186 IntroCertificate introCert2(prefix, *introducee2, certName4.getPrefix(-1));
187 keychain.sign(introCert2, certName4);
188 validator.addParticipant(introCert2);
189 BOOST_CHECK(validator.canTrust(certName5) == false);
190 BOOST_CHECK(validator.canTrust(certName4) == false);
191
192 validator.setAnchor(*introducer2);
193 BOOST_CHECK(validator.canTrust(certName1) == false);
194 BOOST_CHECK(validator.canTrust(certName2) == false);
195 BOOST_CHECK(validator.canTrust(certName3) == false);
196 BOOST_CHECK(validator.canTrust(certName4));
197 BOOST_CHECK(validator.canTrust(certName5));
198
199 Name dataName1 = prefix;
200 dataName1.append("data-1");
201 shared_ptr<Data> data1 = make_shared<Data>(dataName1);
202 keychain.sign(*data1, certName5);
203
204 validator.validate(*data1,
205 bind(&onValidated, _1),
206 bind(&onValidationFailed, _1, _2));
207
208 Name dataName2 = prefix;
209 dataName2.append("data-2");
210 shared_ptr<Data> data2 = make_shared<Data>(dataName2);
211 keychain.sign(*data2, certName1);
212
213 validator.validate(*data2,
214 bind(&onValidated2, _1),
215 bind(&onValidationFailed2, _1, _2));
216
Yingdi Yu6e1c9cd2014-03-25 10:26:54 -0700217 // ioService->run();
Yingdi Yu0eee6002014-02-11 15:54:17 -0800218
219 keychain.deleteIdentity(identity1);
220 keychain.deleteIdentity(identity2);
221 keychain.deleteIdentity(identity3);
222 keychain.deleteIdentity(identity4);
223 keychain.deleteIdentity(identity5);
224}
225
Yingdi Yu6e1c9cd2014-03-25 10:26:54 -0700226struct FacesFixture
227{
228 FacesFixture()
229 : regPrefixId(0)
230 , regPrefixId2(0)
231 {}
Yingdi Yua873d642014-04-15 21:31:33 -0700232
Yingdi Yu6e1c9cd2014-03-25 10:26:54 -0700233 void
234 onInterest(ndn::shared_ptr<ndn::Face> face, ndn::shared_ptr<ndn::Data> data)
235 {
236 face->put(*data);
237 face->unsetInterestFilter(regPrefixId);
238 }
239
240 void
241 onInterest2(ndn::shared_ptr<ndn::Face> face, ndn::shared_ptr<ndn::Data> data)
242 {
243 face->put(*data);
244 face->unsetInterestFilter(regPrefixId2);
245 }
246
247 void
248 onRegFailed()
249 {}
250
251 void
Yingdi Yua873d642014-04-15 21:31:33 -0700252 validate(ndn::shared_ptr<Sync::SyncValidator> validator, ndn::shared_ptr<ndn::Data> data,
Yingdi Yu6e1c9cd2014-03-25 10:26:54 -0700253 const ndn::Name& certName3, const ndn::Name& certName4)
254 {
255 validator->validate(*data,
256 bind(&onValidated, _1),
257 bind(&onValidationFailed, _1, _2));
258
259
260 BOOST_CHECK(validator->canTrust(certName3));
261 BOOST_CHECK(validator->canTrust(certName4));
262 }
263
264 void
265 terminate(ndn::shared_ptr<ndn::Face> face)
266 {
Alexander Afanasyev7fe59832014-07-02 12:17:46 -0700267 face->getIoService().stop();
Yingdi Yu6e1c9cd2014-03-25 10:26:54 -0700268 }
269
270 const ndn::RegisteredPrefixId* regPrefixId;
271 const ndn::RegisteredPrefixId* regPrefixId2;
272};
273
274BOOST_FIXTURE_TEST_CASE(OnlineValidate, FacesFixture)
Yingdi Yu0eee6002014-02-11 15:54:17 -0800275{
276 using namespace Sync;
277 using namespace ndn;
278
279 Name prefix("/Sync/TestSyncValidator/OnlineValidate");
280 KeyChain keychain;
281
Yingdi Yua873d642014-04-15 21:31:33 -0700282 Name identity1("/TestSyncValidator/OnlineValidate-1/"
Yingdi Yu6e1c9cd2014-03-25 10:26:54 -0700283 + boost::lexical_cast<std::string>(ndn::time::toUnixTimestamp(ndn::time::system_clock::now()).count()));
Yingdi Yu0eee6002014-02-11 15:54:17 -0800284 Name certName1 = keychain.createIdentity(identity1);
285 shared_ptr<IdentityCertificate> anchor = keychain.getCertificate(certName1);
286
Yingdi Yua873d642014-04-15 21:31:33 -0700287 Name identity2("/TestSyncValidator/OnlineValidate-2/"
Yingdi Yu6e1c9cd2014-03-25 10:26:54 -0700288 + boost::lexical_cast<std::string>(ndn::time::toUnixTimestamp(ndn::time::system_clock::now()).count()));
Yingdi Yu0eee6002014-02-11 15:54:17 -0800289 Name certName2 = keychain.createIdentity(identity2);
290 shared_ptr<IdentityCertificate> introducer = keychain.getCertificate(certName2);
291
Yingdi Yua873d642014-04-15 21:31:33 -0700292 Name identity3("/TestSyncValidator/OnlineValidate-3/"
Yingdi Yu6e1c9cd2014-03-25 10:26:54 -0700293 + boost::lexical_cast<std::string>(ndn::time::toUnixTimestamp(ndn::time::system_clock::now()).count()));
Yingdi Yu0eee6002014-02-11 15:54:17 -0800294 Name certName3 = keychain.createIdentity(identity3);
295 shared_ptr<IdentityCertificate> introducee = keychain.getCertificate(certName3);
296
Yingdi Yu6e1c9cd2014-03-25 10:26:54 -0700297 Name identity4("/TestSyncValidator/OnlineValidate-4/"
298 + boost::lexical_cast<std::string>(ndn::time::toUnixTimestamp(ndn::time::system_clock::now()).count()));
Yingdi Yu0eee6002014-02-11 15:54:17 -0800299 Name certName4 = keychain.createIdentity(identity4);
300 shared_ptr<IdentityCertificate> introducee2 = keychain.getCertificate(certName4);
301
302 shared_ptr<boost::asio::io_service> ioService = make_shared<boost::asio::io_service>();
Alexander Afanasyev7fe59832014-07-02 12:17:46 -0700303 shared_ptr<Face> face = make_shared<Face>(ref(*ioService));
304 shared_ptr<Face> face2 = make_shared<Face>(ref(*ioService));
Yingdi Yu6e1c9cd2014-03-25 10:26:54 -0700305
Yingdi Yu3da10fe2014-02-27 16:37:34 -0800306 shared_ptr<SecRuleRelative> rule;
Yingdi Yu6e1c9cd2014-03-25 10:26:54 -0700307 shared_ptr<SyncValidator> validator = shared_ptr<SyncValidator>
Yingdi Yua873d642014-04-15 21:31:33 -0700308 (new SyncValidator(prefix, *anchor, *face2, bind(&publishData, _1, _2, _3), rule));
Yingdi Yu0eee6002014-02-11 15:54:17 -0800309
Yingdi Yu6e1c9cd2014-03-25 10:26:54 -0700310 validator->addParticipant(*introducer);
311 BOOST_CHECK(validator->canTrust(certName2));
Yingdi Yua873d642014-04-15 21:31:33 -0700312
Yingdi Yu6e1c9cd2014-03-25 10:26:54 -0700313 shared_ptr<IntroCertificate> introCert = shared_ptr<IntroCertificate>(new IntroCertificate(prefix, *introducee, certName2.getPrefix(-1)));
314 keychain.sign(*introCert, certName2);
315 BOOST_CHECK(validator->canTrust(certName3) == false);
Yingdi Yu0eee6002014-02-11 15:54:17 -0800316
Yingdi Yu6e1c9cd2014-03-25 10:26:54 -0700317 shared_ptr<IntroCertificate> introCert2 = shared_ptr<IntroCertificate>(new IntroCertificate(prefix, *introducee2, certName3.getPrefix(-1)));
318 keychain.sign(*introCert2, certName3);
319 BOOST_CHECK(validator->canTrust(certName4) == false);
Yingdi Yu0eee6002014-02-11 15:54:17 -0800320
321 Name dataName1 = prefix;
322 dataName1.append("data-1");
323 shared_ptr<Data> data1 = make_shared<Data>(dataName1);
324 keychain.sign(*data1, certName4);
325
Yingdi Yu6e1c9cd2014-03-25 10:26:54 -0700326 ndn::Scheduler scheduler(*ioService);
Yingdi Yu0eee6002014-02-11 15:54:17 -0800327
Yingdi Yu6e1c9cd2014-03-25 10:26:54 -0700328 scheduler.scheduleEvent(time::seconds(1),
329 bind(&FacesFixture::terminate, this, face));
Yingdi Yu0eee6002014-02-11 15:54:17 -0800330
Yingdi Yu6e1c9cd2014-03-25 10:26:54 -0700331 regPrefixId = face->setInterestFilter(introCert->getName().getPrefix(-1),
332 bind(&FacesFixture::onInterest, this, face, introCert),
333 bind(&FacesFixture::onRegFailed, this));
Yingdi Yua873d642014-04-15 21:31:33 -0700334
Yingdi Yu6e1c9cd2014-03-25 10:26:54 -0700335 regPrefixId2 = face->setInterestFilter(introCert2->getName().getPrefix(-1),
336 bind(&FacesFixture::onInterest2, this, face, introCert2),
337 bind(&FacesFixture::onRegFailed, this));
338
339 scheduler.scheduleEvent(time::milliseconds(200),
340 bind(&FacesFixture::validate, this,
341 validator, data1, certName3, certName4));
Yingdi Yu0eee6002014-02-11 15:54:17 -0800342
343 keychain.deleteIdentity(identity1);
344 keychain.deleteIdentity(identity2);
345 keychain.deleteIdentity(identity3);
346 keychain.deleteIdentity(identity4);
347}
348
349BOOST_AUTO_TEST_SUITE_END()