blob: e48158c39d7513a6259f2e0097d5ec92727aa223 [file] [log] [blame]
akmhoque3d06e792014-05-27 16:23:20 -05001/* -*- Mode:C++; c-file-style:"gnu"; indent-tabs-mode:nil; -*- */
2/**
Nick Gordonfeae5572017-01-13 12:06:26 -06003 * Copyright (c) 2014-2017, The University of Memphis,
Vince Lehmanc2e51f62015-01-20 15:03:11 -06004 * Regents of the University of California,
5 * Arizona Board of Regents.
akmhoque3d06e792014-05-27 16:23:20 -05006 *
7 * This file is part of NLSR (Named-data Link State Routing).
8 * See AUTHORS.md for complete list of NLSR authors and contributors.
9 *
10 * NLSR is free software: you can redistribute it and/or modify it under the terms
11 * of the GNU General Public License as published by the Free Software Foundation,
12 * either version 3 of the License, or (at your option) any later version.
13 *
14 * NLSR is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
15 * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR
16 * PURPOSE. See the GNU General Public License for more details.
17 *
18 * You should have received a copy of the GNU General Public License along with
19 * NLSR, e.g., in COPYING.md file. If not, see <http://www.gnu.org/licenses/>.
akmhoque3d06e792014-05-27 16:23:20 -050020 **/
Vince Lehmanc2e51f62015-01-20 15:03:11 -060021
Ashlesh Gawande3909aa12017-07-28 16:01:35 -050022#include "conf-file-processor.hpp"
Nick Gordond0a7df32017-05-30 16:44:34 -050023#include "conf-parameter.hpp"
Ashlesh Gawande3909aa12017-07-28 16:01:35 -050024#include "adjacent.hpp"
25#include "utility/name-helper.hpp"
26#include "update/prefix-update-processor.hpp"
27
akmhoque53353462014-04-22 08:43:45 -050028#include <iostream>
29#include <fstream>
Alexander Afanasyevb669f9c2014-11-14 12:41:54 -080030
31#include <ndn-cxx/name.hpp>
alvy2fe12872014-11-25 10:32:23 -060032#include <ndn-cxx/util/face-uri.hpp>
Alexander Afanasyevb669f9c2014-11-14 12:41:54 -080033
34// boost needs to be included after ndn-cxx, otherwise there will be conflict with _1, _2, ...
akmhoque157b0a42014-05-13 00:26:37 -050035#include <boost/algorithm/string.hpp>
36#include <boost/property_tree/info_parser.hpp>
37#include <boost/property_tree/ptree.hpp>
akmhoque674b0b12014-05-20 14:33:28 -050038#include <boost/filesystem.hpp>
akmhoque53353462014-04-22 08:43:45 -050039
akmhoque53353462014-04-22 08:43:45 -050040namespace nlsr {
41
42using namespace std;
43
Vince Lehman7b616582014-10-17 16:25:39 -050044template <class T>
45class ConfigurationVariable
46{
47public:
dmcoomes9f936662017-03-02 10:33:09 -060048 typedef std::function<void(T)> ConfParameterCallback;
Vince Lehman7b616582014-10-17 16:25:39 -050049 typedef boost::property_tree::ptree ConfigSection;
50
51 ConfigurationVariable(const std::string& key, const ConfParameterCallback& setter)
52 : m_key(key)
53 , m_setterCallback(setter)
54 , m_minValue(0)
55 , m_maxValue(0)
56 , m_shouldCheckRange(false)
57 , m_isRequired(true)
58 {
59 }
60
61 bool
62 parseFromConfigSection(const ConfigSection& section)
63 {
64 try {
65 T value = section.get<T>(m_key);
66
67 if (!isValidValue(value)) {
68 return false;
69 }
70
71 m_setterCallback(value);
72 return true;
73 }
74 catch (const std::exception& ex) {
75
76 if (m_isRequired) {
77 std::cerr << ex.what() << std::endl;
78 std::cerr << "Missing required configuration variable" << std::endl;
79 return false;
80 }
81 else {
82 m_setterCallback(m_defaultValue);
83 return true;
84 }
85 }
86
87 return false;
88 }
89
90 void
91 setMinAndMaxValue(T min, T max)
92 {
93 m_minValue = min;
94 m_maxValue = max;
95 m_shouldCheckRange = true;
96 }
97
98 void
99 setOptional(T defaultValue)
100 {
101 m_isRequired = false;
102 m_defaultValue = defaultValue;
103 }
104
105private:
106 void
107 printOutOfRangeError(T value)
108 {
109 std::cerr << "Invalid value for " << m_key << ": "
110 << value << ". "
111 << "Valid values: "
112 << m_minValue << " - "
113 << m_maxValue << std::endl;
114 }
115
116 bool
117 isValidValue(T value)
118 {
119 if (!m_shouldCheckRange) {
120 return true;
121 }
122 else if (value < m_minValue || value > m_maxValue)
123 {
124 printOutOfRangeError(value);
125 return false;
126 }
127
128 return true;
129 }
130
131private:
132 const std::string m_key;
133 const ConfParameterCallback m_setterCallback;
134 T m_defaultValue;
135
136 T m_minValue;
137 T m_maxValue;
138
139 bool m_shouldCheckRange;
140 bool m_isRequired;
141};
142
akmhoque157b0a42014-05-13 00:26:37 -0500143bool
akmhoqueb6450b12014-04-24 00:01:03 -0500144ConfFileProcessor::processConfFile()
akmhoque53353462014-04-22 08:43:45 -0500145{
akmhoque157b0a42014-05-13 00:26:37 -0500146 bool ret = true;
147 ifstream inputFile;
148 inputFile.open(m_confFileName.c_str());
149 if (!inputFile.is_open()) {
150 string msg = "Failed to read configuration file: ";
151 msg += m_confFileName;
152 cerr << msg << endl;
akmhoquead5fe952014-06-26 13:34:12 -0500153 return false;
akmhoque157b0a42014-05-13 00:26:37 -0500154 }
155 ret = load(inputFile);
156 inputFile.close();
157 return ret;
158}
159
160bool
161ConfFileProcessor::load(istream& input)
162{
Alexander Afanasyev8388ec62014-08-16 18:38:57 -0700163 ConfigSection pt;
akmhoque157b0a42014-05-13 00:26:37 -0500164 bool ret = true;
165 try {
166 boost::property_tree::read_info(input, pt);
167 }
168 catch (const boost::property_tree::info_parser_error& error) {
169 stringstream msg;
170 std::cerr << "Failed to parse configuration file " << std::endl;
171 std::cerr << m_confFileName << std::endl;
172 return false;
173 }
Alexander Afanasyev8388ec62014-08-16 18:38:57 -0700174
175 for (ConfigSection::const_iterator tn = pt.begin();
akmhoque157b0a42014-05-13 00:26:37 -0500176 tn != pt.end(); ++tn) {
Alexander Afanasyev8388ec62014-08-16 18:38:57 -0700177 ret = processSection(tn->first, tn->second);
akmhoque157b0a42014-05-13 00:26:37 -0500178 if (ret == false) {
179 break;
180 }
181 }
182 return ret;
183}
184
185bool
Alexander Afanasyev8388ec62014-08-16 18:38:57 -0700186ConfFileProcessor::processSection(const std::string& sectionName, const ConfigSection& section)
akmhoque157b0a42014-05-13 00:26:37 -0500187{
188 bool ret = true;
Alexander Afanasyev8388ec62014-08-16 18:38:57 -0700189 if (sectionName == "general")
akmhoque53353462014-04-22 08:43:45 -0500190 {
Alexander Afanasyev8388ec62014-08-16 18:38:57 -0700191 ret = processConfSectionGeneral(section);
akmhoque157b0a42014-05-13 00:26:37 -0500192 }
Alexander Afanasyev8388ec62014-08-16 18:38:57 -0700193 else if (sectionName == "neighbors")
akmhoque157b0a42014-05-13 00:26:37 -0500194 {
Alexander Afanasyev8388ec62014-08-16 18:38:57 -0700195 ret = processConfSectionNeighbors(section);
akmhoque157b0a42014-05-13 00:26:37 -0500196 }
Alexander Afanasyev8388ec62014-08-16 18:38:57 -0700197 else if (sectionName == "hyperbolic")
akmhoque157b0a42014-05-13 00:26:37 -0500198 {
Alexander Afanasyev8388ec62014-08-16 18:38:57 -0700199 ret = processConfSectionHyperbolic(section);
akmhoque157b0a42014-05-13 00:26:37 -0500200 }
Alexander Afanasyev8388ec62014-08-16 18:38:57 -0700201 else if (sectionName == "fib")
akmhoque157b0a42014-05-13 00:26:37 -0500202 {
Alexander Afanasyev8388ec62014-08-16 18:38:57 -0700203 ret = processConfSectionFib(section);
akmhoque157b0a42014-05-13 00:26:37 -0500204 }
Alexander Afanasyev8388ec62014-08-16 18:38:57 -0700205 else if (sectionName == "advertising")
akmhoque157b0a42014-05-13 00:26:37 -0500206 {
Alexander Afanasyev8388ec62014-08-16 18:38:57 -0700207 ret = processConfSectionAdvertising(section);
akmhoque157b0a42014-05-13 00:26:37 -0500208 }
Alexander Afanasyev8388ec62014-08-16 18:38:57 -0700209 else if (sectionName == "security")
Yingdi Yu20e3a6e2014-05-26 23:16:10 -0700210 {
Alexander Afanasyev8388ec62014-08-16 18:38:57 -0700211 ret = processConfSectionSecurity(section);
Yingdi Yu20e3a6e2014-05-26 23:16:10 -0700212 }
akmhoque157b0a42014-05-13 00:26:37 -0500213 else
214 {
Alexander Afanasyev8388ec62014-08-16 18:38:57 -0700215 std::cerr << "Wrong configuration section: " << sectionName << std::endl;
akmhoque157b0a42014-05-13 00:26:37 -0500216 }
217 return ret;
218}
219
220bool
Alexander Afanasyev8388ec62014-08-16 18:38:57 -0700221ConfFileProcessor::processConfSectionGeneral(const ConfigSection& section)
akmhoque157b0a42014-05-13 00:26:37 -0500222{
223 try {
Alexander Afanasyev8388ec62014-08-16 18:38:57 -0700224 std::string network = section.get<string>("network");
225 std::string site = section.get<string>("site");
226 std::string router = section.get<string>("router");
akmhoque157b0a42014-05-13 00:26:37 -0500227 ndn::Name networkName(network);
228 if (!networkName.empty()) {
229 m_nlsr.getConfParameter().setNetwork(networkName);
230 }
231 else {
232 cerr << " Network can not be null or empty or in bad URI format :(!" << endl;
233 return false;
234 }
235 ndn::Name siteName(site);
236 if (!siteName.empty()) {
237 m_nlsr.getConfParameter().setSiteName(siteName);
238 }
239 else {
240 cerr << "Site can not be null or empty or in bad URI format:( !" << endl;
241 return false;
242 }
243 ndn::Name routerName(router);
244 if (!routerName.empty()) {
245 m_nlsr.getConfParameter().setRouterName(routerName);
246 }
247 else {
248 cerr << " Router name can not be null or empty or in bad URI format:( !" << endl;
249 return false;
250 }
251 }
252 catch (const std::exception& ex) {
253 cerr << ex.what() << endl;
254 return false;
255 }
Yingdi Yu20e3a6e2014-05-26 23:16:10 -0700256
alvya2228c62014-12-09 10:25:11 -0600257 // lsa-refresh-time
alvy5a454952014-12-15 12:49:54 -0600258 uint32_t lsaRefreshTime = section.get<uint32_t>("lsa-refresh-time", LSA_REFRESH_TIME_DEFAULT);
alvya2228c62014-12-09 10:25:11 -0600259
260 if (lsaRefreshTime >= LSA_REFRESH_TIME_MIN && lsaRefreshTime <= LSA_REFRESH_TIME_MAX) {
261 m_nlsr.getConfParameter().setLsaRefreshTime(lsaRefreshTime);
akmhoque157b0a42014-05-13 00:26:37 -0500262 }
alvya2228c62014-12-09 10:25:11 -0600263 else {
264 std::cerr << "Wrong value for lsa-refresh-time ";
265 std::cerr << "Allowed value: " << LSA_REFRESH_TIME_MIN << "-";;
266 std::cerr << LSA_REFRESH_TIME_MAX << std::endl;
267
268 return false;
269 }
270
271 // router-dead-interval
alvy5a454952014-12-15 12:49:54 -0600272 uint32_t routerDeadInterval = section.get<uint32_t>("router-dead-interval", (2*lsaRefreshTime));
alvya2228c62014-12-09 10:25:11 -0600273
274 if (routerDeadInterval > m_nlsr.getConfParameter().getLsaRefreshTime()) {
275 m_nlsr.getConfParameter().setRouterDeadInterval(routerDeadInterval);
276 }
277 else {
278 std::cerr << "Value of router-dead-interval must be larger than lsa-refresh-time" << std::endl;
279 return false;
280 }
281
282 // lsa-interest-lifetime
283 int lifetime = section.get<int>("lsa-interest-lifetime", LSA_INTEREST_LIFETIME_DEFAULT);
284
285 if (lifetime >= LSA_INTEREST_LIFETIME_MIN && lifetime <= LSA_INTEREST_LIFETIME_MAX) {
286 m_nlsr.getConfParameter().setLsaInterestLifetime(ndn::time::seconds(lifetime));
287 }
288 else {
289 std::cerr << "Wrong value for lsa-interest-timeout. "
290 << "Allowed value:" << LSA_INTEREST_LIFETIME_MIN << "-"
291 << LSA_INTEREST_LIFETIME_MAX << std::endl;
292
akmhoque157b0a42014-05-13 00:26:37 -0500293 return false;
294 }
Yingdi Yu20e3a6e2014-05-26 23:16:10 -0700295
alvyd5a13cd2015-01-06 16:34:38 -0600296 // log-level
297 std::string logLevel = section.get<string>("log-level", "INFO");
Vince Lehmanf99b87f2014-08-26 15:54:27 -0500298
alvyd5a13cd2015-01-06 16:34:38 -0600299 if (isValidLogLevel(logLevel)) {
300 m_nlsr.getConfParameter().setLogLevel(logLevel);
akmhoque157b0a42014-05-13 00:26:37 -0500301 }
alvyd5a13cd2015-01-06 16:34:38 -0600302 else {
303 std::cerr << "Invalid value for log-level ";
304 std::cerr << "Valid values: ALL, TRACE, DEBUG, INFO, WARN, ERROR, NONE" << std::endl;
akmhoque157b0a42014-05-13 00:26:37 -0500305 return false;
306 }
Yingdi Yu20e3a6e2014-05-26 23:16:10 -0700307
akmhoque674b0b12014-05-20 14:33:28 -0500308 try {
Alexander Afanasyev8388ec62014-08-16 18:38:57 -0700309 std::string logDir = section.get<string>("log-dir");
akmhoque674b0b12014-05-20 14:33:28 -0500310 if (boost::filesystem::exists(logDir)) {
311 if (boost::filesystem::is_directory(logDir)) {
312 std::string testFileName=logDir+"/test.log";
313 ofstream testOutFile;
314 testOutFile.open(testFileName.c_str());
315 if (testOutFile.is_open() && testOutFile.good()) {
316 m_nlsr.getConfParameter().setLogDir(logDir);
317 }
318 else {
319 std::cerr << "User does not have read and write permission on the directory";
320 std::cerr << std::endl;
321 return false;
322 }
323 testOutFile.close();
324 remove(testFileName.c_str());
325 }
326 else {
327 std::cerr << "Provided path is not a directory" << std::endl;
328 return false;
329 }
330 }
331 else {
Muktadir R Chowdhurybfa27602014-10-31 10:57:41 -0500332 std::cerr << "Provided log directory <" << logDir << "> does not exist" << std::endl;
akmhoque674b0b12014-05-20 14:33:28 -0500333 return false;
334 }
335 }
336 catch (const std::exception& ex) {
337 std::cerr << "You must configure log directory" << std::endl;
338 std::cerr << ex.what() << std::endl;
339 return false;
340 }
Muktadir R Chowdhurybfa27602014-10-31 10:57:41 -0500341
akmhoque674b0b12014-05-20 14:33:28 -0500342 try {
Alexander Afanasyev8388ec62014-08-16 18:38:57 -0700343 std::string seqDir = section.get<string>("seq-dir");
akmhoque674b0b12014-05-20 14:33:28 -0500344 if (boost::filesystem::exists(seqDir)) {
345 if (boost::filesystem::is_directory(seqDir)) {
346 std::string testFileName=seqDir+"/test.seq";
347 ofstream testOutFile;
348 testOutFile.open(testFileName.c_str());
349 if (testOutFile.is_open() && testOutFile.good()) {
350 m_nlsr.getConfParameter().setSeqFileDir(seqDir);
351 }
352 else {
353 std::cerr << "User does not have read and write permission on the directory";
354 std::cerr << std::endl;
355 return false;
356 }
357 testOutFile.close();
358 remove(testFileName.c_str());
359 }
360 else {
361 std::cerr << "Provided path is not a directory" << std::endl;
362 return false;
363 }
364 }
365 else {
Muktadir R Chowdhurybfa27602014-10-31 10:57:41 -0500366 std::cerr << "Provided sequence directory <" << seqDir << "> does not exist" << std::endl;
akmhoque674b0b12014-05-20 14:33:28 -0500367 return false;
368 }
369 }
370 catch (const std::exception& ex) {
371 std::cerr << "You must configure sequence directory" << std::endl;
372 std::cerr << ex.what() << std::endl;
373 return false;
374 }
Yingdi Yu20e3a6e2014-05-26 23:16:10 -0700375
Muktadir R Chowdhurybfa27602014-10-31 10:57:41 -0500376 try {
377 std::string log4cxxPath = section.get<string>("log4cxx-conf");
378
379 if (log4cxxPath == "") {
380 std::cerr << "No value provided for log4cxx-conf" << std::endl;
381 return false;
382 }
383
384 if (boost::filesystem::exists(log4cxxPath)) {
385 m_nlsr.getConfParameter().setLog4CxxConfPath(log4cxxPath);
386 }
387 else {
388 std::cerr << "Provided path for log4cxx-conf <" << log4cxxPath
389 << "> does not exist" << std::endl;
390
391 return false;
392 }
393 }
394 catch (const std::exception& ex) {
395 // Variable is optional so default configuration will be used; continue processing file
396 }
397
akmhoque157b0a42014-05-13 00:26:37 -0500398 return true;
399}
400
401bool
Alexander Afanasyev8388ec62014-08-16 18:38:57 -0700402ConfFileProcessor::processConfSectionNeighbors(const ConfigSection& section)
akmhoque157b0a42014-05-13 00:26:37 -0500403{
alvya2228c62014-12-09 10:25:11 -0600404 // hello-retries
405 int retrials = section.get<int>("hello-retries", HELLO_RETRIES_DEFAULT);
406
407 if (retrials >= HELLO_RETRIES_MIN && retrials <= HELLO_RETRIES_MAX) {
408 m_nlsr.getConfParameter().setInterestRetryNumber(retrials);
akmhoque157b0a42014-05-13 00:26:37 -0500409 }
alvya2228c62014-12-09 10:25:11 -0600410 else {
411 std::cerr << "Wrong value for hello-retries." << std::endl;
412 std::cerr << "Allowed value:" << HELLO_RETRIES_MIN << "-";
413 std::cerr << HELLO_RETRIES_MAX << std::endl;
414
akmhoque157b0a42014-05-13 00:26:37 -0500415 return false;
416 }
alvya2228c62014-12-09 10:25:11 -0600417
418 // hello-timeout
alvy5a454952014-12-15 12:49:54 -0600419 uint32_t timeOut = section.get<uint32_t>("hello-timeout", HELLO_TIMEOUT_DEFAULT);
alvya2228c62014-12-09 10:25:11 -0600420
421 if (timeOut >= HELLO_TIMEOUT_MIN && timeOut <= HELLO_TIMEOUT_MAX) {
422 m_nlsr.getConfParameter().setInterestResendTime(timeOut);
akmhoque157b0a42014-05-13 00:26:37 -0500423 }
alvya2228c62014-12-09 10:25:11 -0600424 else {
425 std::cerr << "Wrong value for hello-timeout. ";
426 std::cerr << "Allowed value:" << HELLO_TIMEOUT_MIN << "-";
427 std::cerr << HELLO_TIMEOUT_MAX << std::endl;
428
429 return false;
akmhoque157b0a42014-05-13 00:26:37 -0500430 }
alvya2228c62014-12-09 10:25:11 -0600431
432 // hello-interval
alvy5a454952014-12-15 12:49:54 -0600433 uint32_t interval = section.get<uint32_t>("hello-interval", HELLO_INTERVAL_DEFAULT);
alvya2228c62014-12-09 10:25:11 -0600434
435 if (interval >= HELLO_INTERVAL_MIN && interval <= HELLO_INTERVAL_MAX) {
436 m_nlsr.getConfParameter().setInfoInterestInterval(interval);
akmhoque157b0a42014-05-13 00:26:37 -0500437 }
alvya2228c62014-12-09 10:25:11 -0600438 else {
439 std::cerr << "Wrong value for hello-interval. ";
440 std::cerr << "Allowed value:" << HELLO_INTERVAL_MIN << "-";
441 std::cerr << HELLO_INTERVAL_MAX << std::endl;
442
443 return false;
akmhoque157b0a42014-05-13 00:26:37 -0500444 }
Vince Lehman7b616582014-10-17 16:25:39 -0500445
446 // Event intervals
447 // adj-lsa-build-interval
448 ConfigurationVariable<uint32_t> adjLsaBuildInterval("adj-lsa-build-interval",
dmcoomes9f936662017-03-02 10:33:09 -0600449 std::bind(&ConfParameter::setAdjLsaBuildInterval,
Vince Lehman7b616582014-10-17 16:25:39 -0500450 &m_nlsr.getConfParameter(), _1));
451 adjLsaBuildInterval.setMinAndMaxValue(ADJ_LSA_BUILD_INTERVAL_MIN, ADJ_LSA_BUILD_INTERVAL_MAX);
452 adjLsaBuildInterval.setOptional(ADJ_LSA_BUILD_INTERVAL_DEFAULT);
453
454 if (!adjLsaBuildInterval.parseFromConfigSection(section)) {
455 return false;
456 }
Nick Gordond5c1a372016-10-31 13:56:23 -0500457 // Set the retry count for fetching the FaceStatus dataset
458 ConfigurationVariable<uint32_t> faceDatasetFetchTries("face-dataset-fetch-tries",
459 std::bind(&ConfParameter::setFaceDatasetFetchTries,
460 &m_nlsr.getConfParameter(),
461 _1));
462
463 faceDatasetFetchTries.setMinAndMaxValue(FACE_DATASET_FETCH_TRIES_MIN,
464 FACE_DATASET_FETCH_TRIES_MAX);
465 faceDatasetFetchTries.setOptional(FACE_DATASET_FETCH_TRIES_DEFAULT);
466
467 if (!faceDatasetFetchTries.parseFromConfigSection(section)) {
468 return false;
469 }
470
471 // Set the interval between FaceStatus dataset fetch attempts.
Ashlesh Gawande3909aa12017-07-28 16:01:35 -0500472 ConfigurationVariable<uint32_t> faceDatasetFetchInterval("face-dataset-fetch-interval",
Nick Gordond5c1a372016-10-31 13:56:23 -0500473 bind(&ConfParameter::setFaceDatasetFetchInterval,
474 &m_nlsr.getConfParameter(),
475 _1));
476
Ashlesh Gawande3909aa12017-07-28 16:01:35 -0500477 faceDatasetFetchInterval.setMinAndMaxValue(FACE_DATASET_FETCH_INTERVAL_MIN,
478 FACE_DATASET_FETCH_INTERVAL_MAX);
479 faceDatasetFetchInterval.setOptional(FACE_DATASET_FETCH_INTERVAL_DEFAULT);
Nick Gordond5c1a372016-10-31 13:56:23 -0500480
481 if (!faceDatasetFetchInterval.parseFromConfigSection(section)) {
482 return false;
483 }
Vince Lehman7b616582014-10-17 16:25:39 -0500484
485 // first-hello-interval
486 ConfigurationVariable<uint32_t> firstHelloInterval("first-hello-interval",
dmcoomes9f936662017-03-02 10:33:09 -0600487 std::bind(&ConfParameter::setFirstHelloInterval,
Vince Lehman7b616582014-10-17 16:25:39 -0500488 &m_nlsr.getConfParameter(), _1));
489 firstHelloInterval.setMinAndMaxValue(FIRST_HELLO_INTERVAL_MIN, FIRST_HELLO_INTERVAL_MAX);
490 firstHelloInterval.setOptional(FIRST_HELLO_INTERVAL_DEFAULT);
491
492 if (!firstHelloInterval.parseFromConfigSection(section)) {
493 return false;
494 }
495
Alexander Afanasyev8388ec62014-08-16 18:38:57 -0700496 for (ConfigSection::const_iterator tn =
497 section.begin(); tn != section.end(); ++tn) {
Yingdi Yu20e3a6e2014-05-26 23:16:10 -0700498
Nick Gordond5c1a372016-10-31 13:56:23 -0500499 if (tn->first == "neighbor") {
akmhoque157b0a42014-05-13 00:26:37 -0500500 try {
Alexander Afanasyev8388ec62014-08-16 18:38:57 -0700501 ConfigSection CommandAttriTree = tn->second;
akmhoque157b0a42014-05-13 00:26:37 -0500502 std::string name = CommandAttriTree.get<std::string>("name");
Nick Gordone9733ed2017-04-26 10:48:39 -0500503 std::string uriString = CommandAttriTree.get<std::string>("face-uri");
alvy2fe12872014-11-25 10:32:23 -0600504
Nick Gordone9733ed2017-04-26 10:48:39 -0500505 ndn::util::FaceUri faceUri;
Laqin Fan54a43f02017-03-08 12:31:30 -0600506 if (! faceUri.parse(uriString)) {
507 std::cerr << "parsing failed!" << std::endl;
alvy2fe12872014-11-25 10:32:23 -0600508 return false;
509 }
510
akmhoque157b0a42014-05-13 00:26:37 -0500511 double linkCost = CommandAttriTree.get<double>("link-cost",
512 Adjacent::DEFAULT_LINK_COST);
513 ndn::Name neighborName(name);
514 if (!neighborName.empty()) {
Vince Lehmancb76ade2014-08-28 21:24:41 -0500515 Adjacent adj(name, faceUri, linkCost, Adjacent::STATUS_INACTIVE, 0, 0);
akmhoque157b0a42014-05-13 00:26:37 -0500516 m_nlsr.getAdjacencyList().insert(adj);
517 }
518 else {
akmhoque674b0b12014-05-20 14:33:28 -0500519 std::cerr << " Wrong command format ! [name /nbr/name/ \n face-uri /uri\n]";
akmhoque157b0a42014-05-13 00:26:37 -0500520 std::cerr << " or bad URI format" << std::endl;
akmhoque53353462014-04-22 08:43:45 -0500521 }
522 }
akmhoque157b0a42014-05-13 00:26:37 -0500523 catch (const std::exception& ex) {
524 std::cerr << ex.what() << std::endl;
525 return false;
526 }
akmhoque53353462014-04-22 08:43:45 -0500527 }
528 }
akmhoque157b0a42014-05-13 00:26:37 -0500529 return true;
akmhoque53353462014-04-22 08:43:45 -0500530}
531
akmhoque157b0a42014-05-13 00:26:37 -0500532bool
Alexander Afanasyev8388ec62014-08-16 18:38:57 -0700533ConfFileProcessor::processConfSectionHyperbolic(const ConfigSection& section)
akmhoque53353462014-04-22 08:43:45 -0500534{
alvya2228c62014-12-09 10:25:11 -0600535 // state
536 std::string state = section.get<string>("state", "off");
537
538 if (boost::iequals(state, "off")) {
539 m_nlsr.getConfParameter().setHyperbolicState(HYPERBOLIC_STATE_OFF);
akmhoque53353462014-04-22 08:43:45 -0500540 }
alvya2228c62014-12-09 10:25:11 -0600541 else if (boost::iequals(state, "on")) {
542 m_nlsr.getConfParameter().setHyperbolicState(HYPERBOLIC_STATE_ON);
543 }
544 else if (state == "dry-run") {
545 m_nlsr.getConfParameter().setHyperbolicState(HYPERBOLIC_STATE_DRY_RUN);
546 }
547 else {
548 std::cerr << "Wrong format for hyperbolic state." << std::endl;
549 std::cerr << "Allowed value: off, on, dry-run" << std::endl;
550
akmhoque157b0a42014-05-13 00:26:37 -0500551 return false;
akmhoque53353462014-04-22 08:43:45 -0500552 }
Yingdi Yu20e3a6e2014-05-26 23:16:10 -0700553
akmhoque157b0a42014-05-13 00:26:37 -0500554 try {
Laqin Fan54a43f02017-03-08 12:31:30 -0600555 // Radius and angle(s) are mandatory configuration parameters in hyperbolic section.
556 // Even if router can have hyperbolic routing calculation off but other router
557 // in the network may use hyperbolic routing calculation for FIB generation.
558 // So each router need to advertise its hyperbolic coordinates in the network
Alexander Afanasyev8388ec62014-08-16 18:38:57 -0700559 double radius = section.get<double>("radius");
Muktadir R Chowdhuryb00dc2a2016-11-05 10:48:58 -0600560 std::string angleString = section.get<std::string>("angle");
561
562 std::stringstream ss(angleString);
563 std::vector<double> angles;
564
565 double angle;
566
Laqin Fan54a43f02017-03-08 12:31:30 -0600567 while (ss >> angle) {
Muktadir R Chowdhuryb00dc2a2016-11-05 10:48:58 -0600568 angles.push_back(angle);
Laqin Fan54a43f02017-03-08 12:31:30 -0600569 if (ss.peek() == ',' || ss.peek() == ' ') {
Muktadir R Chowdhuryb00dc2a2016-11-05 10:48:58 -0600570 ss.ignore();
571 }
572 }
573
akmhoque157b0a42014-05-13 00:26:37 -0500574 if (!m_nlsr.getConfParameter().setCorR(radius)) {
575 return false;
576 }
Muktadir R Chowdhuryb00dc2a2016-11-05 10:48:58 -0600577 m_nlsr.getConfParameter().setCorTheta(angles);
akmhoque53353462014-04-22 08:43:45 -0500578 }
akmhoque157b0a42014-05-13 00:26:37 -0500579 catch (const std::exception& ex) {
580 std::cerr << ex.what() << std::endl;
581 if (state == "on" || state == "dry-run") {
582 return false;
583 }
akmhoque53353462014-04-22 08:43:45 -0500584 }
Yingdi Yu20e3a6e2014-05-26 23:16:10 -0700585
akmhoque157b0a42014-05-13 00:26:37 -0500586 return true;
akmhoque53353462014-04-22 08:43:45 -0500587}
588
akmhoque157b0a42014-05-13 00:26:37 -0500589bool
Alexander Afanasyev8388ec62014-08-16 18:38:57 -0700590ConfFileProcessor::processConfSectionFib(const ConfigSection& section)
akmhoque53353462014-04-22 08:43:45 -0500591{
alvya2228c62014-12-09 10:25:11 -0600592 // max-faces-per-prefix
593 int maxFacesPerPrefix = section.get<int>("max-faces-per-prefix", MAX_FACES_PER_PREFIX_DEFAULT);
594
595 if (maxFacesPerPrefix >= MAX_FACES_PER_PREFIX_MIN &&
596 maxFacesPerPrefix <= MAX_FACES_PER_PREFIX_MAX)
597 {
598 m_nlsr.getConfParameter().setMaxFacesPerPrefix(maxFacesPerPrefix);
akmhoque53353462014-04-22 08:43:45 -0500599 }
alvya2228c62014-12-09 10:25:11 -0600600 else {
601 std::cerr << "Wrong value for max-faces-per-prefix. ";
602 std::cerr << MAX_FACES_PER_PREFIX_MIN << std::endl;
603
akmhoque157b0a42014-05-13 00:26:37 -0500604 return false;
605 }
Vince Lehman7b616582014-10-17 16:25:39 -0500606
607 // routing-calc-interval
608 ConfigurationVariable<uint32_t> routingCalcInterval("routing-calc-interval",
dmcoomes9f936662017-03-02 10:33:09 -0600609 std::bind(&ConfParameter::setRoutingCalcInterval,
Vince Lehman7b616582014-10-17 16:25:39 -0500610 &m_nlsr.getConfParameter(), _1));
611 routingCalcInterval.setMinAndMaxValue(ROUTING_CALC_INTERVAL_MIN, ROUTING_CALC_INTERVAL_MAX);
612 routingCalcInterval.setOptional(ROUTING_CALC_INTERVAL_DEFAULT);
613
614 if (!routingCalcInterval.parseFromConfigSection(section)) {
615 return false;
616 }
617
akmhoque157b0a42014-05-13 00:26:37 -0500618 return true;
akmhoque53353462014-04-22 08:43:45 -0500619}
620
akmhoque157b0a42014-05-13 00:26:37 -0500621bool
Alexander Afanasyev8388ec62014-08-16 18:38:57 -0700622ConfFileProcessor::processConfSectionAdvertising(const ConfigSection& section)
akmhoque53353462014-04-22 08:43:45 -0500623{
Alexander Afanasyev8388ec62014-08-16 18:38:57 -0700624 for (ConfigSection::const_iterator tn =
625 section.begin(); tn != section.end(); ++tn) {
akmhoque157b0a42014-05-13 00:26:37 -0500626 if (tn->first == "prefix") {
627 try {
628 std::string prefix = tn->second.data();
629 ndn::Name namePrefix(prefix);
630 if (!namePrefix.empty()) {
631 m_nlsr.getNamePrefixList().insert(namePrefix);
632 }
633 else {
akmhoque674b0b12014-05-20 14:33:28 -0500634 std::cerr << " Wrong command format ! [prefix /name/prefix] or bad URI" << std::endl;
akmhoque157b0a42014-05-13 00:26:37 -0500635 return false;
636 }
637 }
638 catch (const std::exception& ex) {
639 std::cerr << ex.what() << std::endl;
640 return false;
641 }
akmhoque53353462014-04-22 08:43:45 -0500642 }
akmhoque53353462014-04-22 08:43:45 -0500643 }
akmhoque157b0a42014-05-13 00:26:37 -0500644 return true;
akmhoque53353462014-04-22 08:43:45 -0500645}
Yingdi Yu20e3a6e2014-05-26 23:16:10 -0700646
647bool
Alexander Afanasyev8388ec62014-08-16 18:38:57 -0700648ConfFileProcessor::processConfSectionSecurity(const ConfigSection& section)
Yingdi Yu20e3a6e2014-05-26 23:16:10 -0700649{
650 ConfigSection::const_iterator it = section.begin();
651
Vince Lehmand33e5bc2015-06-22 15:27:50 -0500652 if (it == section.end() || it->first != "validator") {
653 std::cerr << "Error: Expect validator section!" << std::endl;
654 return false;
655 }
Yingdi Yu20e3a6e2014-05-26 23:16:10 -0700656
657 m_nlsr.loadValidator(it->second, m_confFileName);
Vince Lehmand33e5bc2015-06-22 15:27:50 -0500658
akmhoqued57f3672014-06-10 10:41:32 -0500659 it++;
Vince Lehmand33e5bc2015-06-22 15:27:50 -0500660 if (it != section.end() && it->first == "prefix-update-validator") {
Vince Lehmand33e5bc2015-06-22 15:27:50 -0500661 m_nlsr.getPrefixUpdateProcessor().loadValidator(it->second, m_confFileName);
Yingdi Yu20e3a6e2014-05-26 23:16:10 -0700662
Vince Lehmand33e5bc2015-06-22 15:27:50 -0500663 it++;
664 for (; it != section.end(); it++) {
Yingdi Yu20e3a6e2014-05-26 23:16:10 -0700665 using namespace boost::filesystem;
Vince Lehmand33e5bc2015-06-22 15:27:50 -0500666
667 if (it->first != "cert-to-publish") {
668 std::cerr << "Error: Expect cert-to-publish!" << std::endl;
669 return false;
670 }
Yingdi Yu20e3a6e2014-05-26 23:16:10 -0700671
672 std::string file = it->second.data();
673 path certfilePath = absolute(file, path(m_confFileName).parent_path());
dmcoomes9f936662017-03-02 10:33:09 -0600674 std::shared_ptr<ndn::IdentityCertificate> idCert =
Yingdi Yu20e3a6e2014-05-26 23:16:10 -0700675 ndn::io::load<ndn::IdentityCertificate>(certfilePath.string());
676
Vince Lehmand33e5bc2015-06-22 15:27:50 -0500677 if (idCert == nullptr) {
678 std::cerr << "Error: Cannot load cert-to-publish: " << file << "!" << std::endl;
679 return false;
680 }
Yingdi Yu20e3a6e2014-05-26 23:16:10 -0700681
682 m_nlsr.loadCertToPublish(idCert);
683 }
Vince Lehmand33e5bc2015-06-22 15:27:50 -0500684 }
Yingdi Yu20e3a6e2014-05-26 23:16:10 -0700685
686 return true;
687}
688
alvy2fe12872014-11-25 10:32:23 -0600689} // namespace nlsr