A Discrete-Event Network Simulator
API
Loading...
Searching...
No Matches
global-routing-multi-switch-plus-router.cc
Go to the documentation of this file.
1/*
2 * Copyright (c) 2015 - Chip Webb
3 *
4 * This program is free software; you can redistribute it and/or modify
5 * it under the terms of the GNU General Public License version 2 as
6 * published by the Free Software Foundation;
7 *
8 * This program is distributed in the hope that it will be useful,
9 * but WITHOUT ANY WARRANTY; without even the implied warranty of
10 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
11 * GNU General Public License for more details.
12 *
13 * You should have received a copy of the GNU General Public License
14 * along with this program; if not, write to the Free Software
15 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
16 *
17 * Author: Chip Webb <ns3 (at) chipwebb.com>
18 *
19 */
20
21// ###################################################################### //
22// Network topology //
23// ---------------------------------------------------------------------- //
24// //
25// This example shows two L2 LANs connected by a WAN link and illustrates //
26// a network that has multiple L2 switches between L3 routers. //
27// //
28// It serves as a test case to verify a patch to global-router-interface //
29// that fixes a previous bug (#2102 in the ns-3 tracker) but is also //
30// another example program. //
31// //
32// The LANs are "top" [192.168.1/24] and "bottom" [192.168.2/24]. //
33// Each LAN network is interconnected by several L2 switches, and each //
34// LAN has its own router to act as a gateway with the WAN. Each LAN //
35// has two endpoints upon which is installed a UDP echo client or server //
36// that are used to test connectivity over the LANs & WAN. //
37// //
38// One pair of UDP endpoints (t3 and b3) have LAN connections with only //
39// one switch between them and their local routers. This path works with //
40// unpatched ns3 code (3.24 & earlier) as well as with the patch applied. //
41// //
42// Another pair of endpoints (t2 and b2) have LAN connections with //
43// a chain of multiple switches between them and their local router. //
44// This path will only work after applying the associated patch. //
45// //
46// The LAN links are modeled by half-duplex Ethernet CSMA links which //
47// have command-line-configurable data rate and latency. //
48// //
49// There are two types of CSMA links: 100Mbit and 10Mbit. The 100Mbit //
50// links are called csmaX, are denoted by [X] in the diagram and can //
51// be controlled with the --csmaXRate and --csmaXDelay command line args. //
52// The 10Mbit links are called csmaY, are denoted by [Y] in the diagram //
53// and can be controlled with the --csmaYRate and --csmaYDelay command //
54// line arguments. Both the top and bottom LAN have a mixture of //
55// 100Mbit/s and 10Mbit/s links. //
56// //
57// The WAN is modeled by a point-to-point link which has configurable //
58// data rate and latency. Unlike many typical home/work networks, //
59// the routers do not perform NAT. //
60// //
61// The WAN link is denoted by [P] in the diagram, and the //
62// speed and latency can be set from the command line with the //
63// --p2pRate and --p2pDelay options. The default for this link is 5Mbit/s //
64// and 50ms delay //
65// //
66// Note: Names in parenthesis after NetDevices are pcap tap locations. //
67// //
68// ---------------------------------------------------------------------- //
69// //
70// 192.168. 192.168. //
71// .1.2 .1.3 //
72// --------- --------- //
73// | t2 | | t3 | //
74// | UDP | | UDP | //
75// | echo | | echo | Node t2 is a UDP echo client (multi-switch) //
76// | client| | server| Node t3 is a UDP echo server (single-switch) //
77// --------- --------- //
78// CSMA(t2) CSMA(t3) //
79// [X] [X] //
80// [X] [X] //
81// CSMA [X] //
82// --------- [X] //
83// | ts4 | [X] Nodes ts1, ts2, ts3 and ts4 are L2 switches //
84// | (sw) | [X] The top LAN is subnet 192.168.1.* //
85// --------- [X] //
86// CSMA [X] The long chain of switches is designed //
87// [Y] [X] to test whether global-router-interface //
88// [Y] [X] can fully enumerate an IP subnet that has //
89// CSMA [X] multiple interconnected L2 switches. //
90// --------- [X] The problem is documented in Bug #2102. //
91// | ts3 | [X] //
92// | (sw) | [X] //
93// --------- [X] //
94// CSMA [X] //
95// [X] [X] //
96// [X] [X] //
97// CSMA [X] //
98// --------- [X] //
99// | ts2 | [X] //
100// | (sw) | [X] //
101// --------- [X] //
102// CSMA [X] //
103// [Y] [X] //
104// [Y] [X] //
105// CSMA CSMA //
106// ------------------ //
107// | ts1 (switch) | //
108// ------------------ //
109// CSMA //
110// [Y] //
111// [Y] //
112// CSMA(trlan) 192.168.1.1 //
113// ------------------ //
114// | tr (router) | Node tr is an L3 router //
115// ------------------ (between 192.168.1.* & 76.1.1.*) //
116// P2P(trwan) 76.1.1.1 //
117// [P] //
118// [P] //
119// [P] //
120// [P] //
121// [P] The WAN is 76.1.1.* //
122// [P] //
123// [P] //
124// [P] //
125// P2P(brwan) 76.1.1.2 //
126// ------------------ //
127// | br (router) | Node br is an L3 router //
128// ------------------ (between 192.168.2.* & 76.1.1.*) //
129// CSMA(brlan) 192.168.2.1 //
130// [X] //
131// [X] //
132// CSMA //
133// ------------------ Nodes bs1 to bs5 are L2 switches //
134// | bs1 (switch) | The bottom LAN is subnet 192.168.2.* //
135// ------------------ //
136// CSMA CSMA //
137// [Y] [Y] //
138// [Y] [Y] //
139// CSMA [Y] //
140// --------- [Y] //
141// | bs2 | [Y] //
142// | (sw) | [Y] //
143// --------- [Y] //
144// CSMA [Y] //
145// [X] [Y] //
146// [X] [Y] //
147// CSMA [Y] //
148// --------- [Y] //
149// | bs3 | [Y] //
150// | (sw) | [Y] //
151// --------- [Y] //
152// CSMA [Y] //
153// [Y] [Y] //
154// [Y] [Y] //
155// CSMA [Y] //
156// --------- [Y] //
157// | bs4 | [Y] //
158// | (sw) | [Y] //
159// --------- [Y] //
160// CSMA [Y] //
161// [X] [Y] //
162// [X] [Y] //
163// CSMA [Y] //
164// --------- [Y] //
165// | bs5 | [Y] //
166// | (sw) | [Y] //
167// --------- [Y] //
168// CSMA [Y] //
169// [Y] [Y] //
170// [Y] [Y] //
171// CSMA(b2) CSMA(b3) //
172// --------- --------- //
173// | b2 | | b3 | //
174// | UDP | | UDP | //
175// | echo | | echo | Node b2 is a UDP echo server (multi-switch) //
176// | server| | client| Node b3 is a UDP echo client (single-switch) //
177// --------- --------- //
178// 192.168. 192.168. //
179// .2.2 .2.3 //
180// //
181// ---------------------------------------------------------------------- //
182// Explanation //
183// ---------------------------------------------------------------------- //
184// //
185// UDP packet flows are configured between nodes on the top and bottom //
186// LANs (using UDP echo client & server). //
187// //
188// The network carrying the "multi switch" UDP flow is connected with //
189// multiple L2 switches between L3 nodes so it should only work if the //
190// global-router-interface source code properly supports bridging. //
191// //
192// The network carrying the "single switch" UDP flow is connected with //
193// only one L2 switch between L3 nodes so it should work with or //
194// without the patch //
195// //
196// = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = //
197// Traffic summary: //
198// ---------------------------------------------------------------------- //
199// //
200// - UDP flow from t2 (192.168.1.2) to b2 (192.168.2.2) [Multi Switch] //
201// from b3 (192.168.2.3) to t3 (192.168.1.3) [Single Switch] //
202// //
203// = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = //
204// Node List & IP addresses assigned during simulation //
205// ---------------------------------------------------------------------- //
206// t2 : 192.168.1.2 : Top multi-switch UDP echo client //
207// t3 : 192.168.1.3 : Top single-switch UDP echo server //
208// : //
209// ts1 : <no IP> : Top switch 1 (bridge) //
210// ts2 : <no IP> : Top switch 2 (bridge) //
211// ts3 : <no IP> : Top switch 3 (bridge) //
212// ts4 : <no IP> : Top switch 4 (bridge) //
213// : //
214// tr : 192.168.1.1 : Router connecting top LAN (192.168.1.*) //
215// : 76.1.1.1 : to the WAN //
216// : //
217// br : 76.1.1.2 : Router connecting the WAN //
218// : 192.168.2.1 : to bot LAN (192.168.2.*) //
219// : //
220// bs1 : <no IP> : Bottom switch 1 (bridge) //
221// bs2 : <no IP> : Bottom switch 2 (bridge) //
222// bs3 : <no IP> : Bottom switch 3 (bridge) //
223// bs4 : <no IP> : Bottom switch 4 (bridge) //
224// bs5 : <no IP> : Bottom switch 5 (bridge) //
225// : //
226// b2 : 192.168.2.2 : Bottom multi-switch UDP echo server //
227// b3 : 192.168.2.3 : Bottom single-switch UDP echo client //
228// : //
229// ---------------------------------------------------------------------- //
230// Author: Chip Webb <ns3 (a) chipwebb dot com> //
231// ###################################################################### //
232
233#include "ns3/applications-module.h"
234#include "ns3/bridge-module.h"
235#include "ns3/core-module.h"
236#include "ns3/csma-module.h"
237#include "ns3/internet-module.h"
238#include "ns3/network-module.h"
239#include "ns3/point-to-point-module.h"
240
241#include <fstream>
242#include <iostream>
243
244using namespace ns3;
245
246// ########################################################################
247// Main routine
248// ########################################################################
249NS_LOG_COMPONENT_DEFINE("GlobalRoutingMultiSwitchPlusRouter");
250
251#define vssearch(loc, vec) std::find((vec).begin(), (vec).end(), (loc)) != (vec).end()
252
253int
254main(int argc, char* argv[])
255{
256 // ----------------------------------------------------------------------
257 // Default values for command line arguments
258 // ----------------------------------------------------------------------
259 bool verbose = true;
260
261 int simDurationSeconds = 60;
262
263 bool enableUdpMultiSW = true;
264 bool enableUdpSingleSW = true;
265
266 std::string pcapLocations = "";
268
269 std::string csmaXLinkDataRate = "100Mbps";
270 std::string csmaXLinkDelay = "500ns";
271
272 std::string csmaYLinkDataRate = "10Mbps";
273 std::string csmaYLinkDelay = "500ns";
274
275 std::string p2pLinkDataRate = "5Mbps";
276 std::string p2pLinkDelay = "50ms";
277
278 uint16_t udpEchoPort = 9; // The well-known UDP echo port
279
280 // ----------------------------------------------------------------------
281 // Create command line options and get them
282 // ----------------------------------------------------------------------
283 CommandLine cmd(__FILE__);
284
285 cmd.Usage("NOTE: valid --pcap arguments are: 't2,t3,b2,b3,trlan,trwan,brlan,brwan'");
286
287 cmd.AddValue("verbose", "Enable printing informational messages", verbose);
288
289 cmd.AddValue("duration", "Duration of simulation.", simDurationSeconds);
290
291 cmd.AddValue("udpMultiSW", "Enable udp over multi-switch links", enableUdpMultiSW);
292 cmd.AddValue("udpSingleSW", "Enable udp over single-switch links", enableUdpSingleSW);
293
294 cmd.AddValue("pcap", "Comma separated list of PCAP Locations to tap", pcapLocations);
295 cmd.AddValue("snapLen", "PCAP packet capture length", snapLen);
296
297 cmd.AddValue("csmaXRate", "CSMA X Link data rate", csmaXLinkDataRate);
298 cmd.AddValue("csmaXDelay", "CSMA X Link delay", csmaXLinkDelay);
299
300 cmd.AddValue("csmaYRate", "CSMA Y Link data rate", csmaYLinkDataRate);
301 cmd.AddValue("csmaYDelay", "CSMA Y Link delay", csmaYLinkDelay);
302
303 cmd.AddValue("p2pRate", "P2P Link data rate", p2pLinkDataRate);
304 cmd.AddValue("p2pDelay", "P2P Link delay", p2pLinkDelay);
305
306 cmd.Parse(argc, argv);
307
308 // --------------------------------------------------------------------
309 // Users may find it convenient to turn on explicit debugging
310 // for selected modules; the below lines suggest how to do this
311 // --------------------------------------------------------------------
312 if (verbose)
313 {
314 LogComponentEnable("GlobalRoutingMultiSwitchPlusRouter", LOG_LEVEL_INFO);
315 }
316
317 // ======================================================================
318 // Define the list of valid PCAP taps
319 // ----------------------------------------------------------------------
320 const std::vector<std::string> pcapTaps{
321 "t2", // multi-switch UDP echo client
322 "t3", // single-switch UDP echo server
323 "b2", // multi-switch UDP echo server
324 "b3", // single-switch UDP echo client
325 "trlan", // top router LAN side
326 "trwan", // top router WAN side
327 "brlan", // bottom router LAN side
328 "brwan", // bottom router WAN side
329 };
330
331 // ----------------------------------------------------------------------
332 // Parse the pcapLocations string into pcapLocationVec
333 // ----------------------------------------------------------------------
334 std::vector<std::string> pcapLocationVec;
335 if (!pcapLocations.empty())
336 {
337 std::stringstream sStream(pcapLocations);
338
339 while (sStream.good())
340 {
341 std::string substr;
342 getline(sStream, substr, ',');
343 if (vssearch(substr, pcapTaps))
344 {
345 pcapLocationVec.push_back(substr);
346 }
347 else
348 {
349 NS_LOG_ERROR("WARNING: Unrecognized PCAP location: <" + substr + ">");
350 }
351 }
352
353 for (auto ploc = pcapLocationVec.begin(); ploc != pcapLocationVec.end(); ++ploc)
354 {
355 NS_LOG_INFO("PCAP capture at: <" + *ploc + ">");
356 }
357 }
358
359 // ======================================================================
360 // Set some simulator-wide values
361 // ======================================================================
362
363 // ----------------------------------------------------------------------
364 // Set PCAP packet capture maximum packet length
365 // ----------------------------------------------------------------------
366 if (snapLen != PcapFile::SNAPLEN_DEFAULT)
367 {
368 Config::SetDefault("ns3::PcapFileWrapper::CaptureSize", UintegerValue(snapLen));
369 }
370
371 // ======================================================================
372 // Create the nodes & links required for the topology shown in comments above.
373 // ----------------------------------------------------------------------
374 NS_LOG_INFO("INFO: Create nodes."); // - - - - - - - - - - - - - - - -
375 // Node IP : Description
376 // - - - - - - - - - - - - - - - -
377 Ptr<Node> t2 = CreateObject<Node>(); // 192.168.1.2 : Top multi-switch udp echo client
378 Ptr<Node> t3 = CreateObject<Node>(); // 192.168.1.3 : Top single-switch udp echo server
379 // :
380 Ptr<Node> ts1 = CreateObject<Node>(); // <no IP> : Top switch #1 (bridge)
381 Ptr<Node> ts2 = CreateObject<Node>(); // <no IP> : Top switch #2 (bridge)
382 Ptr<Node> ts3 = CreateObject<Node>(); // <no IP> : Top switch #3 (bridge)
383 Ptr<Node> ts4 = CreateObject<Node>(); // <no IP> : Top switch #4 (bridge)
384 // :
385 Ptr<Node> tr = CreateObject<Node>(); // 192.168.1.1 : Router connecting top LAN & WAN
386 // 76.1.1.1 :
387 // :
388 Ptr<Node> br = CreateObject<Node>(); // 76.1.1.2 : Router connecting WAN & bottom LANs
389 // 192.168.2.1 :
390 // :
391 Ptr<Node> bs1 = CreateObject<Node>(); // <no IP> : Bottom switch #1 (bridge)
392 Ptr<Node> bs2 = CreateObject<Node>(); // <no IP> : Bottom switch #2 (bridge)
393 Ptr<Node> bs3 = CreateObject<Node>(); // <no IP> : Bottom switch #3 (bridge)
394 Ptr<Node> bs4 = CreateObject<Node>(); // <no IP> : Bottom switch #4 (bridge)
395 Ptr<Node> bs5 = CreateObject<Node>(); // <no IP> : Bottom switch #5 (bridge)
396 // :
397 Ptr<Node> b2 = CreateObject<Node>(); // 192.168.2.2 : Bottom multi-switch udp echo server
398
399 Ptr<Node> b3 = CreateObject<Node>(); // 192.168.2.3 : Bottom single-switch udp echo client
400 // - - - - - - - - - - - - - - - -
401
402 // ----------------------------------------------------------------------
403 // Give the nodes names
404 // ----------------------------------------------------------------------
405 Names::Add("t2", t2);
406 Names::Add("t3", t3);
407 Names::Add("ts1", ts1);
408 Names::Add("ts2", ts2);
409 Names::Add("ts3", ts3);
410 Names::Add("ts4", ts4);
411 Names::Add("tr", tr);
412 Names::Add("br", br);
413 Names::Add("bs1", bs1);
414 Names::Add("bs2", bs2);
415 Names::Add("bs3", bs3);
416 Names::Add("bs4", bs4);
417 Names::Add("bs5", bs5);
418 Names::Add("b2", b2);
419 Names::Add("b3", b3);
420
421 // ======================================================================
422 // Create CSMA links to use for connecting LAN nodes together
423 // ----------------------------------------------------------------------
424
425 // ----------------------------------------
426 // CSMA [X]
427 // ----------------------------------------
428 NS_LOG_INFO("L2: Create a " << csmaXLinkDataRate << " " << csmaXLinkDelay
429 << " CSMA link for csmaX for LANs.");
430 CsmaHelper csmaX;
431 csmaX.SetChannelAttribute("DataRate", StringValue(csmaXLinkDataRate));
432 csmaX.SetChannelAttribute("Delay", StringValue(csmaXLinkDelay));
433
434 // ----------------------------------------
435 // CSMA [Y]
436 // ----------------------------------------
437 NS_LOG_INFO("L2: Create a " << csmaYLinkDataRate << " " << csmaYLinkDelay
438 << " CSMA link for csmaY for LANs.");
439 CsmaHelper csmaY;
440 csmaY.SetChannelAttribute("DataRate", StringValue(csmaYLinkDataRate));
441 csmaY.SetChannelAttribute("Delay", StringValue(csmaYLinkDelay));
442
443 // ----------------------------------------------------------------------
444 // Now, connect the top LAN nodes together with csma links.
445 // ----------------------------------------------------------------------
446 NS_LOG_INFO("L2: Connect nodes on top LAN together with half-duplex CSMA links.");
447
448 // Multi-switch top LAN chain: t2-ts4-ts3-ts2-ts1-tr
449 NetDeviceContainer link_t2_ts4 = csmaX.Install(NodeContainer(t2, ts4));
450 NetDeviceContainer link_ts4_ts3 = csmaY.Install(NodeContainer(ts4, ts3));
451 NetDeviceContainer link_ts3_ts2 = csmaX.Install(NodeContainer(ts3, ts2));
452 NetDeviceContainer link_ts2_ts1 = csmaY.Install(NodeContainer(ts2, ts1));
453
454 // Single-switch top LAN link: t3-ts1-tr
455 NetDeviceContainer link_t3_ts1 = csmaX.Install(NodeContainer(t3, ts1));
456
457 // Common link for top LAN between ts1 and tr (for t2 and t3 to get to tr)
458 NetDeviceContainer link_tr_ts1 = csmaY.Install(NodeContainer(tr, ts1));
459
460 // ----------------------------------------------------------------------
461 // And repeat above steps to connect the bottom LAN nodes together
462 // ----------------------------------------------------------------------
463 NS_LOG_INFO("L2: Connect nodes on bottom LAN together with half-duplex CSMA links.");
464
465 // Multi-switch bottom LAN chain: b2-bs5-bs4-bs3-bs2-bs1-br
466 NetDeviceContainer link_b2_bs5 = csmaY.Install(NodeContainer(b2, bs5));
467 NetDeviceContainer link_bs5_bs4 = csmaX.Install(NodeContainer(bs5, bs4));
468 NetDeviceContainer link_bs4_bs3 = csmaY.Install(NodeContainer(bs4, bs3));
469 NetDeviceContainer link_bs3_bs2 = csmaX.Install(NodeContainer(bs3, bs2));
470 NetDeviceContainer link_bs2_bs1 = csmaY.Install(NodeContainer(bs2, bs1));
471
472 // Single-switch bottom LAN link: b3-bs1-br
473 NetDeviceContainer link_b3_bs1 = csmaY.Install(NodeContainer(b3, bs1));
474
475 // Common link for bottom LAN between bs1 and br (for b2 and b3 to get to br)
476 NetDeviceContainer link_br_bs1 = csmaX.Install(NodeContainer(br, bs1));
477
478 // ======================================================================
479 // Create a point-to-point link for connecting WAN nodes together
480 // (this type of link is full-duplex)
481 // ----------------------------------------------------------------------
482 NS_LOG_INFO("L2: Create a " << p2pLinkDataRate << " " << p2pLinkDelay
483 << " Point-to-Point link for the WAN.");
484
486 p2p.SetDeviceAttribute("DataRate", StringValue(p2pLinkDataRate));
487 p2p.SetChannelAttribute("Delay", StringValue(p2pLinkDelay));
488
489 // ----------------------------------------------------------------------
490 // Now, connect top router to bottom router with a p2p WAN link
491 // ----------------------------------------------------------------------
492 NS_LOG_INFO("L2: Connect the routers together with the Point-to-Point WAN link.");
493
494 NetDeviceContainer link_tr_br;
495 link_tr_br = p2p.Install(NodeContainer(tr, br));
496
497 // ======================================================================
498 // Manually create the list of NetDevices for each switch
499 // ----------------------------------------------------------------------
500
501 // Top Switch 4 NetDevices
502 NetDeviceContainer ts4nd;
503 ts4nd.Add(link_t2_ts4.Get(1));
504 ts4nd.Add(link_ts4_ts3.Get(0));
505
506 // Top Switch 3 NetDevices
507 NetDeviceContainer ts3nd;
508 ts3nd.Add(link_ts4_ts3.Get(1));
509 ts3nd.Add(link_ts3_ts2.Get(0));
510
511 // Top Switch 2 NetDevices
512 NetDeviceContainer ts2nd;
513 ts2nd.Add(link_ts3_ts2.Get(1));
514 ts2nd.Add(link_ts2_ts1.Get(0));
515
516 // Top Switch 1 NetDevices
517 NetDeviceContainer ts1nd;
518 ts1nd.Add(link_ts2_ts1.Get(1));
519 ts1nd.Add(link_t3_ts1.Get(1));
520 ts1nd.Add(link_tr_ts1.Get(1));
521
522 // Bottom Switch 1 NetDevices
523 NetDeviceContainer bs1nd;
524 bs1nd.Add(link_br_bs1.Get(1));
525 bs1nd.Add(link_bs2_bs1.Get(1));
526 bs1nd.Add(link_b3_bs1.Get(1));
527
528 // Bottom Switch 2 NetDevices
529 NetDeviceContainer bs2nd;
530 bs2nd.Add(link_bs2_bs1.Get(0));
531 bs2nd.Add(link_bs3_bs2.Get(1));
532
533 // Bottom Switch 3 NetDevices
534 NetDeviceContainer bs3nd;
535 bs3nd.Add(link_bs3_bs2.Get(0));
536 bs3nd.Add(link_bs4_bs3.Get(1));
537
538 // Bottom Switch 4 NetDevices
539 NetDeviceContainer bs4nd;
540 bs4nd.Add(link_bs4_bs3.Get(0));
541 bs4nd.Add(link_bs5_bs4.Get(1));
542
543 // Bottom Switch 5 NetDevices
544 NetDeviceContainer bs5nd;
545 bs5nd.Add(link_bs5_bs4.Get(0));
546 bs5nd.Add(link_b2_bs5.Get(1));
547
548 // ======================================================================
549 // Install bridging code on each switch
550 // ----------------------------------------------------------------------
551 BridgeHelper bridge;
552
553 bridge.Install(ts1, ts1nd);
554 bridge.Install(ts2, ts2nd);
555 bridge.Install(ts3, ts3nd);
556 bridge.Install(ts4, ts4nd);
557
558 bridge.Install(bs1, bs1nd);
559 bridge.Install(bs2, bs2nd);
560 bridge.Install(bs3, bs3nd);
561 bridge.Install(bs4, bs4nd);
562 bridge.Install(bs5, bs5nd);
563
564 // ======================================================================
565 // Install the L3 internet stack (TCP/IP)
566 // ----------------------------------------------------------------------
567 InternetStackHelper ns3IpStack;
568
569 // ----------------------------------------------------------------------
570 // Install the L3 internet stack on UDP endpoints
571 // ----------------------------------------------------------------------
572 NS_LOG_INFO("L3: Install the ns3 IP stack on udp client and server nodes.");
573 NodeContainer endpointNodes(t2, t3, b2, b3);
574 ns3IpStack.Install(endpointNodes);
575
576 // ----------------------------------------------------------------------
577 // Install the L3 internet stack on routers.
578 // ----------------------------------------------------------------------
579 NS_LOG_INFO("L3: Install the ns3 IP stack on routers.");
580 NodeContainer routerNodes(tr, br);
581 ns3IpStack.Install(routerNodes);
582
583 // ======================================================================
584 // Assign top LAN IP addresses
585 // ----------------------------------------------------------------------
586 NS_LOG_INFO("L3: Assign top LAN IP Addresses.");
587
588 NetDeviceContainer topLanIpDevices; // - - - - - -- - - - - - -
589 topLanIpDevices.Add(link_tr_ts1.Get(0)); // NOTE: order matters here
590 topLanIpDevices.Add(link_t2_ts4.Get(0)); // for IP address
591 topLanIpDevices.Add(link_t3_ts1.Get(0)); // assignment
592 // - - - - - -- - - - - - -
594 ipv4.SetBase("192.168.1.0", "255.255.255.0");
595 ipv4.Assign(topLanIpDevices);
596
597 // ----------------------------------------------------------------------
598 // Assign bottom LAN IP addresses
599 // ----------------------------------------------------------------------
600 NS_LOG_INFO("L3: Assign bottom LAN IP Addresses.");
601
602 NetDeviceContainer botLanIpDevices; // - - - - - -- - - - - - -
603 botLanIpDevices.Add(link_br_bs1.Get(0)); // NOTE: order matters here
604 botLanIpDevices.Add(link_b2_bs5.Get(0)); // for IP address
605 botLanIpDevices.Add(link_b3_bs1.Get(0)); // assignment
606 // - - - - - -- - - - - - -
607
608 ipv4.SetBase("192.168.2.0", "255.255.255.0");
609 ipv4.Assign(botLanIpDevices);
610
611 // ----------------------------------------------------------------------
612 // Assign WAN IP addresses
613 // ----------------------------------------------------------------------
614 NS_LOG_INFO("L3: Assign WAN IP Addresses.");
615
616 ipv4.SetBase("76.1.1.0", "255.255.255.0");
617 ipv4.Assign(link_tr_br);
618
619 // ======================================================================
620 // Calculate and populate routing tables
621 // ----------------------------------------------------------------------
622 NS_LOG_INFO("L3: Populate routing tables.");
624
625 // ======================================================================
626 // Multi-Switch UDP traffic generation
627 // ----------------------------------------------------------------------
629
630 if (enableUdpMultiSW)
631 {
632 // ------------------------------------------------------------------
633 // Install multi-switch UDP echo server on b2
634 // ------------------------------------------------------------------
635 NS_LOG_INFO("APP: Multi-Switch UDP server (on node b2 of bottom LAN)");
636
637 UdpEchoServerHelper server(udpEchoPort);
638
639 ApplicationContainer serverApp = server.Install(b2);
640 serverApp.Start(Seconds(0.5));
641 serverApp.Stop(Seconds(simDurationSeconds));
642
643 // ------------------------------------------------------------------
644 // Install multi-switch UDP echo client on t2
645 // ------------------------------------------------------------------
646 NS_LOG_INFO("APP: Multi-Switch UDP client (on node t2 of top LAN)");
647
648 Time interPacketInterval = Seconds(0.005);
649 uint32_t packetSize = 1000;
650 uint32_t maxPacketCount = (simDurationSeconds - 2.0) / 0.005;
651
652 UdpEchoClientHelper client(Ipv4Address("192.168.2.2"), udpEchoPort);
653
654 client.SetAttribute("MaxPackets", UintegerValue(maxPacketCount));
655 client.SetAttribute("Interval", TimeValue(interPacketInterval));
656 client.SetAttribute("PacketSize", UintegerValue(packetSize));
657
658 ApplicationContainer clientApp = client.Install(t2);
659 clientApp.Start(Seconds(0.5));
660 clientApp.Stop(Seconds(simDurationSeconds));
661 }
662
663 // ======================================================================
664 // Single-Switch UDP traffic generation
665 // ----------------------------------------------------------------------
666 if (enableUdpSingleSW)
667 {
668 // ------------------------------------------------------------------
669 // Install single-switch UDP echo server on t3
670 // ------------------------------------------------------------------
671 NS_LOG_INFO("APP: Single-Switch UDP server (on node t3 of top LAN)");
672
673 UdpEchoServerHelper server(udpEchoPort);
674
675 ApplicationContainer serverApp = server.Install(t3);
676 serverApp.Start(Seconds(0.5));
677 serverApp.Stop(Seconds(simDurationSeconds));
678
679 // ------------------------------------------------------------------
680 // Install single-switch UDP echo client on b3
681 // ------------------------------------------------------------------
682 NS_LOG_INFO("APP: Single-Switch UDP client (on node b3 bottom LAN)");
683
684 Time interPacketInterval = Seconds(0.005);
685 uint32_t packetSize = 1000;
686 uint32_t maxPacketCount = (simDurationSeconds - 2.0) / 0.005;
687
688 UdpEchoClientHelper client(Ipv4Address("192.168.1.3"), udpEchoPort);
689
690 client.SetAttribute("MaxPackets", UintegerValue(maxPacketCount));
691 client.SetAttribute("Interval", TimeValue(interPacketInterval));
692 client.SetAttribute("PacketSize", UintegerValue(packetSize));
693
694 ApplicationContainer clientApp = client.Install(b3);
695 clientApp.Start(Seconds(0.5));
696 clientApp.Stop(Seconds(simDurationSeconds));
697 }
698
699 // ======================================================================
700 // Print routing tables at T=0.1
701 // - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
702 // NOTE: Node 0 and Node 13 must have non-empty tables (except for local
703 // loopback and local LAN) if routing is operating correctly.
704 // ----------------------------------------------------------------------
705 NS_LOG_INFO("Set up to print routing tables at T=0.1s");
706
707 Ptr<OutputStreamWrapper> routingStream =
708 Create<OutputStreamWrapper>("global-routing-multi-switch-plus-router.routes",
709 std::ios::out);
710
712
713 // ======================================================================
714 // Configure PCAP traces
715 // ----------------------------------------------------------------------
716 NS_LOG_INFO("Configure PCAP Tracing (if any configured).");
717
718 // - - - - - - - - - - - - - -
719 // multi-switch UDP echo client
720 // - - - - - - - - - - - - - -
721 if (vssearch("t2", pcapLocationVec))
722 {
723 csmaX.EnablePcap("t2.pcap", topLanIpDevices.Get(1), true, true);
724 }
725
726 // - - - - - - - - - - - - - -
727 // multi-switch UDP echo server
728 // - - - - - - - - - - - - - -
729 if (vssearch("b2", pcapLocationVec))
730 {
731 csmaY.EnablePcap("b2.pcap", botLanIpDevices.Get(1), true, true);
732 }
733
734 // - - - - - - - - - - - - - -
735 // single-switch UDP echo client
736 // - - - - - - - - - - - - - -
737 if (vssearch("b3", pcapLocationVec))
738 {
739 csmaY.EnablePcap("b3.pcap", botLanIpDevices.Get(2), true, true);
740 }
741
742 // - - - - - - - - - - - - - -
743 // single-switch UDP echo server
744 // - - - - - - - - - - - - - -
745 if (vssearch("t3", pcapLocationVec))
746 {
747 csmaX.EnablePcap("t3.pcap", topLanIpDevices.Get(2), true, true);
748 }
749
750 // - - - - - - - - - - - - - -
751 // top router, LAN side
752 // - - - - - - - - - - - - - -
753 if (vssearch("trlan", pcapLocationVec))
754 {
755 csmaY.EnablePcap("trlan.pcap", topLanIpDevices.Get(0), true, true);
756 }
757
758 // - - - - - - - - - - - - - -
759 // bottom router, LAN side
760 // - - - - - - - - - - - - - -
761 if (vssearch("brlan", pcapLocationVec))
762 {
763 csmaX.EnablePcap("brlan.pcap", botLanIpDevices.Get(0), true, true);
764 }
765
766 // - - - - - - - - - - - - - -
767 // top router, WAN side
768 // - - - - - - - - - - - - - -
769 if (vssearch("trwan", pcapLocationVec))
770 {
771 p2p.EnablePcap("trwan.pcap", link_tr_br.Get(0), true, true);
772 }
773
774 // - - - - - - - - - - - - - -
775 // bottom router, WAN side
776 // - - - - - - - - - - - - - -
777 if (vssearch("brwan", pcapLocationVec))
778 {
779 p2p.EnablePcap("brwan.pcap", link_tr_br.Get(1), true, true);
780 }
781
782 // ======================================================================
783 // Now, do the actual simulation.
784 // ----------------------------------------------------------------------
785 NS_LOG_INFO("Run Simulation for " << simDurationSeconds << " seconds.");
786
787 Simulator::Stop(Seconds(simDurationSeconds));
789
791 NS_LOG_INFO("Done.");
792
793 return 0;
794}
holds a vector of ns3::Application pointers.
void Start(Time start) const
Start all of the Applications in this container at the start time given as a parameter.
void Stop(Time stop) const
Arrange for all of the Applications in this container to Stop() at the Time given as a parameter.
Add capability to bridge multiple LAN segments (IEEE 802.1D bridging)
Definition: bridge-helper.h:45
NetDeviceContainer Install(Ptr< Node > node, NetDeviceContainer c)
This method creates an ns3::BridgeNetDevice with the attributes configured by BridgeHelper::SetDevice...
Parse command-line arguments.
Definition: command-line.h:232
build a set of CsmaNetDevice objects
Definition: csma-helper.h:48
void SetChannelAttribute(std::string n1, const AttributeValue &v1)
Definition: csma-helper.cc:56
NetDeviceContainer Install(Ptr< Node > node) const
This method creates an ns3::CsmaChannel with the attributes configured by CsmaHelper::SetChannelAttri...
Definition: csma-helper.cc:226
aggregate IP/TCP/UDP functionality to existing Nodes.
void Install(std::string nodeName) const
Aggregate implementations of the ns3::Ipv4, ns3::Ipv6, ns3::Udp, and ns3::Tcp classes onto the provid...
A helper class to make life easier while doing simple IPv4 address assignment in scripts.
Ipv4 addresses are stored in host order in this class.
Definition: ipv4-address.h:42
static void PopulateRoutingTables()
Build a routing database and initialize the routing tables of the nodes in the simulation.
static void PrintRoutingTableAllAt(Time printTime, Ptr< OutputStreamWrapper > stream, Time::Unit unit=Time::S)
prints the routing tables of all nodes at a particular time.
static void Add(std::string name, Ptr< Object > object)
Add the association between the string "name" and the Ptr<Object> obj.
Definition: names.cc:775
holds a vector of ns3::NetDevice pointers
void Add(NetDeviceContainer other)
Append the contents of another NetDeviceContainer to the end of this container.
Ptr< NetDevice > Get(uint32_t i) const
Get the Ptr<NetDevice> stored in this container at a given index.
keep track of a set of node pointers.
static const uint32_t SNAPLEN_DEFAULT
Default value for maximum octets to save per packet.
Definition: pcap-file.h:46
void EnablePcap(std::string prefix, Ptr< NetDevice > nd, bool promiscuous=false, bool explicitFilename=false)
Enable pcap output the indicated net device.
Build a set of PointToPointNetDevice objects.
Smart pointer class similar to boost::intrusive_ptr.
Definition: ptr.h:77
static void Destroy()
Execute the events scheduled with ScheduleDestroy().
Definition: simulator.cc:142
static void Run()
Run the simulation.
Definition: simulator.cc:178
static void Stop()
Tell the Simulator the calling event should be the last one executed.
Definition: simulator.cc:186
Hold variables of type string.
Definition: string.h:56
Simulation virtual time values and global simulation resolution.
Definition: nstime.h:105
AttributeValue implementation for Time.
Definition: nstime.h:1406
Create an application which sends a UDP packet and waits for an echo of this packet.
Create a server application which waits for input UDP packets and sends them back to the original sen...
Hold an unsigned integer type.
Definition: uinteger.h:45
#define vssearch(loc, vec)
void SetDefault(std::string name, const AttributeValue &value)
Definition: config.cc:894
#define NS_LOG_ERROR(msg)
Use NS_LOG to output a message of level LOG_ERROR.
Definition: log.h:254
#define NS_LOG_COMPONENT_DEFINE(name)
Define a Log component with a specific name.
Definition: log.h:202
#define NS_LOG_INFO(msg)
Use NS_LOG to output a message of level LOG_INFO.
Definition: log.h:275
Time Seconds(double value)
Construct a Time in the indicated unit.
Definition: nstime.h:1319
Every class exported by the ns3 library is enclosed in the ns3 namespace.
void LogComponentEnable(const std::string &name, LogLevel level)
Enable the logging output associated with that log component.
Definition: log.cc:302
@ LOG_LEVEL_INFO
LOG_INFO and above.
Definition: log.h:104
bool verbose
static const uint32_t packetSize
Packet size generated at the AP.