blob: 83ea6db0712a9c7aeaf0de477717f806fad69f8d [file] [log] [blame]
Alexander Afanasyeva8f2a922014-02-26 14:21:56 -08001/* -*- Mode:C++; c-file-style:"gnu"; indent-tabs-mode:nil -*- */
Eric Newberryc8e18582018-05-31 19:27:01 -07002/*
Eric Newberryb4ef4782018-06-21 00:05:46 -07003 * Copyright (c) 2014-2018 Arizona Board of Regents.
Alexander Afanasyeva8f2a922014-02-26 14:21:56 -08004 *
Davide Pesaventod0b59982015-02-27 19:15:15 +01005 * This program is free software: you can redistribute it and/or modify
6 * it under the terms of the GNU General Public License as published by
7 * the Free Software Foundation, either version 3 of the License, or
8 * (at your option) any later version.
9 *
10 * This program is distributed in the hope that it will be useful,
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 * GNU General Public License for more details.
14 *
15 * You should have received a copy of the GNU General Public License
16 * along with this program. If not, see <http://www.gnu.org/licenses/>.
Alexander Afanasyeva8f2a922014-02-26 14:21:56 -080017 *
18 * Author: Jerald Paul Abraham <jeraldabraham@email.arizona.edu>
19 */
20
Eric Newberryc8e18582018-05-31 19:27:01 -070021#include "logger.hpp"
22
23#include <ndn-cxx/face.hpp>
24#include <ndn-cxx/security/key-chain.hpp>
25#include <ndn-cxx/security/signing-info.hpp>
26#include <ndn-cxx/util/backports.hpp>
jeraldabraham420dbf02014-04-25 22:58:31 -070027
Davide Pesaventod0b59982015-02-27 19:15:15 +010028#include <boost/asio/io_service.hpp>
29#include <boost/asio/signal_set.hpp>
Alexander Afanasyeva8f2a922014-02-26 14:21:56 -080030#include <boost/filesystem.hpp>
jeraldabraham420dbf02014-04-25 22:58:31 -070031#include <boost/noncopyable.hpp>
Alexander Afanasyeva8f2a922014-02-26 14:21:56 -080032
Eric Newberryc8e18582018-05-31 19:27:01 -070033#include <cctype>
34#include <cstdlib>
35#include <fstream>
36#include <string>
37#include <unistd.h>
38#include <vector>
Alexander Afanasyeva8f2a922014-02-26 14:21:56 -080039
40namespace ndn {
41
jeraldabraham420dbf02014-04-25 22:58:31 -070042class NdnTrafficServer : boost::noncopyable
Alexander Afanasyeva8f2a922014-02-26 14:21:56 -080043{
44public:
jeraldabrahamcc3c6c92014-03-28 02:21:45 -070045 explicit
Davide Pesaventod0b59982015-02-27 19:15:15 +010046 NdnTrafficServer(const char* programName)
jeraldabrahamcc3c6c92014-03-28 02:21:45 -070047 : m_logger("NdnTrafficServer")
48 , m_programName(programName)
49 , m_hasError(false)
jeraldabraham420dbf02014-04-25 22:58:31 -070050 , m_hasQuietLogging(false)
jeraldabrahamcc3c6c92014-03-28 02:21:45 -070051 , m_nRegistrationsFailed(0)
52 , m_nMaximumInterests(-1)
53 , m_nInterestsReceived(0)
54 , m_contentDelay(time::milliseconds(-1))
Spencer Lee8e990232015-11-27 03:54:39 -070055 , m_instanceId(to_string(std::rand()))
jeraldabrahamcc3c6c92014-03-28 02:21:45 -070056 , m_face(m_ioService)
Eric Newberry51459402018-06-28 00:06:18 -070057 , m_signalSet(m_ioService, SIGINT, SIGTERM)
Alexander Afanasyeva8f2a922014-02-26 14:21:56 -080058 {
Alexander Afanasyeva8f2a922014-02-26 14:21:56 -080059 }
60
61 class DataTrafficConfiguration
62 {
63 public:
Alexander Afanasyeva8f2a922014-02-26 14:21:56 -080064 DataTrafficConfiguration()
jeraldabrahamcc3c6c92014-03-28 02:21:45 -070065 : m_contentType(-1)
66 , m_freshnessPeriod(time::milliseconds(-1))
67 , m_contentBytes(-1)
68 , m_contentDelay(time::milliseconds(-1))
69 , m_nInterestsReceived(0)
Spencer Leeef561432015-12-13 19:40:22 -070070 , m_signingInfo()
Alexander Afanasyeva8f2a922014-02-26 14:21:56 -080071 {
Alexander Afanasyeva8f2a922014-02-26 14:21:56 -080072 }
73
74 void
Alexander Afanasyevfda32a32014-03-20 10:50:00 -070075 printTrafficConfiguration(Logger& logger)
Alexander Afanasyeva8f2a922014-02-26 14:21:56 -080076 {
Spencer Leeef561432015-12-13 19:40:22 -070077 std::stringstream detail;
Davide Pesaventod0b59982015-02-27 19:15:15 +010078
Eric Newberryc8e18582018-05-31 19:27:01 -070079 if (!m_name.empty()) {
Spencer Leeef561432015-12-13 19:40:22 -070080 detail << "Name=" << m_name << ", ";
Eric Newberryc8e18582018-05-31 19:27:01 -070081 }
82 if (m_contentType >= 0) {
Spencer Leeef561432015-12-13 19:40:22 -070083 detail << "ContentType=" << to_string(m_contentType) << ", ";
Eric Newberryc8e18582018-05-31 19:27:01 -070084 }
85 if (m_freshnessPeriod >= time::milliseconds(0)) {
Spencer Leeef561432015-12-13 19:40:22 -070086 detail << "FreshnessPeriod=" <<
87 to_string(static_cast<int>(m_freshnessPeriod.count())) << ", ";
Eric Newberryc8e18582018-05-31 19:27:01 -070088 }
89 if (m_contentBytes >= 0) {
Spencer Leeef561432015-12-13 19:40:22 -070090 detail << "ContentBytes=" << to_string(m_contentBytes) << ", ";
Eric Newberryc8e18582018-05-31 19:27:01 -070091 }
92 if (m_contentDelay >= time::milliseconds(0)) {
Spencer Leeef561432015-12-13 19:40:22 -070093 detail << "ContentDelay=" << to_string(m_contentDelay.count()) << ", ";
Eric Newberryc8e18582018-05-31 19:27:01 -070094 }
95 if (!m_content.empty()) {
Spencer Leeef561432015-12-13 19:40:22 -070096 detail << "Content=" << m_content << ", ";
Eric Newberryc8e18582018-05-31 19:27:01 -070097 }
Spencer Leeef561432015-12-13 19:40:22 -070098 detail << "SigningInfo=" << m_signingInfo;
Davide Pesaventod0b59982015-02-27 19:15:15 +010099
Spencer Leeef561432015-12-13 19:40:22 -0700100 logger.log(detail.str(), false, false);
Alexander Afanasyeva8f2a922014-02-26 14:21:56 -0800101 }
102
Alexander Afanasyeva8f2a922014-02-26 14:21:56 -0800103 bool
Davide Pesaventod0b59982015-02-27 19:15:15 +0100104 extractParameterValue(const std::string& detail, std::string& parameter, std::string& value)
Alexander Afanasyeva8f2a922014-02-26 14:21:56 -0800105 {
Alexander Afanasyeva8f2a922014-02-26 14:21:56 -0800106 std::string allowedCharacters = ":/+._-%";
Davide Pesaventod0b59982015-02-27 19:15:15 +0100107 std::size_t i = 0;
108
Alexander Afanasyeva8f2a922014-02-26 14:21:56 -0800109 parameter = "";
110 value = "";
Davide Pesaventod0b59982015-02-27 19:15:15 +0100111 while (detail[i] != '=' && i < detail.length()) {
112 parameter += detail[i];
113 i++;
114 }
Alexander Afanasyeva8f2a922014-02-26 14:21:56 -0800115 if (i == detail.length())
116 return false;
Davide Pesaventod0b59982015-02-27 19:15:15 +0100117
Alexander Afanasyeva8f2a922014-02-26 14:21:56 -0800118 i++;
Alexander Afanasyevfda32a32014-03-20 10:50:00 -0700119 while ((std::isalnum(detail[i]) ||
120 allowedCharacters.find(detail[i]) != std::string::npos) &&
Davide Pesaventod0b59982015-02-27 19:15:15 +0100121 i < detail.length()) {
122 value += detail[i];
123 i++;
124 }
125
126 if (parameter.empty() || value.empty())
Alexander Afanasyeva8f2a922014-02-26 14:21:56 -0800127 return false;
Davide Pesaventod0b59982015-02-27 19:15:15 +0100128 else
129 return true;
Alexander Afanasyeva8f2a922014-02-26 14:21:56 -0800130 }
131
132 bool
Alexander Afanasyevfda32a32014-03-20 10:50:00 -0700133 processConfigurationDetail(const std::string& detail,
jeraldabrahamcc3c6c92014-03-28 02:21:45 -0700134 Logger& logger,
135 int lineNumber)
Alexander Afanasyeva8f2a922014-02-26 14:21:56 -0800136 {
137 std::string parameter, value;
Spencer Leee7a5b742015-10-29 02:18:11 -0700138 if (extractParameterValue(detail, parameter, value)) {
139 if (parameter == "Name") {
140 m_name = value;
141 }
142 else if (parameter == "ContentType") {
143 m_contentType = std::stoi(value);
144 }
145 else if (parameter == "FreshnessPeriod") {
146 m_freshnessPeriod = time::milliseconds(std::stoi(value));
147 }
148 else if (parameter == "ContentDelay") {
149 m_contentDelay = time::milliseconds(std::stoi(value));
150 }
151 else if (parameter == "ContentBytes") {
152 m_contentBytes = std::stoi(value);
153 }
154 else if (parameter == "Content") {
155 m_content = value;
156 }
Spencer Leeef561432015-12-13 19:40:22 -0700157 else if (parameter == "SigningInfo") {
158 m_signingInfo = security::SigningInfo(value);
Alexander Afanasyeva8f2a922014-02-26 14:21:56 -0800159 }
Spencer Leee7a5b742015-10-29 02:18:11 -0700160 else {
Spencer Lee8e990232015-11-27 03:54:39 -0700161 logger.log("Line " + to_string(lineNumber) +
Spencer Leee7a5b742015-10-29 02:18:11 -0700162 " \t- Invalid Parameter='" + parameter + "'", false, true);
Alexander Afanasyeva8f2a922014-02-26 14:21:56 -0800163 }
Spencer Leee7a5b742015-10-29 02:18:11 -0700164 }
165 else {
Spencer Lee8e990232015-11-27 03:54:39 -0700166 logger.log("Line " + to_string(lineNumber) +
Spencer Leee7a5b742015-10-29 02:18:11 -0700167 " \t- Improper Traffic Configuration Line - " + detail, false, true);
168 return false;
169 }
170
Alexander Afanasyeva8f2a922014-02-26 14:21:56 -0800171 return true;
172 }
173
174 bool
175 checkTrafficDetailCorrectness()
176 {
177 return true;
178 }
179
Davide Pesaventod0b59982015-02-27 19:15:15 +0100180 private:
jeraldabrahamcc3c6c92014-03-28 02:21:45 -0700181 std::string m_name;
182 int m_contentType;
183 time::milliseconds m_freshnessPeriod;
184 int m_contentBytes;
185 time::milliseconds m_contentDelay;
186 std::string m_content;
187 int m_nInterestsReceived;
Spencer Leeef561432015-12-13 19:40:22 -0700188 security::SigningInfo m_signingInfo;
Alexander Afanasyeva8f2a922014-02-26 14:21:56 -0800189
Davide Pesaventod0b59982015-02-27 19:15:15 +0100190 friend class NdnTrafficServer;
Alexander Afanasyeva8f2a922014-02-26 14:21:56 -0800191 };
192
Alexander Afanasyeva8f2a922014-02-26 14:21:56 -0800193 void
Davide Pesaventod0b59982015-02-27 19:15:15 +0100194 usage() const
Alexander Afanasyeva8f2a922014-02-26 14:21:56 -0800195 {
Davide Pesaventod0b59982015-02-27 19:15:15 +0100196 std::cout << "Usage:\n"
197 << " " << m_programName << " [options] <Traffic_Configuration_File>\n"
198 << "\n"
199 << "Respond to Interests as per provided Traffic Configuration File.\n"
200 << "Multiple prefixes can be configured for handling.\n"
201 << "Set environment variable NDN_TRAFFIC_LOGFOLDER to redirect output to a log file.\n"
202 << "\n"
203 << "Options:\n"
204 << " [-d interval] - set delay before responding to interest, in milliseconds\n"
205 << " [-c count] - specify maximum number of interests to be satisfied\n"
206 << " [-q] - quiet mode: no interest reception/data generation logging\n"
207 << " [-h] - print this help text and exit\n";
208 exit(EXIT_FAILURE);
Alexander Afanasyeva8f2a922014-02-26 14:21:56 -0800209 }
210
jeraldabrahamcc3c6c92014-03-28 02:21:45 -0700211 void
212 setMaximumInterests(int maximumInterests)
Alexander Afanasyeva8f2a922014-02-26 14:21:56 -0800213 {
Eric Newberryc8e18582018-05-31 19:27:01 -0700214 if (maximumInterests < 0) {
jeraldabrahamcc3c6c92014-03-28 02:21:45 -0700215 usage();
Eric Newberryc8e18582018-05-31 19:27:01 -0700216 }
jeraldabrahamcc3c6c92014-03-28 02:21:45 -0700217 m_nMaximumInterests = maximumInterests;
218 }
219
220 bool
221 hasError() const
222 {
223 return m_hasError;
Alexander Afanasyeva8f2a922014-02-26 14:21:56 -0800224 }
225
226 void
jeraldabrahamcc3c6c92014-03-28 02:21:45 -0700227 setContentDelay(int contentDelay)
Alexander Afanasyeva8f2a922014-02-26 14:21:56 -0800228 {
Eric Newberryc8e18582018-05-31 19:27:01 -0700229 if (contentDelay < 0) {
Alexander Afanasyeva8f2a922014-02-26 14:21:56 -0800230 usage();
Eric Newberryc8e18582018-05-31 19:27:01 -0700231 }
jeraldabrahamcc3c6c92014-03-28 02:21:45 -0700232 m_contentDelay = time::milliseconds(contentDelay);
Alexander Afanasyeva8f2a922014-02-26 14:21:56 -0800233 }
234
235 void
Davide Pesaventod0b59982015-02-27 19:15:15 +0100236 setConfigurationFile(const char* configurationFile)
Alexander Afanasyeva8f2a922014-02-26 14:21:56 -0800237 {
jeraldabrahamcc3c6c92014-03-28 02:21:45 -0700238 m_configurationFile = configurationFile;
Alexander Afanasyeva8f2a922014-02-26 14:21:56 -0800239 }
240
241 void
jeraldabraham420dbf02014-04-25 22:58:31 -0700242 setQuietLogging()
243 {
244 m_hasQuietLogging = true;
245 }
246
247 void
Alexander Afanasyeva8f2a922014-02-26 14:21:56 -0800248 signalHandler()
249 {
Alexander Afanasyeva8f2a922014-02-26 14:21:56 -0800250 logStatistics();
Davide Pesaventod0b59982015-02-27 19:15:15 +0100251
jeraldabrahamcc3c6c92014-03-28 02:21:45 -0700252 m_face.shutdown();
Alexander Afanasyev976c3972014-05-26 17:03:40 +0300253 m_ioService.stop();
Davide Pesaventod0b59982015-02-27 19:15:15 +0100254
255 exit(m_hasError ? EXIT_FAILURE : EXIT_SUCCESS);
Alexander Afanasyeva8f2a922014-02-26 14:21:56 -0800256 }
257
258 void
259 logStatistics()
260 {
Alexander Afanasyeva8f2a922014-02-26 14:21:56 -0800261 m_logger.log("\n\n== Interest Traffic Report ==\n", false, true);
Alexander Afanasyevfda32a32014-03-20 10:50:00 -0700262 m_logger.log("Total Traffic Pattern Types = " +
Spencer Lee8e990232015-11-27 03:54:39 -0700263 to_string(m_trafficPatterns.size()), false, true);
Alexander Afanasyevfda32a32014-03-20 10:50:00 -0700264 m_logger.log("Total Interests Received = " +
Spencer Lee8e990232015-11-27 03:54:39 -0700265 to_string(m_nInterestsReceived), false, true);
Davide Pesaventod0b59982015-02-27 19:15:15 +0100266
Eric Newberryc8e18582018-05-31 19:27:01 -0700267 if (m_nInterestsReceived < m_nMaximumInterests) {
jeraldabrahamcc3c6c92014-03-28 02:21:45 -0700268 m_hasError = true;
Eric Newberryc8e18582018-05-31 19:27:01 -0700269 }
Davide Pesaventod0b59982015-02-27 19:15:15 +0100270
Eric Newberryc8e18582018-05-31 19:27:01 -0700271 for (std::size_t patternId = 0; patternId < m_trafficPatterns.size(); patternId++) {
272 m_logger.log("\nTraffic Pattern Type #" + to_string(patternId + 1), false, true);
273 m_trafficPatterns[patternId].printTrafficConfiguration(m_logger);
274 m_logger.log("Total Interests Received = " + to_string(
275 m_trafficPatterns[patternId].m_nInterestsReceived) + "\n", false, true);
276 }
Alexander Afanasyeva8f2a922014-02-26 14:21:56 -0800277 }
278
279 bool
280 checkTrafficPatternCorrectness()
281 {
282 return true;
283 }
284
285 void
jeraldabrahamcc3c6c92014-03-28 02:21:45 -0700286 parseConfigurationFile()
Alexander Afanasyeva8f2a922014-02-26 14:21:56 -0800287 {
Alexander Afanasyeva8f2a922014-02-26 14:21:56 -0800288 std::string patternLine;
289 std::ifstream patternFile;
jeraldabrahamcc3c6c92014-03-28 02:21:45 -0700290 m_logger.log("Analyzing Traffic Configuration File: " + m_configurationFile, true, true);
Davide Pesaventod0b59982015-02-27 19:15:15 +0100291
jeraldabrahamcc3c6c92014-03-28 02:21:45 -0700292 patternFile.open(m_configurationFile.c_str());
Eric Newberryc8e18582018-05-31 19:27:01 -0700293 if (patternFile.is_open()) {
294 int lineNumber = 0;
295 while (getline(patternFile, patternLine)) {
296 lineNumber++;
297 if (std::isalpha(patternLine[0])) {
298 DataTrafficConfiguration dataData;
299 bool shouldSkipLine = false;
300 if (dataData.processConfigurationDetail(patternLine, m_logger, lineNumber)) {
301 while (getline(patternFile, patternLine) && std::isalpha(patternLine[0])) {
302 lineNumber++;
303 if (!dataData.processConfigurationDetail(patternLine, m_logger, lineNumber)) {
304 shouldSkipLine = true;
305 break;
Alexander Afanasyeva8f2a922014-02-26 14:21:56 -0800306 }
Eric Newberryc8e18582018-05-31 19:27:01 -0700307 }
308 lineNumber++;
Alexander Afanasyeva8f2a922014-02-26 14:21:56 -0800309 }
Eric Newberryc8e18582018-05-31 19:27:01 -0700310 else {
311 shouldSkipLine = true;
Alexander Afanasyeva8f2a922014-02-26 14:21:56 -0800312 }
Eric Newberryc8e18582018-05-31 19:27:01 -0700313 if (!shouldSkipLine) {
314 if (dataData.checkTrafficDetailCorrectness()) {
315 m_trafficPatterns.push_back(dataData);
316 }
Alexander Afanasyeva8f2a922014-02-26 14:21:56 -0800317 }
Eric Newberryc8e18582018-05-31 19:27:01 -0700318 }
Alexander Afanasyeva8f2a922014-02-26 14:21:56 -0800319 }
Eric Newberryc8e18582018-05-31 19:27:01 -0700320 patternFile.close();
321
322 if (!checkTrafficPatternCorrectness()) {
323 m_logger.log("ERROR - Traffic Configuration Provided Is Not Proper - " +
324 m_configurationFile, false, true);
Davide Pesaventod0b59982015-02-27 19:15:15 +0100325 exit(EXIT_FAILURE);
Alexander Afanasyeva8f2a922014-02-26 14:21:56 -0800326 }
Eric Newberryc8e18582018-05-31 19:27:01 -0700327
328 m_logger.log("Traffic Configuration File Processing Completed\n", true, false);
329 for (std::size_t patternId = 0; patternId < m_trafficPatterns.size(); patternId++) {
330 m_logger.log("Traffic Pattern Type #" +
331 to_string(patternId + 1), false, false);
332 m_trafficPatterns[patternId].printTrafficConfiguration(m_logger);
333 m_logger.log("", false, false);
334 }
335 }
336 else {
337 m_logger.log("ERROR - Unable To Open Traffic Configuration File: " +
338 m_configurationFile, false, true);
Eric Newberryc8e18582018-05-31 19:27:01 -0700339 exit(EXIT_FAILURE);
340 }
Alexander Afanasyeva8f2a922014-02-26 14:21:56 -0800341 }
342
343 void
344 initializeTrafficConfiguration()
345 {
Eric Newberryc8e18582018-05-31 19:27:01 -0700346 if (boost::filesystem::exists(boost::filesystem::path(m_configurationFile))) {
347 if (boost::filesystem::is_regular_file(boost::filesystem::path(m_configurationFile))) {
348 parseConfigurationFile();
Alexander Afanasyeva8f2a922014-02-26 14:21:56 -0800349 }
Eric Newberryc8e18582018-05-31 19:27:01 -0700350 else {
351 m_logger.log("ERROR - Traffic Configuration File Is Not A Regular File: " +
352 m_configurationFile, false, true);
Davide Pesaventod0b59982015-02-27 19:15:15 +0100353 exit(EXIT_FAILURE);
Alexander Afanasyeva8f2a922014-02-26 14:21:56 -0800354 }
Eric Newberryc8e18582018-05-31 19:27:01 -0700355 }
356 else {
357 m_logger.log("ERROR - Traffic Configuration File Does Not Exist: " +
358 m_configurationFile, false, true);
Eric Newberryc8e18582018-05-31 19:27:01 -0700359 exit(EXIT_FAILURE);
360 }
Alexander Afanasyeva8f2a922014-02-26 14:21:56 -0800361 }
362
363 static std::string
Davide Pesaventod0b59982015-02-27 19:15:15 +0100364 getRandomByteString(std::size_t randomSize)
Alexander Afanasyeva8f2a922014-02-26 14:21:56 -0800365 {
jeraldabrahamcc3c6c92014-03-28 02:21:45 -0700366 std::string randomString;
Eric Newberryc8e18582018-05-31 19:27:01 -0700367 for (std::size_t i = 0; i < randomSize; i++) {
jeraldabrahamcc3c6c92014-03-28 02:21:45 -0700368 randomString += static_cast<char>(std::rand() % 128);
Eric Newberryc8e18582018-05-31 19:27:01 -0700369 }
jeraldabrahamcc3c6c92014-03-28 02:21:45 -0700370 return randomString;
Alexander Afanasyeva8f2a922014-02-26 14:21:56 -0800371 }
372
373 void
Alexander Afanasyevfda32a32014-03-20 10:50:00 -0700374 onInterest(const Name& name, const Interest& interest, int patternId)
Alexander Afanasyeva8f2a922014-02-26 14:21:56 -0800375 {
Spencer Leee7a5b742015-10-29 02:18:11 -0700376 auto& pattern = m_trafficPatterns[patternId];
377
Eric Newberryc8e18582018-05-31 19:27:01 -0700378 if (m_nMaximumInterests < 0 || m_nInterestsReceived < m_nMaximumInterests) {
379 Data data(interest.getName());
Alexander Afanasyeva8f2a922014-02-26 14:21:56 -0800380
Eric Newberryc8e18582018-05-31 19:27:01 -0700381 if (pattern.m_contentType >= 0)
382 data.setContentType(pattern.m_contentType);
jeraldabrahamcc3c6c92014-03-28 02:21:45 -0700383
Eric Newberryc8e18582018-05-31 19:27:01 -0700384 if (pattern.m_freshnessPeriod >= time::milliseconds(0))
385 data.setFreshnessPeriod(pattern.m_freshnessPeriod);
jeraldabrahamcc3c6c92014-03-28 02:21:45 -0700386
Eric Newberryc8e18582018-05-31 19:27:01 -0700387 std::string content;
388 if (pattern.m_contentBytes >= 0)
389 content = getRandomByteString(pattern.m_contentBytes);
390 if (!pattern.m_content.empty())
391 content = pattern.m_content;
jeraldabrahamcc3c6c92014-03-28 02:21:45 -0700392
Eric Newberryc8e18582018-05-31 19:27:01 -0700393 data.setContent(reinterpret_cast<const uint8_t*>(content.c_str()), content.length());
394 m_keyChain.sign(data, pattern.m_signingInfo);
Spencer Leee7a5b742015-10-29 02:18:11 -0700395
Eric Newberryc8e18582018-05-31 19:27:01 -0700396 m_nInterestsReceived++;
397 pattern.m_nInterestsReceived++;
Davide Pesaventod0b59982015-02-27 19:15:15 +0100398
Eric Newberryc8e18582018-05-31 19:27:01 -0700399 if (!m_hasQuietLogging) {
400 std::string logLine =
401 "Interest Received - PatternType=" + to_string(patternId + 1) +
402 ", GlobalID=" + to_string(m_nInterestsReceived) +
403 ", LocalID=" + to_string(pattern.m_nInterestsReceived) +
404 ", Name=" + pattern.m_name;
405 m_logger.log(logLine, true, false);
jeraldabrahamcc3c6c92014-03-28 02:21:45 -0700406 }
Eric Newberryc8e18582018-05-31 19:27:01 -0700407
408 if (pattern.m_contentDelay > time::milliseconds(-1))
409 usleep(pattern.m_contentDelay.count() * 1000);
410 if (m_contentDelay > time::milliseconds(-1))
411 usleep(m_contentDelay.count() * 1000);
412 m_face.put(data);
413 }
414 if (m_nMaximumInterests >= 0 && m_nInterestsReceived == m_nMaximumInterests) {
415 logStatistics();
Eric Newberryb4ef4782018-06-21 00:05:46 -0700416 for (auto registeredPrefix : m_registeredPrefixes) {
417 m_face.unsetInterestFilter(registeredPrefix);
418 }
Eric Newberry51459402018-06-28 00:06:18 -0700419 m_signalSet.cancel();
Eric Newberryc8e18582018-05-31 19:27:01 -0700420 }
Alexander Afanasyeva8f2a922014-02-26 14:21:56 -0800421 }
422
423 void
Alexander Afanasyevfda32a32014-03-20 10:50:00 -0700424 onRegisterFailed(const ndn::Name& prefix, const std::string& reason, int patternId)
Alexander Afanasyeva8f2a922014-02-26 14:21:56 -0800425 {
Davide Pesaventod0b59982015-02-27 19:15:15 +0100426 std::string logLine;
Spencer Lee8e990232015-11-27 03:54:39 -0700427 logLine += "Prefix Registration Failed - PatternType=" + to_string(patternId + 1);
jeraldabrahamcc3c6c92014-03-28 02:21:45 -0700428 logLine += ", Name=" + m_trafficPatterns[patternId].m_name;
Alexander Afanasyeva8f2a922014-02-26 14:21:56 -0800429 m_logger.log(logLine, true, true);
Davide Pesaventod0b59982015-02-27 19:15:15 +0100430
jeraldabrahamcc3c6c92014-03-28 02:21:45 -0700431 m_nRegistrationsFailed++;
Eric Newberryc8e18582018-05-31 19:27:01 -0700432 if (m_nRegistrationsFailed == m_trafficPatterns.size()) {
433 m_hasError = true;
434 signalHandler();
435 }
Alexander Afanasyeva8f2a922014-02-26 14:21:56 -0800436 }
437
438 void
jeraldabrahamcc3c6c92014-03-28 02:21:45 -0700439 run()
Alexander Afanasyeva8f2a922014-02-26 14:21:56 -0800440 {
Eric Newberry51459402018-06-28 00:06:18 -0700441 m_signalSet.async_wait(bind(&NdnTrafficServer::signalHandler, this));
Davide Pesaventod0b59982015-02-27 19:15:15 +0100442
jeraldabrahamcc3c6c92014-03-28 02:21:45 -0700443 m_logger.initializeLog(m_instanceId);
Alexander Afanasyeva8f2a922014-02-26 14:21:56 -0800444 initializeTrafficConfiguration();
Eric Newberryc8e18582018-05-31 19:27:01 -0700445 if (m_nMaximumInterests == 0) {
446 logStatistics();
Eric Newberryc8e18582018-05-31 19:27:01 -0700447 return;
448 }
jeraldabrahamcc3c6c92014-03-28 02:21:45 -0700449
Eric Newberryc8e18582018-05-31 19:27:01 -0700450 for (std::size_t patternId = 0; patternId < m_trafficPatterns.size(); patternId++) {
Eric Newberryb4ef4782018-06-21 00:05:46 -0700451 m_registeredPrefixes.push_back(
452 m_face.setInterestFilter(m_trafficPatterns[patternId].m_name,
453 bind(&NdnTrafficServer::onInterest, this, _1, _2, patternId),
Eric Newberry51459402018-06-28 00:06:18 -0700454 nullptr,
Eric Newberryb4ef4782018-06-21 00:05:46 -0700455 bind(&NdnTrafficServer::onRegisterFailed, this, _1, _2, patternId)));
Eric Newberryc8e18582018-05-31 19:27:01 -0700456 }
Alexander Afanasyeva8f2a922014-02-26 14:21:56 -0800457
458 try {
jeraldabrahamcc3c6c92014-03-28 02:21:45 -0700459 m_face.processEvents();
Alexander Afanasyeva8f2a922014-02-26 14:21:56 -0800460 }
Davide Pesaventod0b59982015-02-27 19:15:15 +0100461 catch (const std::exception& e) {
462 m_logger.log("ERROR: " + std::string(e.what()), true, true);
jeraldabrahamcc3c6c92014-03-28 02:21:45 -0700463 m_hasError = true;
Alexander Afanasyev976c3972014-05-26 17:03:40 +0300464 m_ioService.stop();
Alexander Afanasyeva8f2a922014-02-26 14:21:56 -0800465 }
466 }
467
468private:
jeraldabrahamcc3c6c92014-03-28 02:21:45 -0700469 KeyChain m_keyChain;
Alexander Afanasyev740812e2014-10-30 15:37:45 -0700470 Logger m_logger;
jeraldabrahamcc3c6c92014-03-28 02:21:45 -0700471 std::string m_programName;
472 bool m_hasError;
jeraldabraham420dbf02014-04-25 22:58:31 -0700473 bool m_hasQuietLogging;
Davide Pesaventod0b59982015-02-27 19:15:15 +0100474 std::size_t m_nRegistrationsFailed;
Alexander Afanasyev740812e2014-10-30 15:37:45 -0700475 int m_nMaximumInterests;
476 int m_nInterestsReceived;
477 time::milliseconds m_contentDelay;
478 std::string m_instanceId;
jeraldabrahamcc3c6c92014-03-28 02:21:45 -0700479 std::string m_configurationFile;
Alexander Afanasyev740812e2014-10-30 15:37:45 -0700480
Alexander Afanasyev976c3972014-05-26 17:03:40 +0300481 boost::asio::io_service m_ioService;
jeraldabrahamcc3c6c92014-03-28 02:21:45 -0700482 Face m_face;
Eric Newberry51459402018-06-28 00:06:18 -0700483 boost::asio::signal_set m_signalSet;
jeraldabrahamcc3c6c92014-03-28 02:21:45 -0700484 std::vector<DataTrafficConfiguration> m_trafficPatterns;
Eric Newberryb4ef4782018-06-21 00:05:46 -0700485 std::vector<const RegisteredPrefixId*> m_registeredPrefixes;
Alexander Afanasyeva8f2a922014-02-26 14:21:56 -0800486};
487
488} // namespace ndn
489
Alexander Afanasyevfda32a32014-03-20 10:50:00 -0700490int
491main(int argc, char* argv[])
Alexander Afanasyeva8f2a922014-02-26 14:21:56 -0800492{
Davide Pesaventod0b59982015-02-27 19:15:15 +0100493 std::srand(std::time(nullptr));
494
495 ndn::NdnTrafficServer server(argv[0]);
Alexander Afanasyeva8f2a922014-02-26 14:21:56 -0800496 int option;
jeraldabraham420dbf02014-04-25 22:58:31 -0700497 while ((option = getopt(argc, argv, "hqc:d:")) != -1) {
Alexander Afanasyeva8f2a922014-02-26 14:21:56 -0800498 switch (option) {
jeraldabrahamcc3c6c92014-03-28 02:21:45 -0700499 case 'h':
Davide Pesaventod0b59982015-02-27 19:15:15 +0100500 server.usage();
Alexander Afanasyeva8f2a922014-02-26 14:21:56 -0800501 break;
jeraldabrahamcc3c6c92014-03-28 02:21:45 -0700502 case 'c':
Davide Pesaventod0b59982015-02-27 19:15:15 +0100503 server.setMaximumInterests(atoi(optarg));
Alexander Afanasyeva8f2a922014-02-26 14:21:56 -0800504 break;
jeraldabrahamcc3c6c92014-03-28 02:21:45 -0700505 case 'd':
Davide Pesaventod0b59982015-02-27 19:15:15 +0100506 server.setContentDelay(atoi(optarg));
jeraldabrahamcc3c6c92014-03-28 02:21:45 -0700507 break;
jeraldabraham420dbf02014-04-25 22:58:31 -0700508 case 'q':
Davide Pesaventod0b59982015-02-27 19:15:15 +0100509 server.setQuietLogging();
jeraldabraham420dbf02014-04-25 22:58:31 -0700510 break;
jeraldabrahamcc3c6c92014-03-28 02:21:45 -0700511 default:
Davide Pesaventod0b59982015-02-27 19:15:15 +0100512 server.usage();
Alexander Afanasyeva8f2a922014-02-26 14:21:56 -0800513 break;
514 }
515 }
516
517 argc -= optind;
518 argv += optind;
519
Eric Newberryc8e18582018-05-31 19:27:01 -0700520 if (!argc) {
Davide Pesaventod0b59982015-02-27 19:15:15 +0100521 server.usage();
Eric Newberryc8e18582018-05-31 19:27:01 -0700522 }
Alexander Afanasyeva8f2a922014-02-26 14:21:56 -0800523
Davide Pesaventod0b59982015-02-27 19:15:15 +0100524 server.setConfigurationFile(argv[0]);
525 server.run();
Alexander Afanasyeva8f2a922014-02-26 14:21:56 -0800526
Davide Pesaventod0b59982015-02-27 19:15:15 +0100527 return server.hasError() ? EXIT_FAILURE : EXIT_SUCCESS;
Eric Newberryc8e18582018-05-31 19:27:01 -0700528}