Refactor config file parsing and improve error handling
Change-Id: I8a54ba1f0d414bea70923e0f45ca354ac7e957a3
This commit is contained in:
1 parent
032c98004f
commit
306e5bc606
5 files changed
+196
-277
No files matched your search
@@ -2,20 +2,19 @@
|
|||||||
# THIS IS A SAMPLE CLIENT INTEREST TRAFFIC CONFIGURATION FILE
|
# THIS IS A SAMPLE CLIENT INTEREST TRAFFIC CONFIGURATION FILE
|
||||||
#
|
#
|
||||||
# * TO BE USED TO GENERATE INTEREST MESSAGES BASED ON A PROBABILITY
|
# * TO BE USED TO GENERATE INTEREST MESSAGES BASED ON A PROBABILITY
|
||||||
# PATTERN.
|
# PATTERN
|
||||||
# * EVERY INIVIDUAL PATTERN DESCRIPTION MUST BE SEPARATED BY ONE
|
# * EVERY INDIVIDUAL PATTERN DESCRIPTION MUST BE SEPARATED BY ONE
|
||||||
# OR MORE '#' CHARACTERS FOR THE TOOL TO DISTINGUISH THEM
|
# OR MORE '#' CHARACTERS FOR THE TOOL TO DISTINGUISH THEM
|
||||||
# INDIVIDUALLY
|
|
||||||
# * THE FOLLOWING PARAMETERS MAY BE ADDED FOR EVERY TRAFFIC PATTERN
|
# * THE FOLLOWING PARAMETERS MAY BE ADDED FOR EVERY TRAFFIC PATTERN
|
||||||
# * (Mandatory) NEXT TO A PARAMETER MEANS EVERY PATTERN SHOULD HAVE
|
# * 'Mandatory' ARE PARAMETERS THAT EVERY PATTERN MUST HAVE IN ORDER
|
||||||
# IT FOR BEING CONSIDERED VALID
|
# TO BE CONSIDERED VALID
|
||||||
# (Optional) MEANS OTHERWISE
|
# * 'Boolean' ACCEPTS EITHER 0/false/no/off OR 1/true/yes/on AS VALUE
|
||||||
# * ALSO PROVIDED ARE VALID VALUES POSSIBLE FOR EACH PARAMETER
|
# * 'NNI' STANDS FOR NON-NEGATIVE INTEGER
|
||||||
# * PLEASE ENSURE THAT THE SUM OF TrafficPercentage FOR ALL DECLARED
|
|
||||||
# PATTERNS DOES NOT EXCEED 100 IN ORDER TO MAINTAIN CORRECT BEHAVIOR
|
|
||||||
# * NNI STANDS FOR NON-NEGATIVE INTEGER
|
|
||||||
# * RANGE OF POSSIBLE VALUES IS SPECIFIED IN []
|
# * RANGE OF POSSIBLE VALUES IS SPECIFIED IN []
|
||||||
|
# * PLEASE ENSURE THAT THE SUM OF 'TrafficPercentage' FOR ALL DECLARED
|
||||||
|
# PATTERNS DOES NOT EXCEED 100 IN ORDER TO MAINTAIN CORRECT BEHAVIOR
|
||||||
#
|
#
|
||||||
|
|
||||||
# (Mandatory)
|
# (Mandatory)
|
||||||
#TrafficPercentage=NNI [0-100]
|
#TrafficPercentage=NNI [0-100]
|
||||||
#Name=NDN Name
|
#Name=NDN Name
|
||||||
@@ -23,10 +22,10 @@
|
|||||||
# (Optional)
|
# (Optional)
|
||||||
#NameAppendBytes=NNI [>0]
|
#NameAppendBytes=NNI [>0]
|
||||||
#NameAppendSequenceNumber=NNI [>=0]
|
#NameAppendSequenceNumber=NNI [>=0]
|
||||||
#MustBeFresh=NNI [0-1]
|
#MustBeFresh=Boolean
|
||||||
#NonceDuplicationPercentage=NNI [0-100]
|
#NonceDuplicationPercentage=NNI [0-100]
|
||||||
#InterestLifetime=NNI [Milliseconds]
|
#InterestLifetime=Milliseconds [>=0]
|
||||||
#NextHopFaceId=NNI
|
#NextHopFaceId=NNI [>0]
|
||||||
#ExpectedContent=String
|
#ExpectedContent=String
|
||||||
|
|
||||||
##########
|
##########
|
||||||
|
|||||||
@@ -3,26 +3,25 @@
|
|||||||
#
|
#
|
||||||
# * TO BE USED TO CONFIGURE RESPONSE TO INTERESTS
|
# * TO BE USED TO CONFIGURE RESPONSE TO INTERESTS
|
||||||
# * MULTIPLE SERVER PREFIXES CAN BE CONFIGURED FOR BEING HANDLED
|
# * MULTIPLE SERVER PREFIXES CAN BE CONFIGURED FOR BEING HANDLED
|
||||||
# * EVERY INIVIDUAL PATTERN DESCRIPTION MUST BE SEPARATED BY ONE
|
# * EVERY INDIVIDUAL PATTERN DESCRIPTION MUST BE SEPARATED BY ONE
|
||||||
# OR MORE '#' CHARACTERS FOR THE TOOL TO DISTINGUISH THEM
|
# OR MORE '#' CHARACTERS FOR THE TOOL TO DISTINGUISH THEM
|
||||||
# INDIVIDUALLY
|
|
||||||
# * THE FOLLOWING PARAMETERS MAY BE ADDED FOR EVERY TRAFFIC PATTERN
|
# * THE FOLLOWING PARAMETERS MAY BE ADDED FOR EVERY TRAFFIC PATTERN
|
||||||
# * (Mandatory) NEXT TO A PARAMETER MEANS EVERY PATTERN SHOULD HAVE
|
# * 'Mandatory' ARE PARAMETERS THAT EVERY PATTERN MUST HAVE IN ORDER
|
||||||
# IT FOR BEING CONSIDERED VALID
|
# TO BE CONSIDERED VALID
|
||||||
# (Optional) MEANS OTHERWISE
|
# * 'Boolean' ACCEPTS EITHER 0/false/no/off OR 1/true/yes/on AS VALUE
|
||||||
# * ALSO PROVIDED ARE VALID VALUES POSSIBLE FOR EACH PARAMETER
|
# * 'NNI' STANDS FOR NON-NEGATIVE INTEGER
|
||||||
# * NNI STANDS FOR NON-NEGATIVE INTEGER
|
|
||||||
# * RANGE OF POSSIBLE VALUES IS SPECIFIED IN []
|
# * RANGE OF POSSIBLE VALUES IS SPECIFIED IN []
|
||||||
#
|
#
|
||||||
|
|
||||||
# (Mandatory)
|
# (Mandatory)
|
||||||
#Name=NDN Name
|
#Name=NDN Name
|
||||||
#
|
#
|
||||||
# (Optional)
|
# (Optional)
|
||||||
|
#ContentDelay=Milliseconds [>=0]
|
||||||
|
#FreshnessPeriod=Milliseconds [>=0]
|
||||||
#ContentType=NNI [>=0]
|
#ContentType=NNI [>=0]
|
||||||
#FreshnessPeriod=NNI [milliseconds]
|
|
||||||
#ContentBytes=NNI [>0]
|
#ContentBytes=NNI [>0]
|
||||||
#Content=String
|
#Content=String
|
||||||
#ContentDelay=NNI [milliseconds]
|
|
||||||
#SigningInfo=String [examples below]
|
#SigningInfo=String [examples below]
|
||||||
|
|
||||||
##########
|
##########
|
||||||
|
|||||||
+61
-130
@@ -18,7 +18,6 @@
|
|||||||
* Author: Jerald Paul Abraham <jeraldabraham@email.arizona.edu>
|
* Author: Jerald Paul Abraham <jeraldabraham@email.arizona.edu>
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include "logger.hpp"
|
|
||||||
#include "util.hpp"
|
#include "util.hpp"
|
||||||
|
|
||||||
#include <ndn-cxx/face.hpp>
|
#include <ndn-cxx/face.hpp>
|
||||||
@@ -27,7 +26,6 @@
|
|||||||
#include <ndn-cxx/util/backports.hpp>
|
#include <ndn-cxx/util/backports.hpp>
|
||||||
#include <ndn-cxx/util/random.hpp>
|
#include <ndn-cxx/util/random.hpp>
|
||||||
|
|
||||||
#include <cctype>
|
|
||||||
#include <limits>
|
#include <limits>
|
||||||
#include <vector>
|
#include <vector>
|
||||||
|
|
||||||
@@ -36,7 +34,6 @@
|
|||||||
#include <boost/asio/signal_set.hpp>
|
#include <boost/asio/signal_set.hpp>
|
||||||
#include <boost/date_time/posix_time/posix_time.hpp>
|
#include <boost/date_time/posix_time/posix_time.hpp>
|
||||||
#include <boost/lexical_cast.hpp>
|
#include <boost/lexical_cast.hpp>
|
||||||
#include <boost/logic/tribool.hpp>
|
|
||||||
#include <boost/noncopyable.hpp>
|
#include <boost/noncopyable.hpp>
|
||||||
#include <boost/program_options/options_description.hpp>
|
#include <boost/program_options/options_description.hpp>
|
||||||
#include <boost/program_options/parsers.hpp>
|
#include <boost/program_options/parsers.hpp>
|
||||||
@@ -58,12 +55,6 @@ public:
|
|||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
bool
|
|
||||||
hasError() const
|
|
||||||
{
|
|
||||||
return m_hasError;
|
|
||||||
}
|
|
||||||
|
|
||||||
void
|
void
|
||||||
setMaximumInterests(uint64_t maxInterests)
|
setMaximumInterests(uint64_t maxInterests)
|
||||||
{
|
{
|
||||||
@@ -83,15 +74,30 @@ public:
|
|||||||
m_wantQuiet = true;
|
m_wantQuiet = true;
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
int
|
||||||
run()
|
run()
|
||||||
{
|
{
|
||||||
m_logger.initializeLog(to_string(random::generateWord32()));
|
m_logger.initializeLog(to_string(random::generateWord32()));
|
||||||
initializeTrafficConfiguration();
|
|
||||||
|
if (!readConfigurationFile(m_configurationFile, m_trafficPatterns, m_logger)) {
|
||||||
|
return 2;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!checkTrafficPatternCorrectness()) {
|
||||||
|
m_logger.log("ERROR: Traffic configuration provided is not proper", false, true);
|
||||||
|
return 2;
|
||||||
|
}
|
||||||
|
|
||||||
|
m_logger.log("Traffic configuration file processing completed.\n", true, false);
|
||||||
|
for (std::size_t i = 0; i < m_trafficPatterns.size(); i++) {
|
||||||
|
m_logger.log("Traffic Pattern Type #" + to_string(i + 1), false, false);
|
||||||
|
m_trafficPatterns[i].printTrafficConfiguration(m_logger);
|
||||||
|
m_logger.log("", false, false);
|
||||||
|
}
|
||||||
|
|
||||||
if (m_nMaximumInterests == 0) {
|
if (m_nMaximumInterests == 0) {
|
||||||
logStatistics();
|
logStatistics();
|
||||||
return;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
m_signalSet.async_wait([this] (auto&&...) { this->stop(); });
|
m_signalSet.async_wait([this] (auto&&...) { this->stop(); });
|
||||||
@@ -102,11 +108,12 @@ public:
|
|||||||
|
|
||||||
try {
|
try {
|
||||||
m_face.processEvents();
|
m_face.processEvents();
|
||||||
|
return m_hasError ? 1 : 0;
|
||||||
}
|
}
|
||||||
catch (const std::exception& e) {
|
catch (const std::exception& e) {
|
||||||
m_logger.log("ERROR: "s + e.what(), true, true);
|
m_logger.log("ERROR: "s + e.what(), true, true);
|
||||||
m_hasError = true;
|
|
||||||
m_ioService.stop();
|
m_ioService.stop();
|
||||||
|
return 1;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -120,14 +127,12 @@ private:
|
|||||||
std::string detail;
|
std::string detail;
|
||||||
|
|
||||||
detail += "TrafficPercentage=" + to_string(m_trafficPercentage) + ", ";
|
detail += "TrafficPercentage=" + to_string(m_trafficPercentage) + ", ";
|
||||||
if (!m_name.empty())
|
detail += "Name=" + m_name + ", ";
|
||||||
detail += "Name=" + m_name + ", ";
|
|
||||||
if (m_nameAppendBytes)
|
if (m_nameAppendBytes)
|
||||||
detail += "NameAppendBytes=" + to_string(*m_nameAppendBytes) + ", ";
|
detail += "NameAppendBytes=" + to_string(*m_nameAppendBytes) + ", ";
|
||||||
if (m_nameAppendSeqNum)
|
if (m_nameAppendSeqNum)
|
||||||
detail += "NameAppendSequenceNumber=" + to_string(*m_nameAppendSeqNum) + ", ";
|
detail += "NameAppendSequenceNumber=" + to_string(*m_nameAppendSeqNum) + ", ";
|
||||||
if (!boost::logic::indeterminate(m_mustBeFresh))
|
detail += "MustBeFresh=" + to_string(m_mustBeFresh) + ", ";
|
||||||
detail += "MustBeFresh=" + to_string(bool(m_mustBeFresh)) + ", ";
|
|
||||||
if (m_nonceDuplicationPercentage > 0)
|
if (m_nonceDuplicationPercentage > 0)
|
||||||
detail += "NonceDuplicationPercentage=" + to_string(m_nonceDuplicationPercentage) + ", ";
|
detail += "NonceDuplicationPercentage=" + to_string(m_nonceDuplicationPercentage) + ", ";
|
||||||
if (m_interestLifetime >= 0_ms)
|
if (m_interestLifetime >= 0_ms)
|
||||||
@@ -143,36 +148,45 @@ private:
|
|||||||
}
|
}
|
||||||
|
|
||||||
bool
|
bool
|
||||||
processConfigurationDetail(const std::string& detail, Logger& logger, int lineNumber)
|
parseConfigurationLine(const std::string& line, Logger& logger, int lineNumber)
|
||||||
{
|
{
|
||||||
std::string parameter, value;
|
std::string parameter, value;
|
||||||
if (parseParameterAndValue(detail, parameter, value)) {
|
if (!extractParameterAndValue(line, parameter, value)) {
|
||||||
if (parameter == "TrafficPercentage")
|
logger.log("Line " + to_string(lineNumber) + " - Invalid syntax: " + line,
|
||||||
m_trafficPercentage = std::stoul(value);
|
false, true);
|
||||||
else if (parameter == "Name")
|
return false;
|
||||||
m_name = value;
|
}
|
||||||
else if (parameter == "NameAppendBytes")
|
|
||||||
m_nameAppendBytes = std::stoul(value);
|
if (parameter == "TrafficPercentage") {
|
||||||
else if (parameter == "NameAppendSequenceNumber")
|
m_trafficPercentage = std::stoul(value);
|
||||||
m_nameAppendSeqNum = std::stoull(value);
|
}
|
||||||
else if (parameter == "MustBeFresh")
|
else if (parameter == "Name") {
|
||||||
m_mustBeFresh = bool(std::stoul(value));
|
m_name = value;
|
||||||
else if (parameter == "NonceDuplicationPercentage")
|
}
|
||||||
m_nonceDuplicationPercentage = std::stoul(value);
|
else if (parameter == "NameAppendBytes") {
|
||||||
else if (parameter == "InterestLifetime")
|
m_nameAppendBytes = std::stoul(value);
|
||||||
m_interestLifetime = time::milliseconds(std::stoul(value));
|
}
|
||||||
else if (parameter == "NextHopFaceId")
|
else if (parameter == "NameAppendSequenceNumber") {
|
||||||
m_nextHopFaceId = std::stoull(value);
|
m_nameAppendSeqNum = std::stoull(value);
|
||||||
else if (parameter == "ExpectedContent")
|
}
|
||||||
m_expectedContent = value;
|
else if (parameter == "MustBeFresh") {
|
||||||
else
|
m_mustBeFresh = parseBoolean(value);
|
||||||
logger.log("Line " + to_string(lineNumber) +
|
}
|
||||||
" - Unknown parameter '" + parameter + "'", false, true);
|
else if (parameter == "NonceDuplicationPercentage") {
|
||||||
|
m_nonceDuplicationPercentage = std::stoul(value);
|
||||||
|
}
|
||||||
|
else if (parameter == "InterestLifetime") {
|
||||||
|
m_interestLifetime = time::milliseconds(std::stoul(value));
|
||||||
|
}
|
||||||
|
else if (parameter == "NextHopFaceId") {
|
||||||
|
m_nextHopFaceId = std::stoull(value);
|
||||||
|
}
|
||||||
|
else if (parameter == "ExpectedContent") {
|
||||||
|
m_expectedContent = value;
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
logger.log("Line " + to_string(lineNumber) +
|
logger.log("Line " + to_string(lineNumber) + " - Ignoring unknown parameter: " + parameter,
|
||||||
" - Invalid traffic configuration line: " + detail, false, true);
|
false, true);
|
||||||
return false;
|
|
||||||
}
|
}
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
@@ -188,7 +202,7 @@ private:
|
|||||||
std::string m_name;
|
std::string m_name;
|
||||||
optional<std::size_t> m_nameAppendBytes;
|
optional<std::size_t> m_nameAppendBytes;
|
||||||
optional<uint64_t> m_nameAppendSeqNum;
|
optional<uint64_t> m_nameAppendSeqNum;
|
||||||
boost::logic::tribool m_mustBeFresh = boost::logic::indeterminate;
|
bool m_mustBeFresh = false;
|
||||||
uint8_t m_nonceDuplicationPercentage = 0;
|
uint8_t m_nonceDuplicationPercentage = 0;
|
||||||
time::milliseconds m_interestLifetime = -1_ms;
|
time::milliseconds m_interestLifetime = -1_ms;
|
||||||
uint64_t m_nextHopFaceId = 0;
|
uint64_t m_nextHopFaceId = 0;
|
||||||
@@ -272,88 +286,10 @@ private:
|
|||||||
bool
|
bool
|
||||||
checkTrafficPatternCorrectness() const
|
checkTrafficPatternCorrectness() const
|
||||||
{
|
{
|
||||||
|
// TODO
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
|
||||||
parseConfigurationFile()
|
|
||||||
{
|
|
||||||
std::ifstream patternFile;
|
|
||||||
m_logger.log("Parsing traffic configuration file: " + m_configurationFile, true, true);
|
|
||||||
|
|
||||||
patternFile.open(m_configurationFile.data());
|
|
||||||
if (patternFile.is_open()) {
|
|
||||||
int lineNumber = 0;
|
|
||||||
std::string patternLine;
|
|
||||||
while (getline(patternFile, patternLine)) {
|
|
||||||
lineNumber++;
|
|
||||||
if (std::isalpha(patternLine[0])) {
|
|
||||||
InterestTrafficConfiguration interestData;
|
|
||||||
bool shouldSkipLine = false;
|
|
||||||
if (interestData.processConfigurationDetail(patternLine, m_logger, lineNumber)) {
|
|
||||||
while (getline(patternFile, patternLine) && std::isalpha(patternLine[0])) {
|
|
||||||
lineNumber++;
|
|
||||||
if (!interestData.processConfigurationDetail(patternLine, m_logger, lineNumber)) {
|
|
||||||
shouldSkipLine = true;
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
lineNumber++;
|
|
||||||
}
|
|
||||||
else {
|
|
||||||
shouldSkipLine = true;
|
|
||||||
}
|
|
||||||
if (!shouldSkipLine) {
|
|
||||||
if (interestData.checkTrafficDetailCorrectness()) {
|
|
||||||
m_trafficPatterns.push_back(interestData);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
patternFile.close();
|
|
||||||
|
|
||||||
if (!checkTrafficPatternCorrectness()) {
|
|
||||||
m_logger.log("ERROR: Traffic configuration provided is not proper - " +
|
|
||||||
m_configurationFile, false, true);
|
|
||||||
exit(2);
|
|
||||||
}
|
|
||||||
|
|
||||||
m_logger.log("Traffic configuration file processing completed.\n", true, false);
|
|
||||||
for (std::size_t patternId = 0; patternId < m_trafficPatterns.size(); patternId++) {
|
|
||||||
m_logger.log("Traffic Pattern Type #" + to_string(patternId + 1), false, false);
|
|
||||||
m_trafficPatterns[patternId].printTrafficConfiguration(m_logger);
|
|
||||||
m_logger.log("", false, false);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else {
|
|
||||||
m_logger.log("ERROR: Unable to open traffic configuration file: " + m_configurationFile, false, true);
|
|
||||||
exit(2);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void
|
|
||||||
initializeTrafficConfiguration()
|
|
||||||
{
|
|
||||||
namespace fs = boost::filesystem;
|
|
||||||
|
|
||||||
fs::path configPath(m_configurationFile);
|
|
||||||
if (fs::exists(configPath)) {
|
|
||||||
if (fs::is_regular_file(configPath)) {
|
|
||||||
parseConfigurationFile();
|
|
||||||
}
|
|
||||||
else {
|
|
||||||
m_logger.log("ERROR: Traffic configuration file is not a regular file: " +
|
|
||||||
m_configurationFile, false, true);
|
|
||||||
exit(2);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else {
|
|
||||||
m_logger.log("ERROR: Traffic configuration file does not exist: " +
|
|
||||||
m_configurationFile, false, true);
|
|
||||||
exit(2);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
uint32_t
|
uint32_t
|
||||||
getNewNonce()
|
getNewNonce()
|
||||||
{
|
{
|
||||||
@@ -409,10 +345,7 @@ private:
|
|||||||
}
|
}
|
||||||
interest.setName(name);
|
interest.setName(name);
|
||||||
|
|
||||||
if (pattern.m_mustBeFresh)
|
interest.setMustBeFresh(pattern.m_mustBeFresh);
|
||||||
interest.setMustBeFresh(true);
|
|
||||||
else if (!pattern.m_mustBeFresh)
|
|
||||||
interest.setMustBeFresh(false);
|
|
||||||
|
|
||||||
static std::uniform_int_distribution<> duplicateNonceDist(1, 100);
|
static std::uniform_int_distribution<> duplicateNonceDist(1, 100);
|
||||||
if (duplicateNonceDist(random::getRandomNumberEngine()) <= pattern.m_nonceDuplicationPercentage)
|
if (duplicateNonceDist(random::getRandomNumberEngine()) <= pattern.m_nonceDuplicationPercentage)
|
||||||
@@ -688,7 +621,5 @@ main(int argc, char* argv[])
|
|||||||
client.setQuietLogging();
|
client.setQuietLogging();
|
||||||
}
|
}
|
||||||
|
|
||||||
client.run();
|
return client.run();
|
||||||
|
|
||||||
return client.hasError() ? 1 : 0;
|
|
||||||
}
|
}
|
||||||
+51
-124
@@ -18,7 +18,6 @@
|
|||||||
* Author: Jerald Paul Abraham <jeraldabraham@email.arizona.edu>
|
* Author: Jerald Paul Abraham <jeraldabraham@email.arizona.edu>
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include "logger.hpp"
|
|
||||||
#include "util.hpp"
|
#include "util.hpp"
|
||||||
|
|
||||||
#include <ndn-cxx/data.hpp>
|
#include <ndn-cxx/data.hpp>
|
||||||
@@ -28,7 +27,6 @@
|
|||||||
#include <ndn-cxx/util/backports.hpp>
|
#include <ndn-cxx/util/backports.hpp>
|
||||||
#include <ndn-cxx/util/random.hpp>
|
#include <ndn-cxx/util/random.hpp>
|
||||||
|
|
||||||
#include <cctype>
|
|
||||||
#include <limits>
|
#include <limits>
|
||||||
#include <sstream>
|
#include <sstream>
|
||||||
#include <vector>
|
#include <vector>
|
||||||
@@ -57,12 +55,6 @@ public:
|
|||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
bool
|
|
||||||
hasError() const
|
|
||||||
{
|
|
||||||
return m_hasError;
|
|
||||||
}
|
|
||||||
|
|
||||||
void
|
void
|
||||||
setMaximumInterests(uint64_t maxInterests)
|
setMaximumInterests(uint64_t maxInterests)
|
||||||
{
|
{
|
||||||
@@ -82,15 +74,30 @@ public:
|
|||||||
m_wantQuiet = true;
|
m_wantQuiet = true;
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
int
|
||||||
run()
|
run()
|
||||||
{
|
{
|
||||||
m_logger.initializeLog(to_string(random::generateWord32()));
|
m_logger.initializeLog(to_string(random::generateWord32()));
|
||||||
initializeTrafficConfiguration();
|
|
||||||
|
if (!readConfigurationFile(m_configurationFile, m_trafficPatterns, m_logger)) {
|
||||||
|
return 2;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!checkTrafficPatternCorrectness()) {
|
||||||
|
m_logger.log("ERROR: Traffic configuration provided is not proper", false, true);
|
||||||
|
return 2;
|
||||||
|
}
|
||||||
|
|
||||||
|
m_logger.log("Traffic configuration file processing completed.\n", true, false);
|
||||||
|
for (std::size_t i = 0; i < m_trafficPatterns.size(); i++) {
|
||||||
|
m_logger.log("Traffic Pattern Type #" + to_string(i + 1), false, false);
|
||||||
|
m_trafficPatterns[i].printTrafficConfiguration(m_logger);
|
||||||
|
m_logger.log("", false, false);
|
||||||
|
}
|
||||||
|
|
||||||
if (m_nMaximumInterests == 0) {
|
if (m_nMaximumInterests == 0) {
|
||||||
logStatistics();
|
logStatistics();
|
||||||
return;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
m_signalSet.async_wait([this] (const boost::system::error_code&, int) {
|
m_signalSet.async_wait([this] (const boost::system::error_code&, int) {
|
||||||
@@ -110,11 +117,12 @@ public:
|
|||||||
|
|
||||||
try {
|
try {
|
||||||
m_face.processEvents();
|
m_face.processEvents();
|
||||||
|
return m_hasError ? 1 : 0;
|
||||||
}
|
}
|
||||||
catch (const std::exception& e) {
|
catch (const std::exception& e) {
|
||||||
m_logger.log("ERROR: "s + e.what(), true, true);
|
m_logger.log("ERROR: "s + e.what(), true, true);
|
||||||
m_hasError = true;
|
|
||||||
m_ioService.stop();
|
m_ioService.stop();
|
||||||
|
return 1;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -151,40 +159,39 @@ private:
|
|||||||
}
|
}
|
||||||
|
|
||||||
bool
|
bool
|
||||||
processConfigurationDetail(const std::string& detail, Logger& logger, int lineNumber)
|
parseConfigurationLine(const std::string& line, Logger& logger, int lineNumber)
|
||||||
{
|
{
|
||||||
std::string parameter, value;
|
std::string parameter, value;
|
||||||
if (parseParameterAndValue(detail, parameter, value)) {
|
if (!extractParameterAndValue(line, parameter, value)) {
|
||||||
if (parameter == "Name") {
|
logger.log("Line " + to_string(lineNumber) + " - Invalid syntax: " + line,
|
||||||
m_name = value;
|
false, true);
|
||||||
}
|
return false;
|
||||||
else if (parameter == "ContentDelay") {
|
}
|
||||||
m_contentDelay = time::milliseconds(std::stoul(value));
|
|
||||||
}
|
if (parameter == "Name") {
|
||||||
else if (parameter == "FreshnessPeriod") {
|
m_name = value;
|
||||||
m_freshnessPeriod = time::milliseconds(std::stoul(value));
|
}
|
||||||
}
|
else if (parameter == "ContentDelay") {
|
||||||
else if (parameter == "ContentType") {
|
m_contentDelay = time::milliseconds(std::stoul(value));
|
||||||
m_contentType = std::stoul(value);
|
}
|
||||||
}
|
else if (parameter == "FreshnessPeriod") {
|
||||||
else if (parameter == "ContentBytes") {
|
m_freshnessPeriod = time::milliseconds(std::stoul(value));
|
||||||
m_contentLength = std::stoul(value);
|
}
|
||||||
}
|
else if (parameter == "ContentType") {
|
||||||
else if (parameter == "Content") {
|
m_contentType = std::stoul(value);
|
||||||
m_content = value;
|
}
|
||||||
}
|
else if (parameter == "ContentBytes") {
|
||||||
else if (parameter == "SigningInfo") {
|
m_contentLength = std::stoul(value);
|
||||||
m_signingInfo = security::SigningInfo(value);
|
}
|
||||||
}
|
else if (parameter == "Content") {
|
||||||
else {
|
m_content = value;
|
||||||
logger.log("Line " + to_string(lineNumber) +
|
}
|
||||||
" - Unknown parameter '" + parameter + "'", false, true);
|
else if (parameter == "SigningInfo") {
|
||||||
}
|
m_signingInfo = security::SigningInfo(value);
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
logger.log("Line " + to_string(lineNumber) +
|
logger.log("Line " + to_string(lineNumber) + " - Ignoring unknown parameter: " + parameter,
|
||||||
" - Invalid traffic configuration line: " + detail, false, true);
|
false, true);
|
||||||
return false;
|
|
||||||
}
|
}
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
@@ -226,88 +233,10 @@ private:
|
|||||||
bool
|
bool
|
||||||
checkTrafficPatternCorrectness() const
|
checkTrafficPatternCorrectness() const
|
||||||
{
|
{
|
||||||
|
// TODO
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
|
||||||
parseConfigurationFile()
|
|
||||||
{
|
|
||||||
std::ifstream patternFile;
|
|
||||||
m_logger.log("Parsing traffic configuration file: " + m_configurationFile, true, true);
|
|
||||||
|
|
||||||
patternFile.open(m_configurationFile.data());
|
|
||||||
if (patternFile.is_open()) {
|
|
||||||
int lineNumber = 0;
|
|
||||||
std::string patternLine;
|
|
||||||
while (getline(patternFile, patternLine)) {
|
|
||||||
lineNumber++;
|
|
||||||
if (std::isalpha(patternLine[0])) {
|
|
||||||
DataTrafficConfiguration dataData;
|
|
||||||
bool shouldSkipLine = false;
|
|
||||||
if (dataData.processConfigurationDetail(patternLine, m_logger, lineNumber)) {
|
|
||||||
while (getline(patternFile, patternLine) && std::isalpha(patternLine[0])) {
|
|
||||||
lineNumber++;
|
|
||||||
if (!dataData.processConfigurationDetail(patternLine, m_logger, lineNumber)) {
|
|
||||||
shouldSkipLine = true;
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
lineNumber++;
|
|
||||||
}
|
|
||||||
else {
|
|
||||||
shouldSkipLine = true;
|
|
||||||
}
|
|
||||||
if (!shouldSkipLine) {
|
|
||||||
if (dataData.checkTrafficDetailCorrectness()) {
|
|
||||||
m_trafficPatterns.push_back(dataData);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
patternFile.close();
|
|
||||||
|
|
||||||
if (!checkTrafficPatternCorrectness()) {
|
|
||||||
m_logger.log("ERROR: Traffic configuration provided is not proper - " +
|
|
||||||
m_configurationFile, false, true);
|
|
||||||
exit(2);
|
|
||||||
}
|
|
||||||
|
|
||||||
m_logger.log("Traffic configuration file processing completed.\n", true, false);
|
|
||||||
for (std::size_t patternId = 0; patternId < m_trafficPatterns.size(); patternId++) {
|
|
||||||
m_logger.log("Traffic Pattern Type #" + to_string(patternId + 1), false, false);
|
|
||||||
m_trafficPatterns[patternId].printTrafficConfiguration(m_logger);
|
|
||||||
m_logger.log("", false, false);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else {
|
|
||||||
m_logger.log("ERROR: Unable to open traffic configuration file: " + m_configurationFile, false, true);
|
|
||||||
exit(2);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void
|
|
||||||
initializeTrafficConfiguration()
|
|
||||||
{
|
|
||||||
namespace fs = boost::filesystem;
|
|
||||||
|
|
||||||
fs::path configPath(m_configurationFile);
|
|
||||||
if (fs::exists(configPath)) {
|
|
||||||
if (fs::is_regular_file(configPath)) {
|
|
||||||
parseConfigurationFile();
|
|
||||||
}
|
|
||||||
else {
|
|
||||||
m_logger.log("ERROR: Traffic configuration file is not a regular file: " +
|
|
||||||
m_configurationFile, false, true);
|
|
||||||
exit(2);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else {
|
|
||||||
m_logger.log("ERROR: Traffic configuration file does not exist: " +
|
|
||||||
m_configurationFile, false, true);
|
|
||||||
exit(2);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
static std::string
|
static std::string
|
||||||
getRandomByteString(std::size_t length)
|
getRandomByteString(std::size_t length)
|
||||||
{
|
{
|
||||||
@@ -501,7 +430,5 @@ main(int argc, char* argv[])
|
|||||||
server.setQuietLogging();
|
server.setQuietLogging();
|
||||||
}
|
}
|
||||||
|
|
||||||
server.run();
|
return server.run();
|
||||||
|
|
||||||
return server.hasError() ? 1 : 0;
|
|
||||||
}
|
}
|
||||||
+64
-1
@@ -21,13 +21,17 @@
|
|||||||
#ifndef NTG_UTIL_HPP
|
#ifndef NTG_UTIL_HPP
|
||||||
#define NTG_UTIL_HPP
|
#define NTG_UTIL_HPP
|
||||||
|
|
||||||
|
#include "logger.hpp"
|
||||||
|
|
||||||
#include <cctype>
|
#include <cctype>
|
||||||
#include <string>
|
#include <string>
|
||||||
|
|
||||||
|
#include <boost/algorithm/string/predicate.hpp>
|
||||||
|
|
||||||
namespace ndn {
|
namespace ndn {
|
||||||
|
|
||||||
static inline bool
|
static inline bool
|
||||||
parseParameterAndValue(const std::string& input, std::string& parameter, std::string& value)
|
extractParameterAndValue(const std::string& input, std::string& parameter, std::string& value)
|
||||||
{
|
{
|
||||||
static const std::string allowedCharacters = ":/+._-%";
|
static const std::string allowedCharacters = ":/+._-%";
|
||||||
parameter = "";
|
parameter = "";
|
||||||
@@ -56,6 +60,65 @@ parseParameterAndValue(const std::string& input, std::string& parameter, std::st
|
|||||||
return !parameter.empty() && !value.empty() && i == input.length();
|
return !parameter.empty() && !value.empty() && i == input.length();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static inline bool
|
||||||
|
parseBoolean(const std::string& input)
|
||||||
|
{
|
||||||
|
if (boost::iequals(input, "no") || boost::iequals(input, "off") ||
|
||||||
|
boost::iequals(input, "false") || input == "0")
|
||||||
|
return false;
|
||||||
|
|
||||||
|
if (boost::iequals(input, "yes") || boost::iequals(input, "on") ||
|
||||||
|
boost::iequals(input, "true") || input == "1")
|
||||||
|
return true;
|
||||||
|
|
||||||
|
throw std::invalid_argument("'" + input + "' is not a valid boolean value");
|
||||||
|
}
|
||||||
|
|
||||||
|
template<typename TrafficConfigurationType>
|
||||||
|
static inline bool
|
||||||
|
readConfigurationFile(const std::string& filename,
|
||||||
|
std::vector<TrafficConfigurationType>& patterns,
|
||||||
|
Logger& logger)
|
||||||
|
{
|
||||||
|
std::ifstream patternFile(filename);
|
||||||
|
if (!patternFile) {
|
||||||
|
logger.log("ERROR: Unable to open traffic configuration file: " + filename, false, true);
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
logger.log("Reading traffic configuration file: " + filename, true, true);
|
||||||
|
|
||||||
|
int lineNumber = 0;
|
||||||
|
std::string patternLine;
|
||||||
|
while (getline(patternFile, patternLine)) {
|
||||||
|
lineNumber++;
|
||||||
|
if (std::isalpha(patternLine[0])) {
|
||||||
|
TrafficConfigurationType trafficConf;
|
||||||
|
bool shouldSkipLine = false;
|
||||||
|
if (trafficConf.parseConfigurationLine(patternLine, logger, lineNumber)) {
|
||||||
|
while (getline(patternFile, patternLine) && std::isalpha(patternLine[0])) {
|
||||||
|
lineNumber++;
|
||||||
|
if (!trafficConf.parseConfigurationLine(patternLine, logger, lineNumber)) {
|
||||||
|
shouldSkipLine = true;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
lineNumber++;
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
shouldSkipLine = true;
|
||||||
|
}
|
||||||
|
if (!shouldSkipLine) {
|
||||||
|
if (trafficConf.checkTrafficDetailCorrectness()) {
|
||||||
|
patterns.push_back(std::move(trafficConf));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
} // namespace ndn
|
} // namespace ndn
|
||||||
|
|
||||||
#endif // NTG_UTIL_HPP
|
#endif // NTG_UTIL_HPP
|
||||||
Reference in new issue
Block a user