A Discrete-Event Network Simulator
API
csma-system-test-suite.cc
Go to the documentation of this file.
1 /* -*- Mode:C++; c-file-style:"gnu"; indent-tabs-mode:nil; -*- */
2 /*
3  * This program is free software; you can redistribute it and/or modify
4  * it under the terms of the GNU General Public License version 2 as
5  * published by the Free Software Foundation;
6  *
7  * This program is distributed in the hope that it will be useful,
8  * but WITHOUT ANY WARRANTY; without even the implied warranty of
9  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
10  * GNU General Public License for more details.
11  *
12  * You should have received a copy of the GNU General Public License
13  * along with this program; if not, write to the Free Software
14  * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
15  */
16 
17 // This is not a test of CsmaNetDevice model behavior per-se, but
18 // instead is a roll up of several end-to-end examples in examples/csma
19 // directory, converted into system tests. Writing a test suite
20 // to test Csma itself is for further study.
21 
22 #include <string>
23 
24 #include "ns3/address.h"
25 #include "ns3/application-container.h"
26 #include "ns3/bridge-helper.h"
27 #include "ns3/callback.h"
28 #include "ns3/config.h"
29 #include "ns3/csma-helper.h"
30 #include "ns3/csma-star-helper.h"
31 #include "ns3/inet-socket-address.h"
32 #include "ns3/internet-stack-helper.h"
33 #include "ns3/ipv4-address-helper.h"
34 #include "ns3/ipv4-global-routing-helper.h"
35 #include "ns3/ipv4-static-routing-helper.h"
36 #include "ns3/node.h"
37 #include "ns3/data-rate.h"
38 #include "ns3/node-container.h"
39 #include "ns3/on-off-helper.h"
40 #include "ns3/packet.h"
41 #include "ns3/packet-sink-helper.h"
42 #include "ns3/packet-socket-helper.h"
43 #include "ns3/packet-socket-address.h"
44 #include "ns3/pointer.h"
45 #include "ns3/simple-channel.h"
46 #include "ns3/simulator.h"
47 #include "ns3/string.h"
48 #include "ns3/test.h"
49 #include "ns3/uinteger.h"
50 #include "ns3/v4ping-helper.h"
51 
52 using namespace ns3;
53 
55 {
56 public:
58  virtual ~CsmaBridgeTestCase ();
59 
60 private:
61  virtual void DoRun (void);
62  void SinkRx (Ptr<const Packet> p, const Address &ad);
63  uint32_t m_count;
64 };
65 
66 // Add some help text to this case to describe what it is intended to test
68  : TestCase ("Bridge example for Carrier Sense Multiple Access (CSMA) networks"), m_count (0)
69 {
70 }
71 
73 {
74 }
75 
76 void
78 {
79  m_count++;
80 }
81 
82 // Network topology
83 //
84 // n0 n1
85 // | |
86 // ----------
87 // | Switch |
88 // ----------
89 // | |
90 // n2 n3
91 //
92 // - CBR/UDP test flow from n0 to n1; test that packets received on n1
93 //
94 void
96 {
97  NodeContainer terminals;
98  terminals.Create (4);
99 
100  NodeContainer csmaSwitch;
101  csmaSwitch.Create (1);
102 
104  csma.SetChannelAttribute ("DataRate", DataRateValue (5000000));
105  csma.SetChannelAttribute ("Delay", TimeValue (MilliSeconds (2)));
106 
107  NetDeviceContainer terminalDevices;
108  NetDeviceContainer switchDevices;
109 
110  for (int i = 0; i < 4; i++)
111  {
112  NetDeviceContainer link = csma.Install (NodeContainer (terminals.Get (i), csmaSwitch));
113  terminalDevices.Add (link.Get (0));
114  switchDevices.Add (link.Get (1));
115  }
116 
117  // Create the bridge netdevice, which will do the packet switching
118  Ptr<Node> switchNode = csmaSwitch.Get (0);
119  BridgeHelper bridge;
120  bridge.Install (switchNode, switchDevices);
121 
122  InternetStackHelper internet;
123  internet.Install (terminals);
124 
125  Ipv4AddressHelper ipv4;
126  ipv4.SetBase ("10.1.1.0", "255.255.255.0");
127  ipv4.Assign (terminalDevices);
128 
129  uint16_t port = 9; // Discard port (RFC 863)
130 
131  // Create the OnOff application to send UDP datagrams from n0 to n1.
132  //
133  // Make packets be sent about every DefaultPacketSize / DataRate =
134  // 4096 bits / (5000 bits/second) = 0.82 second.
135  OnOffHelper onoff ("ns3::UdpSocketFactory",
136  Address (InetSocketAddress (Ipv4Address ("10.1.1.2"), port)));
137  onoff.SetConstantRate (DataRate (5000));
138 
139  ApplicationContainer app = onoff.Install (terminals.Get (0));
140  app.Start (Seconds (1.0));
141  app.Stop (Seconds (10.0));
142 
143  PacketSinkHelper sink ("ns3::UdpSocketFactory",
144  Address (InetSocketAddress (Ipv4Address::GetAny (), port)));
145  app = sink.Install (terminals.Get (1));
146  app.Start (Seconds (0.0));
147 
148  // Trace receptions
149  Config::ConnectWithoutContext ("/NodeList/1/ApplicationList/0/$ns3::PacketSink/Rx", MakeCallback (&CsmaBridgeTestCase::SinkRx, this));
150 
151  Simulator::Run ();
152  Simulator::Destroy ();
153 
154  // We should have sent and received 10 packets
155  NS_TEST_ASSERT_MSG_EQ (m_count, 10, "Bridge should have passed 10 packets");
156 }
157 
159 {
160 public:
162  virtual ~CsmaBroadcastTestCase ();
163 
164 private:
165  virtual void DoRun (void);
166  void SinkRxNode1 (Ptr<const Packet> p, const Address &ad);
167  void SinkRxNode2 (Ptr<const Packet> p, const Address &ad);
168  void DropEvent (Ptr<const Packet> p);
169  uint32_t m_countNode1;
170  uint32_t m_countNode2;
171  uint32_t m_drops;
172 };
173 
174 // Add some help text to this case to describe what it is intended to test
176  : TestCase ("Broadcast example for Carrier Sense Multiple Access (CSMA) networks"), m_countNode1 (0), m_countNode2 (0), m_drops (0)
177 {
178 }
179 
181 {
182 }
183 
184 void
186 {
187  m_countNode1++;
188 }
189 
190 void
192 {
193  m_countNode2++;
194 }
195 
196 void
198 {
199  m_drops++;
200 }
201 
202 //
203 // Example of the sending of a datagram to a broadcast address
204 //
205 // Network topology
206 // ==============
207 // | |
208 // n0 n1 n2
209 // | |
210 // ==========
211 //
212 // n0 originates UDP broadcast to 255.255.255.255/discard port, which
213 // is replicated and received on both n1 and n2
214 //
215 void
217 {
218  NodeContainer c;
219  c.Create (3);
220  NodeContainer c0 = NodeContainer (c.Get (0), c.Get (1));
221  NodeContainer c1 = NodeContainer (c.Get (0), c.Get (2));
222 
224  csma.SetChannelAttribute ("DataRate", DataRateValue (DataRate (5000000)));
225  csma.SetChannelAttribute ("Delay", TimeValue (MilliSeconds (2)));
226 
227  NetDeviceContainer n0 = csma.Install (c0);
228  NetDeviceContainer n1 = csma.Install (c1);
229 
230  InternetStackHelper internet;
231  internet.Install (c);
232 
233  Ipv4AddressHelper ipv4;
234  ipv4.SetBase ("10.1.0.0", "255.255.255.0");
235  ipv4.Assign (n0);
236  ipv4.SetBase ("192.168.1.0", "255.255.255.0");
237  ipv4.Assign (n1);
238 
239 
240  // RFC 863 discard port ("9") indicates packet should be thrown away
241  // by the system. We allow this silent discard to be overridden
242  // by the PacketSink application.
243  uint16_t port = 9;
244 
245  // Create the OnOff application to send UDP datagrams from n0.
246  //
247  // Make packets be sent about every DefaultPacketSize / DataRate =
248  // 4096 bits / (5000 bits/second) = 0.82 second.
249  OnOffHelper onoff ("ns3::UdpSocketFactory",
250  Address (InetSocketAddress (Ipv4Address ("255.255.255.255"), port)));
251  onoff.SetConstantRate (DataRate (5000));
252 
253  ApplicationContainer app = onoff.Install (c0.Get (0));
254  // Start the application
255  app.Start (Seconds (1.0));
256  app.Stop (Seconds (10.0));
257 
258  // Create an optional packet sink to receive these packets
259  PacketSinkHelper sink ("ns3::UdpSocketFactory",
260  Address (InetSocketAddress (Ipv4Address::GetAny (), port)));
261  app = sink.Install (c0.Get (1));
262  app.Add (sink.Install (c1.Get (1)));
263  app.Start (Seconds (1.0));
264  app.Stop (Seconds (10.0));
265 
266  // Trace receptions
267  Config::ConnectWithoutContext ("/NodeList/1/ApplicationList/0/$ns3::PacketSink/Rx", MakeCallback (&CsmaBroadcastTestCase::SinkRxNode1, this));
268  Config::ConnectWithoutContext ("/NodeList/2/ApplicationList/0/$ns3::PacketSink/Rx", MakeCallback (&CsmaBroadcastTestCase::SinkRxNode2, this));
269 
270  Simulator::Run ();
271  Simulator::Destroy ();
272 
273  // We should have sent and received 10 packets
274  NS_TEST_ASSERT_MSG_EQ (m_countNode1, 10, "Node 1 should have received 10 packets");
275  NS_TEST_ASSERT_MSG_EQ (m_countNode2, 10, "Node 2 should have received 10 packets");
276 }
277 
279 {
280 public:
282  virtual ~CsmaMulticastTestCase ();
283 
284 private:
285  virtual void DoRun (void);
286  void SinkRx (Ptr<const Packet> p, const Address &ad);
287  void DropEvent (Ptr<const Packet> p);
288  uint32_t m_count;
289  uint32_t m_drops;
290 };
291 
292 // Add some help text to this case to describe what it is intended to test
294  : TestCase ("Multicast example for Carrier Sense Multiple Access (CSMA) networks"), m_count (0), m_drops (0)
295 {
296 }
297 
299 {
300 }
301 
302 void
304 {
305  m_count++;
306 }
307 
308 void
310 {
311  m_drops++;
312 }
313 
314 // Network topology
315 //
316 // Lan1
317 // ===========
318 // | | |
319 // n0 n1 n2 n3 n4
320 // | | |
321 // ===========
322 // Lan0
323 //
324 // - Multicast source is at node n0;
325 // - Multicast forwarded by node n2 onto LAN1;
326 // - Nodes n0, n1, n2, n3, and n4 receive the multicast frame.
327 // - Node n4 listens for the data
328 //
329 void
331 {
332  //
333  // Set up default values for the simulation.
334  //
335  // Select DIX/Ethernet II-style encapsulation (no LLC/Snap header)
336  Config::SetDefault ("ns3::CsmaNetDevice::EncapsulationMode", StringValue ("Dix"));
337 
338  NodeContainer c;
339  c.Create (5);
340  // We will later want two subcontainers of these nodes, for the two LANs
341  NodeContainer c0 = NodeContainer (c.Get (0), c.Get (1), c.Get (2));
342  NodeContainer c1 = NodeContainer (c.Get (2), c.Get (3), c.Get (4));
343 
345  csma.SetChannelAttribute ("DataRate", DataRateValue (DataRate (5000000)));
346  csma.SetChannelAttribute ("Delay", TimeValue (MilliSeconds (2)));
347 
348  // We will use these NetDevice containers later, for IP addressing
349  NetDeviceContainer nd0 = csma.Install (c0); // First LAN
350  NetDeviceContainer nd1 = csma.Install (c1); // Second LAN
351 
352  InternetStackHelper internet;
353  internet.Install (c);
354 
355  Ipv4AddressHelper ipv4Addr;
356  ipv4Addr.SetBase ("10.1.1.0", "255.255.255.0");
357  ipv4Addr.Assign (nd0);
358  ipv4Addr.SetBase ("10.1.2.0", "255.255.255.0");
359  ipv4Addr.Assign (nd1);
360 
361  //
362  // Now we can configure multicasting. As described above, the multicast
363  // source is at node zero, which we assigned the IP address of 10.1.1.1
364  // earlier. We need to define a multicast group to send packets to. This
365  // can be any multicast address from 224.0.0.0 through 239.255.255.255
366  // (avoiding the reserved routing protocol addresses).
367  //
368 
369  Ipv4Address multicastSource ("10.1.1.1");
370  Ipv4Address multicastGroup ("225.1.2.4");
371 
372  // Now, we will set up multicast routing. We need to do three things:
373  // 1) Configure a (static) multicast route on node n2
374  // 2) Set up a default multicast route on the sender n0
375  // 3) Have node n4 join the multicast group
376  // We have a helper that can help us with static multicast
377  Ipv4StaticRoutingHelper multicast;
378 
379  // 1) Configure a (static) multicast route on node n2 (multicastRouter)
380  Ptr<Node> multicastRouter = c.Get (2); // The node in question
381  Ptr<NetDevice> inputIf = nd0.Get (2); // The input NetDevice
382  NetDeviceContainer outputDevices; // A container of output NetDevices
383  outputDevices.Add (nd1.Get (0)); // (we only need one NetDevice here)
384 
385  multicast.AddMulticastRoute (multicastRouter, multicastSource,
386  multicastGroup, inputIf, outputDevices);
387 
388  // 2) Set up a default multicast route on the sender n0
389  Ptr<Node> sender = c.Get (0);
390  Ptr<NetDevice> senderIf = nd0.Get (0);
391  multicast.SetDefaultMulticastRoute (sender, senderIf);
392 
393  //
394  // Create an OnOff application to send UDP datagrams from node zero to the
395  // multicast group (node four will be listening).
396  //
397 
398  uint16_t multicastPort = 9; // Discard port (RFC 863)
399 
400  // Configure a multicast packet generator.
401  //
402  // Make packets be sent about every defaultPacketSize / dataRate =
403  // 4096 bits / (5000 bits/second) = 0.82 second.
404  OnOffHelper onoff ("ns3::UdpSocketFactory",
405  Address (InetSocketAddress (multicastGroup, multicastPort)));
406  onoff.SetConstantRate (DataRate (5000));
407 
408  ApplicationContainer srcC = onoff.Install (c0.Get (0));
409 
410  //
411  // Tell the application when to start and stop.
412  //
413  srcC.Start (Seconds (1.));
414  srcC.Stop (Seconds (10.));
415 
416  // Create an optional packet sink to receive these packets
417  PacketSinkHelper sink ("ns3::UdpSocketFactory",
418  InetSocketAddress (Ipv4Address::GetAny (), multicastPort));
419 
420  ApplicationContainer sinkC = sink.Install (c1.Get (2)); // Node n4
421  // Start the sink
422  sinkC.Start (Seconds (1.0));
423  sinkC.Stop (Seconds (10.0));
424 
425  // Trace receptions
426  Config::ConnectWithoutContext ("/NodeList/4/ApplicationList/0/$ns3::PacketSink/Rx", MakeCallback (&CsmaMulticastTestCase::SinkRx, this));
427 
428  //
429  // Now, do the actual simulation.
430  //
431  Simulator::Run ();
432  Simulator::Destroy ();
433 
434  // We should have sent and received 10 packets
435  NS_TEST_ASSERT_MSG_EQ (m_count, 10, "Node 4 should have received 10 packets");
436 }
437 
439 {
440 public:
442  virtual ~CsmaOneSubnetTestCase ();
443 
444 private:
445  virtual void DoRun (void);
446  void SinkRxNode0 (Ptr<const Packet> p, const Address &ad);
447  void SinkRxNode1 (Ptr<const Packet> p, const Address &ad);
448  void DropEvent (Ptr<const Packet> p);
449  uint32_t m_countNode0;
450  uint32_t m_countNode1;
451  uint32_t m_drops;
452 };
453 
454 // Add some help text to this case to describe what it is intended to test
456  : TestCase ("One subnet example for Carrier Sense Multiple Access (CSMA) networks"), m_countNode0 (0), m_countNode1 (0), m_drops (0)
457 {
458 }
459 
461 {
462 }
463 
464 void
466 {
467  m_countNode0++;
468 }
469 
470 void
472 {
473  m_countNode1++;
474 }
475 
476 void
478 {
479  m_drops++;
480 }
481 
482 // Network topology
483 //
484 // n0 n1 n2 n3
485 // | | | |
486 // =================
487 // LAN
488 //
489 // - CBR/UDP flows from n0 to n1 and from n3 to n0
490 // - DropTail queues
491 //
492 void
494 {
496  nodes.Create (4);
497 
499  csma.SetChannelAttribute ("DataRate", DataRateValue (5000000));
500  csma.SetChannelAttribute ("Delay", TimeValue (MilliSeconds (2)));
501  //
502  // Now fill out the topology by creating the net devices required to connect
503  // the nodes to the channels and hooking them up.
504  //
505  NetDeviceContainer devices = csma.Install (nodes);
506 
507  InternetStackHelper internet;
508  internet.Install (nodes);
509 
510  // We've got the "hardware" in place. Now we need to add IP addresses.
511  //
512  Ipv4AddressHelper ipv4;
513  ipv4.SetBase ("10.1.1.0", "255.255.255.0");
515 
516  uint16_t port = 9; // Discard port (RFC 863)
517 
518  //
519  // Create an OnOff application to send UDP datagrams from node zero
520  // to node 1.
521  //
522  // Make packets be sent about every defaultPacketSize / dataRate =
523  // 4096 bits / (5000 bits/second) = 0.82 second.
524  OnOffHelper onoff ("ns3::UdpSocketFactory",
525  Address (InetSocketAddress (interfaces.GetAddress (1), port)));
526  onoff.SetConstantRate (DataRate (5000));
527 
528  ApplicationContainer app = onoff.Install (nodes.Get (0));
529  // Start the application
530  app.Start (Seconds (1.0));
531  app.Stop (Seconds (10.0));
532 
533  // Create an optional packet sink to receive these packets
534  PacketSinkHelper sink ("ns3::UdpSocketFactory",
535  Address (InetSocketAddress (Ipv4Address::GetAny (), port)));
536  app = sink.Install (nodes.Get (1));
537  app.Start (Seconds (0.0));
538 
539  //
540  // Create a similar flow from n3 to n0, starting at time 1.1 seconds
541  //
542  onoff.SetAttribute ("Remote",
543  AddressValue (InetSocketAddress (interfaces.GetAddress (0), port)));
544  app = onoff.Install (nodes.Get (3));
545  app.Start (Seconds (1.1));
546  app.Stop (Seconds (10.0));
547 
548  app = sink.Install (nodes.Get (0));
549  app.Start (Seconds (0.0));
550 
551  // Trace receptions
552  Config::ConnectWithoutContext ("/NodeList/0/ApplicationList/1/$ns3::PacketSink/Rx", MakeCallback (&CsmaOneSubnetTestCase::SinkRxNode0, this));
553  Config::ConnectWithoutContext ("/NodeList/1/ApplicationList/0/$ns3::PacketSink/Rx", MakeCallback (&CsmaOneSubnetTestCase::SinkRxNode1, this));
554 
555  //
556  // Now, do the actual simulation.
557  //
558  Simulator::Run ();
559  Simulator::Destroy ();
560 
561  // We should have sent and received 10 packets
562  NS_TEST_ASSERT_MSG_EQ (m_countNode0, 10, "Node 0 should have received 10 packets");
563  NS_TEST_ASSERT_MSG_EQ (m_countNode1, 10, "Node 1 should have received 10 packets");
564 }
565 
567 {
568 public:
570  virtual ~CsmaPacketSocketTestCase ();
571 
572 private:
573  virtual void DoRun (void);
574  void SinkRx (std::string path, Ptr<const Packet> p, const Address &address);
575  void DropEvent (Ptr<const Packet> p);
576  uint32_t m_count;
577  uint32_t m_drops;
578 };
579 
580 // Add some help text to this case to describe what it is intended to test
582  : TestCase ("Packet socket example for Carrier Sense Multiple Access (CSMA) networks"), m_count (0), m_drops (0)
583 {
584 }
585 
587 {
588 }
589 
590 void
592 {
593  m_count++;
594 }
595 
596 void
598 {
599  m_drops++;
600 }
601 
602 //
603 // Network topology
604 //
605 // n0 n1 n2 n3
606 // | | | |
607 // =====================
608 //
609 // - Packet socket flow from n0 to n1 and from node n3 to n0
610 // -- We will test reception at node n0
611 // - Default 512 byte packets generated by traffic generator
612 //
613 void
615 {
616  // Here, we will explicitly create four nodes.
618  nodes.Create (4);
619 
620  PacketSocketHelper packetSocket;
621  packetSocket.Install (nodes);
622 
623  // create the shared medium used by all csma devices.
624  Ptr<CsmaChannel> channel = CreateObjectWithAttributes<CsmaChannel> (
625  "DataRate", DataRateValue (DataRate (5000000)),
626  "Delay", TimeValue (MilliSeconds (2)));
627 
628  // use a helper function to connect our nodes to the shared channel.
630  csma.SetDeviceAttribute ("EncapsulationMode", StringValue ("Llc"));
631  NetDeviceContainer devs = csma.Install (nodes, channel);
632 
633  // Create the OnOff application to send raw datagrams
634  //
635  // Make packets be sent about every DefaultPacketSize / DataRate =
636  // 4096 bits / (5000 bits/second) = 0.82 second.
637  PacketSocketAddress socket;
638  socket.SetSingleDevice (devs.Get (0)->GetIfIndex ());
639  socket.SetPhysicalAddress (devs.Get (1)->GetAddress ());
640  socket.SetProtocol (2);
641  OnOffHelper onoff ("ns3::PacketSocketFactory", Address (socket));
642  onoff.SetConstantRate (DataRate (5000));
643  ApplicationContainer apps = onoff.Install (nodes.Get (0));
644  apps.Start (Seconds (1.0));
645  apps.Stop (Seconds (10.0));
646 
647  socket.SetSingleDevice (devs.Get (3)->GetIfIndex ());
648  socket.SetPhysicalAddress (devs.Get (0)->GetAddress ());
649  socket.SetProtocol (3);
650  onoff.SetAttribute ("Remote", AddressValue (socket));
651  apps = onoff.Install (nodes.Get (3));
652  apps.Start (Seconds (1.0));
653  apps.Stop (Seconds (10.0));
654 
655  PacketSinkHelper sink = PacketSinkHelper ("ns3::PacketSocketFactory",
656  socket);
657  apps = sink.Install (nodes.Get (0));
658  apps.Start (Seconds (0.0));
659  apps.Stop (Seconds (20.0));
660 
661  // Trace receptions
662  Config::Connect ("/NodeList/0/ApplicationList/*/$ns3::PacketSink/Rx",
664 
665  Simulator::Run ();
666  Simulator::Destroy ();
667 
668  // We should have received 10 packets on node 0
669  NS_TEST_ASSERT_MSG_EQ (m_count, 10, "Node 0 should have received 10 packets");
670 }
671 
673 {
674 public:
675  CsmaPingTestCase ();
676  virtual ~CsmaPingTestCase ();
677 
678 private:
679  virtual void DoRun (void);
680  void SinkRx (Ptr<const Packet> p, const Address &ad);
681  void PingRtt (std::string context, Time rtt);
682  void DropEvent (Ptr<const Packet> p);
683  uint32_t m_countSinkRx;
684  uint32_t m_countPingRtt;
685  uint32_t m_drops;
686 };
687 
688 // Add some help text to this case to describe what it is intended to test
690  : TestCase ("Ping example for Carrier Sense Multiple Access (CSMA) networks"), m_countSinkRx (0), m_countPingRtt (0), m_drops (0)
691 {
692 }
693 
695 {
696 }
697 
698 void
700 {
701  m_countSinkRx++;
702 }
703 
704 void
705 CsmaPingTestCase::PingRtt (std::string context, Time rtt)
706 {
707  m_countPingRtt++;
708 }
709 
710 void
712 {
713  m_drops++;
714 }
715 
716 // Network topology
717 //
718 // n0 n1 n2 n3
719 // | | | |
720 // =====================
721 //
722 // node n0,n1,n3 pings to node n2
723 // node n0 generates protocol 2 (IGMP) to node n3
724 //
725 void
727 {
728  // Here, we will explicitly create four nodes.
729  NodeContainer c;
730  c.Create (4);
731 
732  // connect all our nodes to a shared channel.
734  csma.SetChannelAttribute ("DataRate", DataRateValue (DataRate (5000000)));
735  csma.SetChannelAttribute ("Delay", TimeValue (MilliSeconds (2)));
736  csma.SetDeviceAttribute ("EncapsulationMode", StringValue ("Llc"));
737  NetDeviceContainer devs = csma.Install (c);
738 
739  // add an ip stack to all nodes.
740  InternetStackHelper ipStack;
741  ipStack.Install (c);
742 
743  // assign ip addresses
745  ip.SetBase ("192.168.1.0", "255.255.255.0");
746  Ipv4InterfaceContainer addresses = ip.Assign (devs);
747 
748  // Create the OnOff application to send UDP datagrams from n0 to n1.
749  //
750  // Make packets be sent about every DefaultPacketSize / DataRate =
751  // 4096 bits / (5000 bits/second) = 0.82 second.
752  Config::SetDefault ("ns3::Ipv4RawSocketImpl::Protocol", StringValue ("2"));
753  InetSocketAddress dst = InetSocketAddress (addresses.GetAddress (3));
754  OnOffHelper onoff = OnOffHelper ("ns3::Ipv4RawSocketFactory", dst);
755  onoff.SetConstantRate (DataRate (5000));
756 
757  ApplicationContainer apps = onoff.Install (c.Get (0));
758  apps.Start (Seconds (1.0));
759  apps.Stop (Seconds (10.0));
760 
761  PacketSinkHelper sink = PacketSinkHelper ("ns3::Ipv4RawSocketFactory", dst);
762  apps = sink.Install (c.Get (3));
763  apps.Start (Seconds (0.0));
764  apps.Stop (Seconds (11.0));
765 
766  V4PingHelper ping = V4PingHelper (addresses.GetAddress (2));
767  NodeContainer pingers;
768  pingers.Add (c.Get (0));
769  pingers.Add (c.Get (1));
770  pingers.Add (c.Get (3));
771  apps = ping.Install (pingers);
772  apps.Start (Seconds (2.0));
773  apps.Stop (Seconds (5.0));
774 
775  // Trace receptions
776  Config::ConnectWithoutContext ("/NodeList/3/ApplicationList/0/$ns3::PacketSink/Rx",
778 
779  // Trace pings
780  Config::Connect ("/NodeList/*/ApplicationList/*/$ns3::V4Ping/Rtt",
782 
783  Simulator::Run ();
784  Simulator::Destroy ();
785 
786  // We should have sent and received 10 packets
787  NS_TEST_ASSERT_MSG_EQ (m_countSinkRx, 10, "Node 3 should have received 10 packets");
788 
789  // We should have 3 pingers that ping every second for 3 seconds.
790  NS_TEST_ASSERT_MSG_EQ (m_countPingRtt, 9, "Node 2 should have been pinged 9 times");
791 }
792 
794 {
795 public:
797  virtual ~CsmaRawIpSocketTestCase ();
798 
799 private:
800  virtual void DoRun (void);
801  void SinkRx (Ptr<const Packet> p, const Address &ad);
802  void DropEvent (Ptr<const Packet> p);
803  uint32_t m_count;
804  uint32_t m_drops;
805 };
806 
807 // Add some help text to this case to describe what it is intended to test
809  : TestCase ("Raw internet protocol socket example for Carrier Sense Multiple Access (CSMA) networks"), m_count (0), m_drops (0)
810 {
811 }
812 
814 {
815 }
816 
817 void
819 {
820  m_count++;
821 }
822 
823 void
825 {
826  m_drops++;
827 }
828 
829 //
830 // Network topology
831 // (sender) (receiver)
832 // n0 n1 n2 n3
833 // | | | |
834 // =====================
835 //
836 // Node n0 sends data to node n3 over a raw IP socket. The protocol
837 // number used is 2.
838 //
839 void
841 {
842  // Here, we will explicitly create four nodes.
843  NodeContainer c;
844  c.Create (4);
845 
846  // connect all our nodes to a shared channel.
848  csma.SetChannelAttribute ("DataRate", DataRateValue (DataRate (5000000)));
849  csma.SetChannelAttribute ("Delay", TimeValue (MilliSeconds (2)));
850  csma.SetDeviceAttribute ("EncapsulationMode", StringValue ("Llc"));
851  NetDeviceContainer devs = csma.Install (c);
852 
853  // add an ip stack to all nodes.
854  InternetStackHelper ipStack;
855  ipStack.Install (c);
856 
857  // assign ip addresses
859  ip.SetBase ("192.168.1.0", "255.255.255.0");
860  Ipv4InterfaceContainer addresses = ip.Assign (devs);
861 
862  // IP protocol configuration
863  //
864  // Make packets be sent about every DefaultPacketSize / DataRate =
865  // 4096 bits / (5000 bits/second) = 0.82 second.
866  Config::SetDefault ("ns3::Ipv4RawSocketImpl::Protocol", StringValue ("2"));
867  InetSocketAddress dst = InetSocketAddress (addresses.GetAddress (3));
868  OnOffHelper onoff = OnOffHelper ("ns3::Ipv4RawSocketFactory", dst);
869  onoff.SetConstantRate (DataRate (5000));
870 
871  ApplicationContainer apps = onoff.Install (c.Get (0));
872  apps.Start (Seconds (1.0));
873  apps.Stop (Seconds (10.0));
874 
875  PacketSinkHelper sink = PacketSinkHelper ("ns3::Ipv4RawSocketFactory", dst);
876  apps = sink.Install (c.Get (3));
877  apps.Start (Seconds (0.0));
878  apps.Stop (Seconds (12.0));
879 
880  // Trace receptions
881  Config::ConnectWithoutContext ("/NodeList/3/ApplicationList/0/$ns3::PacketSink/Rx",
883 
884  Simulator::Run ();
885  Simulator::Destroy ();
886 
887  // We should have sent and received 10 packets
888  NS_TEST_ASSERT_MSG_EQ (m_count, 10, "Node 3 should have received 10 packets");
889 }
890 
892 {
893 public:
894  CsmaStarTestCase ();
895  virtual ~CsmaStarTestCase ();
896 
897 private:
898  virtual void DoRun (void);
899  void SinkRx (Ptr<const Packet> p, const Address &ad);
900  void DropEvent (Ptr<const Packet> p);
901  uint32_t m_count;
902  uint32_t m_drops;
903 };
904 
905 // Add some help text to this case to describe what it is intended to test
907  : TestCase ("Star example for Carrier Sense Multiple Access (CSMA) networks"), m_count (0), m_drops (0)
908 {
909 }
910 
912 {
913 }
914 
915 void
917 {
918  m_count++;
919 }
920 
921 void
923 {
924  m_drops++;
925 }
926 
927 // Network topology (default)
928 //
929 // n2 + + n3 .
930 // | ... |\ /| ... | .
931 // ======= \ / ======= .
932 // CSMA \ / CSMA .
933 // \ / .
934 // n1 +--- n0 ---+ n4 .
935 // | ... | / \ | ... | .
936 // ======= / \ ======= .
937 // CSMA / \ CSMA .
938 // / \ .
939 // n6 + + n5 .
940 // | ... | | ... | .
941 // ======= ======= .
942 // CSMA CSMA .
943 //
944 void
946 {
947  //
948  // Default number of nodes in the star.
949  //
950  uint32_t nSpokes = 7;
951 
953  csma.SetChannelAttribute ("DataRate", StringValue ("100Mbps"));
954  csma.SetChannelAttribute ("Delay", StringValue ("1ms"));
955  CsmaStarHelper star (nSpokes, csma);
956 
957  NodeContainer fillNodes;
958 
959  //
960  // Just to be nasy, hang some more nodes off of the CSMA channel for each
961  // spoke, so that there are a total of 16 nodes on each channel. Stash
962  // all of these new devices into a container.
963  //
964  NetDeviceContainer fillDevices;
965 
966  uint32_t nFill = 14;
967  for (uint32_t i = 0; i < star.GetSpokeDevices ().GetN (); ++i)
968  {
969  Ptr<Channel> channel = star.GetSpokeDevices ().Get (i)->GetChannel ();
970  Ptr<CsmaChannel> csmaChannel = channel->GetObject<CsmaChannel> ();
971  NodeContainer newNodes;
972  newNodes.Create (nFill);
973  fillNodes.Add (newNodes);
974  fillDevices.Add (csma.Install (newNodes, csmaChannel));
975  }
976 
977  InternetStackHelper internet;
978  star.InstallStack (internet);
979  internet.Install (fillNodes);
980 
981  star.AssignIpv4Addresses (Ipv4AddressHelper ("10.1.0.0", "255.255.255.0"));
982 
983  //
984  // We assigned addresses to the logical hub and the first "drop" of the
985  // CSMA network that acts as the spoke, but we also have a number of fill
986  // devices (nFill) also hanging off the CSMA network. We have got to
987  // assign addresses to them as well. We put all of the fill devices into
988  // a single device container, so the first nFill devices are associated
989  // with the channel connected to spokeDevices.Get (0), the second nFill
990  // devices afe associated with the channel connected to spokeDevices.Get (1)
991  // etc.
992  //
994  for(uint32_t i = 0; i < star.SpokeCount (); ++i)
995  {
996  std::ostringstream subnet;
997  subnet << "10.1." << i << ".0";
998  address.SetBase (subnet.str ().c_str (), "255.255.255.0", "0.0.0.3");
999 
1000  for (uint32_t j = 0; j < nFill; ++j)
1001  {
1002  address.Assign (fillDevices.Get (i * nFill + j));
1003  }
1004  }
1005 
1006  //
1007  // Create a packet sink on the star "hub" to receive packets.
1008  //
1009  uint16_t port = 50000;
1010  Address hubLocalAddress (InetSocketAddress (Ipv4Address::GetAny (), port));
1011  PacketSinkHelper packetSinkHelper ("ns3::TcpSocketFactory", hubLocalAddress);
1012  ApplicationContainer hubApp = packetSinkHelper.Install (star.GetHub ());
1013  hubApp.Start (Seconds (1.0));
1014  hubApp.Stop (Seconds (10.0));
1015 
1016  //
1017  // Create OnOff applications to send TCP to the hub, one on each spoke node.
1018  //
1019  // Make packets be sent about every DefaultPacketSize / DataRate =
1020  // 4096 bits / (5000 bits/second) = 0.82 second.
1021  OnOffHelper onOffHelper ("ns3::TcpSocketFactory", Address ());
1022  onOffHelper.SetConstantRate (DataRate (5000));
1023 
1024  ApplicationContainer spokeApps;
1025 
1026  for (uint32_t i = 0; i < star.SpokeCount (); ++i)
1027  {
1028  AddressValue remoteAddress (InetSocketAddress (star.GetHubIpv4Address (i), port));
1029  onOffHelper.SetAttribute ("Remote", remoteAddress);
1030  spokeApps.Add (onOffHelper.Install (star.GetSpokeNode (i)));
1031  }
1032 
1033  spokeApps.Start (Seconds (1.0));
1034  spokeApps.Stop (Seconds (10.0));
1035 
1036  //
1037  // Because we are evil, we also add OnOff applications to send TCP to the hub
1038  // from the fill devices on each CSMA link. The first nFill nodes in the
1039  // fillNodes container are on the CSMA network talking to the zeroth device
1040  // on the hub node. The next nFill nodes are on the CSMA network talking to
1041  // the first device on the hub node, etc. So the ith fillNode is associated
1042  // with the hub address found on the (i / nFill)th device on the hub node.
1043  //
1044  ApplicationContainer fillApps;
1045 
1046  for (uint32_t i = 0; i < fillNodes.GetN (); ++i)
1047  {
1048  AddressValue remoteAddress (InetSocketAddress (star.GetHubIpv4Address (i / nFill), port));
1049  onOffHelper.SetAttribute ("Remote", remoteAddress);
1050  fillApps.Add (onOffHelper.Install (fillNodes.Get (i)));
1051  }
1052 
1053  fillApps.Start (Seconds (1.0));
1054  fillApps.Stop (Seconds (10.0));
1055 
1056  //
1057  // Turn on global static routing so we can actually be routed across the star.
1058  //
1059  Ipv4GlobalRoutingHelper::PopulateRoutingTables ();
1060 
1061  // Trace receptions
1062  Config::ConnectWithoutContext ("/NodeList/0/ApplicationList/*/$ns3::PacketSink/Rx",
1064 
1065  Simulator::Run ();
1066  Simulator::Destroy ();
1067 
1068  // The hub node should have received 10 packets from the nFill + 1
1069  // nodes on each spoke.
1070  NS_TEST_ASSERT_MSG_EQ (m_count, 10 * ( nSpokes * (nFill + 1)), "Hub node did not receive the proper number of packets");
1071 }
1072 
1074 {
1075 public:
1077 };
1078 
1080  : TestSuite ("csma-system", UNIT)
1081 {
1082  AddTestCase (new CsmaBridgeTestCase, TestCase::QUICK);
1083  AddTestCase (new CsmaBroadcastTestCase, TestCase::QUICK);
1084  AddTestCase (new CsmaMulticastTestCase, TestCase::QUICK);
1085  AddTestCase (new CsmaOneSubnetTestCase, TestCase::QUICK);
1086  AddTestCase (new CsmaPacketSocketTestCase, TestCase::QUICK);
1087  AddTestCase (new CsmaPingTestCase, TestCase::QUICK);
1088  AddTestCase (new CsmaRawIpSocketTestCase, TestCase::QUICK);
1089  AddTestCase (new CsmaStarTestCase, TestCase::QUICK);
1090 }
1091 
1092 // Do not forget to allocate an instance of this TestSuite
virtual void DoRun(void)
Implementation to actually run this TestCase.
Ptr< PacketSink > sink
Definition: wifi-tcp.cc:56
void AssignIpv4Addresses(Ipv4AddressHelper address)
holds a vector of ns3::Application pointers.
void SinkRx(Ptr< const Packet > p, const Address &ad)
void SinkRx(Ptr< const Packet > p, const Address &ad)
void SinkRxNode0(Ptr< const Packet > p, const Address &ad)
virtual void DoRun(void)
Implementation to actually run this TestCase.
Ptr< NetDevice > Get(uint32_t i) const
Get the Ptr<NetDevice> stored in this container at a given index.
Simulation virtual time values and global simulation resolution.
Definition: nstime.h:103
void InstallStack(InternetStackHelper stack)
an Inet address class
virtual void DoRun(void)
Implementation to actually run this TestCase.
holds a vector of std::pair of Ptr<Ipv4> and interface index.
void DropEvent(Ptr< const Packet > p)
Hold variables of type string.
Definition: string.h:41
void Add(ApplicationContainer other)
Append the contents of another ApplicationContainer to the end of this container. ...
A suite of tests to run.
Definition: test.h:1343
static CsmaSystemTestSuite csmaSystemTestSuite
an address for a packet socket
Time MilliSeconds(uint64_t value)
Construct a Time in the indicated unit.
Definition: nstime.h:1297
uint32_t SpokeCount() const
ApplicationContainer Install(NodeContainer c) const
Install an ns3::PacketSinkApplication on each node of the input container configured with all the att...
aggregate IP/TCP/UDP functionality to existing Nodes.
void DropEvent(Ptr< const Packet > p)
A helper to make it easier to instantiate an ns3::PacketSinkApplication on a set of nodes...
void SinkRx(Ptr< const Packet > p, const Address &ad)
virtual void DoRun(void)
Implementation to actually run this TestCase.
void DropEvent(Ptr< const Packet > p)
encapsulates test code
Definition: test.h:1153
void SetDefaultMulticastRoute(Ptr< Node > n, Ptr< NetDevice > nd)
Add a default route to the static routing protocol to forward packets out a particular interface...
A helper to make it easier to instantiate an ns3::OnOffApplication on a set of nodes.
Definition: on-off-helper.h:42
Ptr< Node > GetHub() const
Give ns3::PacketSocket powers to ns3::Node.
void SetSingleDevice(uint32_t device)
Set the address to match only a specified NetDevice.
uint16_t port
Definition: dsdv-manet.cc:45
a polymophic address class
Definition: address.h:90
void DropEvent(Ptr< const Packet > p)
void SinkRxNode1(Ptr< const Packet > p, const Address &ad)
channel
Definition: third.py:92
void AddMulticastRoute(Ptr< Node > n, Ipv4Address source, Ipv4Address group, Ptr< NetDevice > input, NetDeviceContainer output)
Add a multicast route to a node and net device using explicit Ptr<Node> and Ptr<NetDevice> ...
Class for representing data rates.
Definition: data-rate.h:88
ApplicationContainer Install(NodeContainer nodes) const
Install a Ping application on each Node in the provided NodeContainer.
ApplicationContainer Install(NodeContainer c) const
Install an ns3::OnOffApplication on each node of the input container configured with all the attribut...
nodes
Definition: first.py:32
virtual void DoRun(void)
Implementation to actually run this TestCase.
AttributeValue implementation for Time.
Definition: nstime.h:1353
void AddTestCase(TestCase *testCase, TestDuration duration=QUICK)
Add an individual child TestCase to this test suite.
Definition: test.cc:299
Ipv4Address GetAddress(uint32_t i, uint32_t j=0) const
void DropEvent(Ptr< const Packet > p)
void Add(NetDeviceContainer other)
Append the contents of another NetDeviceContainer to the end of this container.
virtual void DoRun(void)
Implementation to actually run this TestCase.
#define NS_TEST_ASSERT_MSG_EQ(actual, limit, msg)
Test that an actual and expected (limit) value are equal and report and abort if not.
Definition: test.h:166
holds a vector of ns3::NetDevice pointers
void ConnectWithoutContext(std::string path, const CallbackBase &cb)
Definition: config.cc:901
Add capability to bridge multiple LAN segments (IEEE 802.1D bridging)
Definition: bridge-helper.h:43
void Start(Time start)
Arrange for all of the Applications in this container to Start() at the Time given as a parameter...
csma
Definition: second.py:63
void Connect(std::string path, const CallbackBase &cb)
Definition: config.cc:920
virtual void DoRun(void)
Implementation to actually run this TestCase.
uint32_t GetN(void) const
Get the number of Ptr<Node> stored in this container.
NetDeviceContainer GetSpokeDevices() const
Csma Channel.
Definition: csma-channel.h:90
Every class exported by the ns3 library is enclosed in the ns3 namespace.
void SetConstantRate(DataRate dataRate, uint32_t packetSize=512)
Helper function to set a constant rate source.
void SetPhysicalAddress(const Address address)
Set the destination address.
keep track of a set of node pointers.
address
Definition: first.py:44
build a set of CsmaNetDevice objects
Definition: csma-helper.h:46
NetDeviceContainer Install(Ptr< Node > node, NetDeviceContainer c)
This method creates an ns3::BridgeNetDevice with the attributes configured by BridgeHelper::SetDevice...
void Install(std::string nodeName) const
Aggregate implementations of the ns3::Ipv4, ns3::Ipv6, ns3::Udp, and ns3::Tcp classes onto the provid...
Ptr< Node > GetSpokeNode(uint32_t i) const
void DropEvent(Ptr< const Packet > p)
void SinkRx(Ptr< const Packet > p, const Address &ad)
Ipv4 addresses are stored in host order in this class.
Definition: ipv4-address.h:41
AttributeValue implementation for Address.
Definition: address.h:278
virtual void DoRun(void)
Implementation to actually run this TestCase.
void Stop(Time stop)
Arrange for all of the Applications in this container to Stop() at the Time given as a parameter...
Ipv4InterfaceContainer Assign(const NetDeviceContainer &c)
Assign IP addresses to the net devices specified in the container based on the current network prefix...
Ipv4Address GetHubIpv4Address(uint32_t i) const
void Add(NodeContainer other)
Append the contents of another NodeContainer to the end of this container.
Helper class that adds ns3::Ipv4StaticRouting objects.
AttributeValue implementation for DataRate.
Definition: data-rate.h:298
Time Seconds(double value)
Construct a Time in the indicated unit.
Definition: nstime.h:1289
uint32_t GetN(void) const
Get the number of Ptr<NetDevice> stored in this container.
void SetDefault(std::string name, const AttributeValue &value)
Definition: config.cc:849
interfaces
Definition: first.py:48
void PingRtt(std::string context, Time rtt)
void SetProtocol(uint16_t protocol)
Set the protocol.
Ptr< Node > Get(uint32_t i) const
Get the Ptr<Node> stored in this container at a given index.
void Install(Ptr< Node > node) const
Aggregate an instance of a ns3::PacketSocketFactory onto the provided node.
void DropEvent(Ptr< const Packet > p)
A helper class to make life easier while doing simple IPv4 address assignment in scripts.
A helper to make it easier to create a star topology with Csma links.
void Create(uint32_t n)
Create n nodes and append pointers to them to the end of this NodeContainer.
devices
Definition: first.py:39
void SinkRx(std::string path, Ptr< const Packet > p, const Address &address)
void SinkRxNode1(Ptr< const Packet > p, const Address &ad)
static void SinkRx(std::string path, Ptr< const Packet > p, const Address &address)
void SinkRx(Ptr< const Packet > p, const Address &ad)
Create a IPv4 ping application and associate it to a node.
Definition: v4ping-helper.h:37
Callback< R, Ts... > MakeCallback(R(T::*memPtr)(Ts...), OBJ objPtr)
Build Callbacks for class method members which take varying numbers of arguments and potentially retu...
Definition: callback.h:1642
void SetAttribute(std::string name, const AttributeValue &value)
Helper function used to set the underlying application attributes.
void SinkRxNode2(Ptr< const Packet > p, const Address &ad)
void SetBase(Ipv4Address network, Ipv4Mask mask, Ipv4Address base="0.0.0.1")
Set the base network number, network mask and base address.