|
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/node-container.h" |
|
38 #include "ns3/on-off-helper.h" |
|
39 #include "ns3/packet.h" |
|
40 #include "ns3/packet-sink-helper.h" |
|
41 #include "ns3/packet-socket-helper.h" |
|
42 #include "ns3/packet-socket-address.h" |
|
43 #include "ns3/pointer.h" |
|
44 #include "ns3/random-variable.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 |
|
54 class CsmaBridgeTestCase : public TestCase |
|
55 { |
|
56 public: |
|
57 CsmaBridgeTestCase (); |
|
58 virtual ~CsmaBridgeTestCase (); |
|
59 |
|
60 private: |
|
61 virtual bool 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 |
|
67 CsmaBridgeTestCase::CsmaBridgeTestCase () |
|
68 : TestCase ("Bridge example for Carrier Sense Multiple Access (CSMA) networks"), m_count (0) |
|
69 { |
|
70 } |
|
71 |
|
72 CsmaBridgeTestCase::~CsmaBridgeTestCase () |
|
73 { |
|
74 } |
|
75 |
|
76 void |
|
77 CsmaBridgeTestCase::SinkRx (Ptr<const Packet> p, const Address &ad) |
|
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 bool |
|
95 CsmaBridgeTestCase::DoRun (void) |
|
96 { |
|
97 NodeContainer terminals; |
|
98 terminals.Create (4); |
|
99 |
|
100 NodeContainer csmaSwitch; |
|
101 csmaSwitch.Create (1); |
|
102 |
|
103 CsmaHelper csma; |
|
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.SetAttribute ("OnTime", RandomVariableValue (ConstantVariable (1))); |
|
138 onoff.SetAttribute ("OffTime", RandomVariableValue (ConstantVariable (0))); |
|
139 onoff.SetAttribute ("DataRate", DataRateValue (DataRate (5000))); |
|
140 |
|
141 ApplicationContainer app = onoff.Install (terminals.Get (0)); |
|
142 app.Start (Seconds (1.0)); |
|
143 app.Stop (Seconds (10.0)); |
|
144 |
|
145 PacketSinkHelper sink ("ns3::UdpSocketFactory", |
|
146 Address (InetSocketAddress (Ipv4Address::GetAny (), port))); |
|
147 app = sink.Install (terminals.Get (1)); |
|
148 app.Start (Seconds (0.0)); |
|
149 |
|
150 // Trace receptions |
|
151 Config::ConnectWithoutContext ("/NodeList/1/ApplicationList/0/$ns3::PacketSink/Rx", MakeCallback (&CsmaBridgeTestCase::SinkRx, this)); |
|
152 |
|
153 Simulator::Run (); |
|
154 Simulator::Destroy (); |
|
155 |
|
156 // We should have sent and received 10 packets |
|
157 NS_TEST_ASSERT_MSG_EQ (m_count, 10, "Bridge should have passed 10 packets"); |
|
158 |
|
159 return GetErrorStatus (); |
|
160 } |
|
161 |
|
162 class CsmaBroadcastTestCase : public TestCase |
|
163 { |
|
164 public: |
|
165 CsmaBroadcastTestCase (); |
|
166 virtual ~CsmaBroadcastTestCase (); |
|
167 |
|
168 private: |
|
169 virtual bool DoRun (void); |
|
170 void SinkRxNode1 (Ptr<const Packet> p, const Address &ad); |
|
171 void SinkRxNode2 (Ptr<const Packet> p, const Address &ad); |
|
172 void DropEvent (Ptr<const Packet> p); |
|
173 uint32_t m_countNode1; |
|
174 uint32_t m_countNode2; |
|
175 uint32_t m_drops; |
|
176 }; |
|
177 |
|
178 // Add some help text to this case to describe what it is intended to test |
|
179 CsmaBroadcastTestCase::CsmaBroadcastTestCase () |
|
180 : TestCase ("Broadcast example for Carrier Sense Multiple Access (CSMA) networks"), m_countNode1 (0), m_countNode2 (0), m_drops (0) |
|
181 { |
|
182 } |
|
183 |
|
184 CsmaBroadcastTestCase::~CsmaBroadcastTestCase () |
|
185 { |
|
186 } |
|
187 |
|
188 void |
|
189 CsmaBroadcastTestCase::SinkRxNode1 (Ptr<const Packet> p, const Address &ad) |
|
190 { |
|
191 m_countNode1++; |
|
192 } |
|
193 |
|
194 void |
|
195 CsmaBroadcastTestCase::SinkRxNode2 (Ptr<const Packet> p, const Address &ad) |
|
196 { |
|
197 m_countNode2++; |
|
198 } |
|
199 |
|
200 void |
|
201 CsmaBroadcastTestCase::DropEvent (Ptr<const Packet> p) |
|
202 { |
|
203 m_drops++; |
|
204 } |
|
205 |
|
206 // |
|
207 // Example of the sending of a datagram to a broadcast address |
|
208 // |
|
209 // Network topology |
|
210 // ============== |
|
211 // | | |
|
212 // n0 n1 n2 |
|
213 // | | |
|
214 // ========== |
|
215 // |
|
216 // n0 originates UDP broadcast to 255.255.255.255/discard port, which |
|
217 // is replicated and received on both n1 and n2 |
|
218 // |
|
219 bool |
|
220 CsmaBroadcastTestCase::DoRun (void) |
|
221 { |
|
222 NodeContainer c; |
|
223 c.Create (3); |
|
224 NodeContainer c0 = NodeContainer (c.Get (0), c.Get (1)); |
|
225 NodeContainer c1 = NodeContainer (c.Get (0), c.Get (2)); |
|
226 |
|
227 CsmaHelper csma; |
|
228 csma.SetChannelAttribute ("DataRate", DataRateValue (DataRate(5000000))); |
|
229 csma.SetChannelAttribute ("Delay", TimeValue (MilliSeconds(2))); |
|
230 |
|
231 NetDeviceContainer n0 = csma.Install (c0); |
|
232 NetDeviceContainer n1 = csma.Install (c1); |
|
233 |
|
234 InternetStackHelper internet; |
|
235 internet.Install (c); |
|
236 |
|
237 Ipv4AddressHelper ipv4; |
|
238 ipv4.SetBase ("10.1.0.0", "255.255.255.0"); |
|
239 ipv4.Assign (n0); |
|
240 ipv4.SetBase ("192.168.1.0", "255.255.255.0"); |
|
241 ipv4.Assign (n1); |
|
242 |
|
243 |
|
244 // RFC 863 discard port ("9") indicates packet should be thrown away |
|
245 // by the system. We allow this silent discard to be overridden |
|
246 // by the PacketSink application. |
|
247 uint16_t port = 9; |
|
248 |
|
249 // Create the OnOff application to send UDP datagrams from n0. |
|
250 // |
|
251 // Make packets be sent about every DefaultPacketSize / DataRate = |
|
252 // 4096 bits / (5000 bits/second) = 0.82 second. |
|
253 OnOffHelper onoff ("ns3::UdpSocketFactory", |
|
254 Address (InetSocketAddress (Ipv4Address ("255.255.255.255"), port))); |
|
255 onoff.SetAttribute ("OnTime", RandomVariableValue (ConstantVariable (1))); |
|
256 onoff.SetAttribute ("OffTime", RandomVariableValue (ConstantVariable (0))); |
|
257 onoff.SetAttribute ("DataRate", DataRateValue (DataRate (5000))); |
|
258 |
|
259 ApplicationContainer app = onoff.Install (c0.Get (0)); |
|
260 // Start the application |
|
261 app.Start (Seconds (1.0)); |
|
262 app.Stop (Seconds (10.0)); |
|
263 |
|
264 // Create an optional packet sink to receive these packets |
|
265 PacketSinkHelper sink ("ns3::UdpSocketFactory", |
|
266 Address (InetSocketAddress (Ipv4Address::GetAny (), port))); |
|
267 app = sink.Install (c0.Get (1)); |
|
268 app.Add (sink.Install (c1.Get (1))); |
|
269 app.Start (Seconds (1.0)); |
|
270 app.Stop (Seconds (10.0)); |
|
271 |
|
272 // Trace receptions |
|
273 Config::ConnectWithoutContext ("/NodeList/1/ApplicationList/0/$ns3::PacketSink/Rx", MakeCallback (&CsmaBroadcastTestCase::SinkRxNode1, this)); |
|
274 Config::ConnectWithoutContext ("/NodeList/2/ApplicationList/0/$ns3::PacketSink/Rx", MakeCallback (&CsmaBroadcastTestCase::SinkRxNode2, this)); |
|
275 |
|
276 Simulator::Run (); |
|
277 Simulator::Destroy (); |
|
278 |
|
279 // We should have sent and received 10 packets |
|
280 NS_TEST_ASSERT_MSG_EQ (m_countNode1, 10, "Node 1 should have received 10 packets"); |
|
281 NS_TEST_ASSERT_MSG_EQ (m_countNode2, 10, "Node 2 should have received 10 packets"); |
|
282 |
|
283 return GetErrorStatus (); |
|
284 } |
|
285 |
|
286 class CsmaMulticastTestCase : public TestCase |
|
287 { |
|
288 public: |
|
289 CsmaMulticastTestCase (); |
|
290 virtual ~CsmaMulticastTestCase (); |
|
291 |
|
292 private: |
|
293 virtual bool DoRun (void); |
|
294 void SinkRx (Ptr<const Packet> p, const Address &ad); |
|
295 void DropEvent (Ptr<const Packet> p); |
|
296 uint32_t m_count; |
|
297 uint32_t m_drops; |
|
298 }; |
|
299 |
|
300 // Add some help text to this case to describe what it is intended to test |
|
301 CsmaMulticastTestCase::CsmaMulticastTestCase () |
|
302 : TestCase ("Multicast example for Carrier Sense Multiple Access (CSMA) networks"), m_count (0), m_drops (0) |
|
303 { |
|
304 } |
|
305 |
|
306 CsmaMulticastTestCase::~CsmaMulticastTestCase () |
|
307 { |
|
308 } |
|
309 |
|
310 void |
|
311 CsmaMulticastTestCase::SinkRx (Ptr<const Packet> p, const Address& ad) |
|
312 { |
|
313 m_count++; |
|
314 } |
|
315 |
|
316 void |
|
317 CsmaMulticastTestCase::DropEvent (Ptr<const Packet> p) |
|
318 { |
|
319 m_drops++; |
|
320 } |
|
321 |
|
322 // Network topology |
|
323 // |
|
324 // Lan1 |
|
325 // =========== |
|
326 // | | | |
|
327 // n0 n1 n2 n3 n4 |
|
328 // | | | |
|
329 // =========== |
|
330 // Lan0 |
|
331 // |
|
332 // - Multicast source is at node n0; |
|
333 // - Multicast forwarded by node n2 onto LAN1; |
|
334 // - Nodes n0, n1, n2, n3, and n4 receive the multicast frame. |
|
335 // - Node n4 listens for the data |
|
336 // |
|
337 bool |
|
338 CsmaMulticastTestCase::DoRun (void) |
|
339 { |
|
340 // |
|
341 // Set up default values for the simulation. |
|
342 // |
|
343 // Select DIX/Ethernet II-style encapsulation (no LLC/Snap header) |
|
344 Config::SetDefault ("ns3::CsmaNetDevice::EncapsulationMode", StringValue ("Dix")); |
|
345 |
|
346 NodeContainer c; |
|
347 c.Create (5); |
|
348 // We will later want two subcontainers of these nodes, for the two LANs |
|
349 NodeContainer c0 = NodeContainer (c.Get (0), c.Get (1), c.Get (2)); |
|
350 NodeContainer c1 = NodeContainer (c.Get (2), c.Get (3), c.Get (4)); |
|
351 |
|
352 CsmaHelper csma; |
|
353 csma.SetChannelAttribute ("DataRate", DataRateValue (DataRate (5000000))); |
|
354 csma.SetChannelAttribute ("Delay", TimeValue (MilliSeconds (2))); |
|
355 |
|
356 // We will use these NetDevice containers later, for IP addressing |
|
357 NetDeviceContainer nd0 = csma.Install (c0); // First LAN |
|
358 NetDeviceContainer nd1 = csma.Install (c1); // Second LAN |
|
359 |
|
360 InternetStackHelper internet; |
|
361 internet.Install (c); |
|
362 |
|
363 Ipv4AddressHelper ipv4Addr; |
|
364 ipv4Addr.SetBase ("10.1.1.0", "255.255.255.0"); |
|
365 ipv4Addr.Assign (nd0); |
|
366 ipv4Addr.SetBase ("10.1.2.0", "255.255.255.0"); |
|
367 ipv4Addr.Assign (nd1); |
|
368 |
|
369 // |
|
370 // Now we can configure multicasting. As described above, the multicast |
|
371 // source is at node zero, which we assigned the IP address of 10.1.1.1 |
|
372 // earlier. We need to define a multicast group to send packets to. This |
|
373 // can be any multicast address from 224.0.0.0 through 239.255.255.255 |
|
374 // (avoiding the reserved routing protocol addresses). |
|
375 // |
|
376 |
|
377 Ipv4Address multicastSource ("10.1.1.1"); |
|
378 Ipv4Address multicastGroup ("225.1.2.4"); |
|
379 |
|
380 // Now, we will set up multicast routing. We need to do three things: |
|
381 // 1) Configure a (static) multicast route on node n2 |
|
382 // 2) Set up a default multicast route on the sender n0 |
|
383 // 3) Have node n4 join the multicast group |
|
384 // We have a helper that can help us with static multicast |
|
385 Ipv4StaticRoutingHelper multicast; |
|
386 |
|
387 // 1) Configure a (static) multicast route on node n2 (multicastRouter) |
|
388 Ptr<Node> multicastRouter = c.Get (2); // The node in question |
|
389 Ptr<NetDevice> inputIf = nd0.Get (2); // The input NetDevice |
|
390 NetDeviceContainer outputDevices; // A container of output NetDevices |
|
391 outputDevices.Add (nd1.Get (0)); // (we only need one NetDevice here) |
|
392 |
|
393 multicast.AddMulticastRoute (multicastRouter, multicastSource, |
|
394 multicastGroup, inputIf, outputDevices); |
|
395 |
|
396 // 2) Set up a default multicast route on the sender n0 |
|
397 Ptr<Node> sender = c.Get (0); |
|
398 Ptr<NetDevice> senderIf = nd0.Get(0); |
|
399 multicast.SetDefaultMulticastRoute (sender, senderIf); |
|
400 |
|
401 // |
|
402 // Create an OnOff application to send UDP datagrams from node zero to the |
|
403 // multicast group (node four will be listening). |
|
404 // |
|
405 |
|
406 uint16_t multicastPort = 9; // Discard port (RFC 863) |
|
407 |
|
408 // Configure a multicast packet generator. |
|
409 // |
|
410 // Make packets be sent about every defaultPacketSize / dataRate = |
|
411 // 4096 bits / (5000 bits/second) = 0.82 second. |
|
412 OnOffHelper onoff ("ns3::UdpSocketFactory", |
|
413 Address (InetSocketAddress (multicastGroup, multicastPort))); |
|
414 onoff.SetAttribute ("OnTime", RandomVariableValue (ConstantVariable (1))); |
|
415 onoff.SetAttribute ("OffTime", RandomVariableValue (ConstantVariable (0))); |
|
416 onoff.SetAttribute ("DataRate", DataRateValue (DataRate (5000))); |
|
417 |
|
418 ApplicationContainer srcC = onoff.Install (c0.Get (0)); |
|
419 |
|
420 // |
|
421 // Tell the application when to start and stop. |
|
422 // |
|
423 srcC.Start(Seconds(1.)); |
|
424 srcC.Stop (Seconds(10.)); |
|
425 |
|
426 // Create an optional packet sink to receive these packets |
|
427 PacketSinkHelper sink ("ns3::UdpSocketFactory", |
|
428 InetSocketAddress (Ipv4Address::GetAny(), multicastPort)); |
|
429 |
|
430 ApplicationContainer sinkC = sink.Install (c1.Get (2)); // Node n4 |
|
431 // Start the sink |
|
432 sinkC.Start (Seconds (1.0)); |
|
433 sinkC.Stop (Seconds (10.0)); |
|
434 |
|
435 // Trace receptions |
|
436 Config::ConnectWithoutContext ("/NodeList/4/ApplicationList/0/$ns3::PacketSink/Rx", MakeCallback (&CsmaMulticastTestCase::SinkRx, this)); |
|
437 |
|
438 // |
|
439 // Now, do the actual simulation. |
|
440 // |
|
441 Simulator::Run (); |
|
442 Simulator::Destroy (); |
|
443 |
|
444 // We should have sent and received 10 packets |
|
445 NS_TEST_ASSERT_MSG_EQ (m_count, 10, "Node 4 should have received 10 packets"); |
|
446 |
|
447 return GetErrorStatus (); |
|
448 } |
|
449 |
|
450 class CsmaOneSubnetTestCase : public TestCase |
|
451 { |
|
452 public: |
|
453 CsmaOneSubnetTestCase (); |
|
454 virtual ~CsmaOneSubnetTestCase (); |
|
455 |
|
456 private: |
|
457 virtual bool DoRun (void); |
|
458 void SinkRxNode0 (Ptr<const Packet> p, const Address &ad); |
|
459 void SinkRxNode1 (Ptr<const Packet> p, const Address &ad); |
|
460 void DropEvent (Ptr<const Packet> p); |
|
461 uint32_t m_countNode0; |
|
462 uint32_t m_countNode1; |
|
463 uint32_t m_drops; |
|
464 }; |
|
465 |
|
466 // Add some help text to this case to describe what it is intended to test |
|
467 CsmaOneSubnetTestCase::CsmaOneSubnetTestCase () |
|
468 : TestCase ("One subnet example for Carrier Sense Multiple Access (CSMA) networks"), m_countNode0 (0), m_countNode1 (0), m_drops (0) |
|
469 { |
|
470 } |
|
471 |
|
472 CsmaOneSubnetTestCase::~CsmaOneSubnetTestCase () |
|
473 { |
|
474 } |
|
475 |
|
476 void |
|
477 CsmaOneSubnetTestCase::SinkRxNode0 (Ptr<const Packet> p, const Address &ad) |
|
478 { |
|
479 m_countNode0++; |
|
480 } |
|
481 |
|
482 void |
|
483 CsmaOneSubnetTestCase::SinkRxNode1 (Ptr<const Packet> p, const Address &ad) |
|
484 { |
|
485 m_countNode1++; |
|
486 } |
|
487 |
|
488 void |
|
489 CsmaOneSubnetTestCase::DropEvent (Ptr<const Packet> p) |
|
490 { |
|
491 m_drops++; |
|
492 } |
|
493 |
|
494 // Network topology |
|
495 // |
|
496 // n0 n1 n2 n3 |
|
497 // | | | | |
|
498 // ================= |
|
499 // LAN |
|
500 // |
|
501 // - CBR/UDP flows from n0 to n1 and from n3 to n0 |
|
502 // - DropTail queues |
|
503 // |
|
504 bool |
|
505 CsmaOneSubnetTestCase::DoRun (void) |
|
506 { |
|
507 NodeContainer nodes; |
|
508 nodes.Create (4); |
|
509 |
|
510 CsmaHelper csma; |
|
511 csma.SetChannelAttribute ("DataRate", DataRateValue (5000000)); |
|
512 csma.SetChannelAttribute ("Delay", TimeValue (MilliSeconds (2))); |
|
513 // |
|
514 // Now fill out the topology by creating the net devices required to connect |
|
515 // the nodes to the channels and hooking them up. |
|
516 // |
|
517 NetDeviceContainer devices = csma.Install (nodes); |
|
518 |
|
519 InternetStackHelper internet; |
|
520 internet.Install (nodes); |
|
521 |
|
522 // We've got the "hardware" in place. Now we need to add IP addresses. |
|
523 // |
|
524 Ipv4AddressHelper ipv4; |
|
525 ipv4.SetBase ("10.1.1.0", "255.255.255.0"); |
|
526 Ipv4InterfaceContainer interfaces = ipv4.Assign (devices); |
|
527 |
|
528 uint16_t port = 9; // Discard port (RFC 863) |
|
529 |
|
530 // |
|
531 // Create an OnOff application to send UDP datagrams from node zero |
|
532 // to node 1. |
|
533 // |
|
534 // Make packets be sent about every defaultPacketSize / dataRate = |
|
535 // 4096 bits / (5000 bits/second) = 0.82 second. |
|
536 OnOffHelper onoff ("ns3::UdpSocketFactory", |
|
537 Address (InetSocketAddress (interfaces.GetAddress (1), port))); |
|
538 onoff.SetAttribute ("OnTime", RandomVariableValue (ConstantVariable (1))); |
|
539 onoff.SetAttribute ("OffTime", RandomVariableValue (ConstantVariable (0))); |
|
540 onoff.SetAttribute ("DataRate", DataRateValue (DataRate (5000))); |
|
541 |
|
542 ApplicationContainer app = onoff.Install (nodes.Get (0)); |
|
543 // Start the application |
|
544 app.Start (Seconds (1.0)); |
|
545 app.Stop (Seconds (10.0)); |
|
546 |
|
547 // Create an optional packet sink to receive these packets |
|
548 PacketSinkHelper sink ("ns3::UdpSocketFactory", |
|
549 Address (InetSocketAddress (Ipv4Address::GetAny (), port))); |
|
550 app = sink.Install (nodes.Get (1)); |
|
551 app.Start (Seconds (0.0)); |
|
552 |
|
553 // |
|
554 // Create a similar flow from n3 to n0, starting at time 1.1 seconds |
|
555 // |
|
556 onoff.SetAttribute ("Remote", |
|
557 AddressValue (InetSocketAddress (interfaces.GetAddress (0), port))); |
|
558 app = onoff.Install (nodes.Get (3)); |
|
559 app.Start(Seconds (1.1)); |
|
560 app.Stop (Seconds (10.0)); |
|
561 |
|
562 app = sink.Install (nodes.Get (0)); |
|
563 app.Start (Seconds (0.0)); |
|
564 |
|
565 // Trace receptions |
|
566 Config::ConnectWithoutContext ("/NodeList/0/ApplicationList/1/$ns3::PacketSink/Rx", MakeCallback (&CsmaOneSubnetTestCase::SinkRxNode0, this)); |
|
567 Config::ConnectWithoutContext ("/NodeList/1/ApplicationList/0/$ns3::PacketSink/Rx", MakeCallback (&CsmaOneSubnetTestCase::SinkRxNode1, this)); |
|
568 |
|
569 // |
|
570 // Now, do the actual simulation. |
|
571 // |
|
572 Simulator::Run (); |
|
573 Simulator::Destroy (); |
|
574 |
|
575 // We should have sent and received 10 packets |
|
576 NS_TEST_ASSERT_MSG_EQ (m_countNode0, 10, "Node 0 should have received 10 packets"); |
|
577 NS_TEST_ASSERT_MSG_EQ (m_countNode1, 10, "Node 1 should have received 10 packets"); |
|
578 |
|
579 return GetErrorStatus (); |
|
580 } |
|
581 |
|
582 class CsmaPacketSocketTestCase : public TestCase |
|
583 { |
|
584 public: |
|
585 CsmaPacketSocketTestCase (); |
|
586 virtual ~CsmaPacketSocketTestCase (); |
|
587 |
|
588 private: |
|
589 virtual bool DoRun (void); |
|
590 void SinkRx (std::string path, Ptr<const Packet> p, const Address &address); |
|
591 void DropEvent (Ptr<const Packet> p); |
|
592 uint32_t m_count; |
|
593 uint32_t m_drops; |
|
594 }; |
|
595 |
|
596 // Add some help text to this case to describe what it is intended to test |
|
597 CsmaPacketSocketTestCase::CsmaPacketSocketTestCase () |
|
598 : TestCase ("Packet socket example for Carrier Sense Multiple Access (CSMA) networks"), m_count (0), m_drops (0) |
|
599 { |
|
600 } |
|
601 |
|
602 CsmaPacketSocketTestCase::~CsmaPacketSocketTestCase () |
|
603 { |
|
604 } |
|
605 |
|
606 void |
|
607 CsmaPacketSocketTestCase::SinkRx (std::string path, Ptr<const Packet> p, const Address& address) |
|
608 { |
|
609 m_count++; |
|
610 } |
|
611 |
|
612 void |
|
613 CsmaPacketSocketTestCase::DropEvent (Ptr<const Packet> p) |
|
614 { |
|
615 m_drops++; |
|
616 } |
|
617 |
|
618 // |
|
619 // Network topology |
|
620 // |
|
621 // n0 n1 n2 n3 |
|
622 // | | | | |
|
623 // ===================== |
|
624 // |
|
625 // - Packet socket flow from n0 to n1 and from node n3 to n0 |
|
626 // -- We will test reception at node n0 |
|
627 // - Default 512 byte packets generated by traffic generator |
|
628 // |
|
629 bool |
|
630 CsmaPacketSocketTestCase::DoRun (void) |
|
631 { |
|
632 // Here, we will explicitly create four nodes. |
|
633 NodeContainer nodes; |
|
634 nodes.Create (4); |
|
635 |
|
636 PacketSocketHelper packetSocket; |
|
637 packetSocket.Install (nodes); |
|
638 |
|
639 // create the shared medium used by all csma devices. |
|
640 Ptr<CsmaChannel> channel = CreateObjectWithAttributes<CsmaChannel> ( |
|
641 "DataRate", DataRateValue (DataRate(5000000)), |
|
642 "Delay", TimeValue (MilliSeconds(2))); |
|
643 |
|
644 // use a helper function to connect our nodes to the shared channel. |
|
645 CsmaHelper csma; |
|
646 csma.SetDeviceAttribute ("EncapsulationMode", StringValue ("Llc")); |
|
647 NetDeviceContainer devs = csma.Install (nodes, channel); |
|
648 |
|
649 // Create the OnOff application to send raw datagrams |
|
650 // |
|
651 // Make packets be sent about every DefaultPacketSize / DataRate = |
|
652 // 4096 bits / (5000 bits/second) = 0.82 second. |
|
653 PacketSocketAddress socket; |
|
654 socket.SetSingleDevice(devs.Get (0)->GetIfIndex ()); |
|
655 socket.SetPhysicalAddress (devs.Get (1)->GetAddress ()); |
|
656 socket.SetProtocol (2); |
|
657 OnOffHelper onoff ("ns3::PacketSocketFactory", Address (socket)); |
|
658 onoff.SetAttribute ("OnTime", RandomVariableValue (ConstantVariable (1.0))); |
|
659 onoff.SetAttribute ("OffTime", RandomVariableValue (ConstantVariable (0.0))); |
|
660 onoff.SetAttribute ("DataRate", DataRateValue (DataRate (5000))); |
|
661 ApplicationContainer apps = onoff.Install (nodes.Get (0)); |
|
662 apps.Start (Seconds (1.0)); |
|
663 apps.Stop (Seconds (10.0)); |
|
664 |
|
665 socket.SetSingleDevice (devs.Get (3)->GetIfIndex ()); |
|
666 socket.SetPhysicalAddress (devs.Get (0)->GetAddress ()); |
|
667 socket.SetProtocol (3); |
|
668 onoff.SetAttribute ("Remote", AddressValue (socket)); |
|
669 onoff.SetAttribute ("OffTime", RandomVariableValue (ConstantVariable (0.0))); |
|
670 apps = onoff.Install (nodes.Get (3)); |
|
671 apps.Start (Seconds (1.0)); |
|
672 apps.Stop (Seconds (10.0)); |
|
673 |
|
674 PacketSinkHelper sink = PacketSinkHelper ("ns3::PacketSocketFactory", |
|
675 socket); |
|
676 apps = sink.Install (nodes.Get (0)); |
|
677 apps.Start (Seconds (0.0)); |
|
678 apps.Stop (Seconds (20.0)); |
|
679 |
|
680 // Trace receptions |
|
681 Config::Connect ("/NodeList/0/ApplicationList/*/$ns3::PacketSink/Rx", |
|
682 MakeCallback (&CsmaPacketSocketTestCase::SinkRx, this)); |
|
683 |
|
684 Simulator::Run (); |
|
685 Simulator::Destroy (); |
|
686 |
|
687 // We should have received 10 packets on node 0 |
|
688 NS_TEST_ASSERT_MSG_EQ (m_count, 10, "Node 0 should have received 10 packets"); |
|
689 |
|
690 return GetErrorStatus (); |
|
691 } |
|
692 |
|
693 class CsmaPingTestCase : public TestCase |
|
694 { |
|
695 public: |
|
696 CsmaPingTestCase (); |
|
697 virtual ~CsmaPingTestCase (); |
|
698 |
|
699 private: |
|
700 virtual bool DoRun (void); |
|
701 void SinkRx (Ptr<const Packet> p, const Address &ad); |
|
702 void PingRtt (std::string context, Time rtt); |
|
703 void DropEvent (Ptr<const Packet> p); |
|
704 uint32_t m_countSinkRx; |
|
705 uint32_t m_countPingRtt; |
|
706 uint32_t m_drops; |
|
707 }; |
|
708 |
|
709 // Add some help text to this case to describe what it is intended to test |
|
710 CsmaPingTestCase::CsmaPingTestCase () |
|
711 : TestCase ("Ping example for Carrier Sense Multiple Access (CSMA) networks"), m_countSinkRx (0), m_countPingRtt (0), m_drops (0) |
|
712 { |
|
713 } |
|
714 |
|
715 CsmaPingTestCase::~CsmaPingTestCase () |
|
716 { |
|
717 } |
|
718 |
|
719 void |
|
720 CsmaPingTestCase::SinkRx (Ptr<const Packet> p, const Address &ad) |
|
721 { |
|
722 m_countSinkRx++; |
|
723 } |
|
724 |
|
725 void |
|
726 CsmaPingTestCase::PingRtt (std::string context, Time rtt) |
|
727 { |
|
728 m_countPingRtt++; |
|
729 } |
|
730 |
|
731 void |
|
732 CsmaPingTestCase::DropEvent (Ptr<const Packet> p) |
|
733 { |
|
734 m_drops++; |
|
735 } |
|
736 |
|
737 // Network topology |
|
738 // |
|
739 // n0 n1 n2 n3 |
|
740 // | | | | |
|
741 // ===================== |
|
742 // |
|
743 // node n0,n1,n3 pings to node n2 |
|
744 // node n0 generates protocol 2 (IGMP) to node n3 |
|
745 // |
|
746 bool |
|
747 CsmaPingTestCase::DoRun (void) |
|
748 { |
|
749 // Here, we will explicitly create four nodes. |
|
750 NodeContainer c; |
|
751 c.Create (4); |
|
752 |
|
753 // connect all our nodes to a shared channel. |
|
754 CsmaHelper csma; |
|
755 csma.SetChannelAttribute ("DataRate", DataRateValue (DataRate (5000000))); |
|
756 csma.SetChannelAttribute ("Delay", TimeValue (MilliSeconds (2))); |
|
757 csma.SetDeviceAttribute ("EncapsulationMode", StringValue ("Llc")); |
|
758 NetDeviceContainer devs = csma.Install (c); |
|
759 |
|
760 // add an ip stack to all nodes. |
|
761 InternetStackHelper ipStack; |
|
762 ipStack.Install (c); |
|
763 |
|
764 // assign ip addresses |
|
765 Ipv4AddressHelper ip; |
|
766 ip.SetBase ("192.168.1.0", "255.255.255.0"); |
|
767 Ipv4InterfaceContainer addresses = ip.Assign (devs); |
|
768 |
|
769 // Create the OnOff application to send UDP datagrams from n0 to n1. |
|
770 // |
|
771 // Make packets be sent about every DefaultPacketSize / DataRate = |
|
772 // 4096 bits / (5000 bits/second) = 0.82 second. |
|
773 Config::SetDefault ("ns3::Ipv4RawSocketImpl::Protocol", StringValue ("2")); |
|
774 InetSocketAddress dst = InetSocketAddress (addresses.GetAddress (3)); |
|
775 OnOffHelper onoff = OnOffHelper ("ns3::Ipv4RawSocketFactory", dst); |
|
776 onoff.SetAttribute ("OnTime", RandomVariableValue (ConstantVariable (1.0))); |
|
777 onoff.SetAttribute ("OffTime", RandomVariableValue (ConstantVariable (0.0))); |
|
778 onoff.SetAttribute ("DataRate", DataRateValue (DataRate (5000))); |
|
779 |
|
780 ApplicationContainer apps = onoff.Install (c.Get (0)); |
|
781 apps.Start (Seconds (1.0)); |
|
782 apps.Stop (Seconds (10.0)); |
|
783 |
|
784 PacketSinkHelper sink = PacketSinkHelper ("ns3::Ipv4RawSocketFactory", dst); |
|
785 apps = sink.Install (c.Get (3)); |
|
786 apps.Start (Seconds (0.0)); |
|
787 apps.Stop (Seconds (11.0)); |
|
788 |
|
789 V4PingHelper ping = V4PingHelper (addresses.GetAddress (2)); |
|
790 NodeContainer pingers; |
|
791 pingers.Add (c.Get (0)); |
|
792 pingers.Add (c.Get (1)); |
|
793 pingers.Add (c.Get (3)); |
|
794 apps = ping.Install (pingers); |
|
795 apps.Start (Seconds (2.0)); |
|
796 apps.Stop (Seconds (5.0)); |
|
797 |
|
798 // Trace receptions |
|
799 Config::ConnectWithoutContext ("/NodeList/3/ApplicationList/0/$ns3::PacketSink/Rx", |
|
800 MakeCallback (&CsmaPingTestCase::SinkRx, this)); |
|
801 |
|
802 // Trace pings |
|
803 Config::Connect ("/NodeList/*/ApplicationList/*/$ns3::V4Ping/Rtt", |
|
804 MakeCallback (&CsmaPingTestCase::PingRtt, this)); |
|
805 |
|
806 Simulator::Run (); |
|
807 Simulator::Destroy (); |
|
808 |
|
809 // We should have sent and received 10 packets |
|
810 NS_TEST_ASSERT_MSG_EQ (m_countSinkRx, 10, "Node 3 should have received 10 packets"); |
|
811 |
|
812 // We should have 3 pingers that ping every second for 3 seconds. |
|
813 NS_TEST_ASSERT_MSG_EQ (m_countPingRtt, 9, "Node 2 should have been pinged 9 times"); |
|
814 |
|
815 return GetErrorStatus (); |
|
816 } |
|
817 |
|
818 class CsmaRawIpSocketTestCase : public TestCase |
|
819 { |
|
820 public: |
|
821 CsmaRawIpSocketTestCase (); |
|
822 virtual ~CsmaRawIpSocketTestCase (); |
|
823 |
|
824 private: |
|
825 virtual bool DoRun (void); |
|
826 void SinkRx (Ptr<const Packet> p, const Address &ad); |
|
827 void DropEvent (Ptr<const Packet> p); |
|
828 uint32_t m_count; |
|
829 uint32_t m_drops; |
|
830 }; |
|
831 |
|
832 // Add some help text to this case to describe what it is intended to test |
|
833 CsmaRawIpSocketTestCase::CsmaRawIpSocketTestCase () |
|
834 : TestCase ("Raw internet protocol socket example for Carrier Sense Multiple Access (CSMA) networks"), m_count (0), m_drops (0) |
|
835 { |
|
836 } |
|
837 |
|
838 CsmaRawIpSocketTestCase::~CsmaRawIpSocketTestCase () |
|
839 { |
|
840 } |
|
841 |
|
842 void |
|
843 CsmaRawIpSocketTestCase::SinkRx (Ptr<const Packet> p, const Address &ad) |
|
844 { |
|
845 m_count++; |
|
846 } |
|
847 |
|
848 void |
|
849 CsmaRawIpSocketTestCase::DropEvent (Ptr<const Packet> p) |
|
850 { |
|
851 m_drops++; |
|
852 } |
|
853 |
|
854 // |
|
855 // Network topology |
|
856 // (sender) (receiver) |
|
857 // n0 n1 n2 n3 |
|
858 // | | | | |
|
859 // ===================== |
|
860 // |
|
861 // Node n0 sends data to node n3 over a raw IP socket. The protocol |
|
862 // number used is 2. |
|
863 // |
|
864 bool |
|
865 CsmaRawIpSocketTestCase::DoRun (void) |
|
866 { |
|
867 // Here, we will explicitly create four nodes. |
|
868 NodeContainer c; |
|
869 c.Create (4); |
|
870 |
|
871 // connect all our nodes to a shared channel. |
|
872 CsmaHelper csma; |
|
873 csma.SetChannelAttribute ("DataRate", DataRateValue (DataRate (5000000))); |
|
874 csma.SetChannelAttribute ("Delay", TimeValue (MilliSeconds (2))); |
|
875 csma.SetDeviceAttribute ("EncapsulationMode", StringValue ("Llc")); |
|
876 NetDeviceContainer devs = csma.Install (c); |
|
877 |
|
878 // add an ip stack to all nodes. |
|
879 InternetStackHelper ipStack; |
|
880 ipStack.Install (c); |
|
881 |
|
882 // assign ip addresses |
|
883 Ipv4AddressHelper ip; |
|
884 ip.SetBase ("192.168.1.0", "255.255.255.0"); |
|
885 Ipv4InterfaceContainer addresses = ip.Assign (devs); |
|
886 |
|
887 // IP protocol configuration |
|
888 // |
|
889 // Make packets be sent about every DefaultPacketSize / DataRate = |
|
890 // 4096 bits / (5000 bits/second) = 0.82 second. |
|
891 Config::SetDefault ("ns3::Ipv4RawSocketImpl::Protocol", StringValue ("2")); |
|
892 InetSocketAddress dst = InetSocketAddress (addresses.GetAddress (3)); |
|
893 OnOffHelper onoff = OnOffHelper ("ns3::Ipv4RawSocketFactory", dst); |
|
894 onoff.SetAttribute ("OnTime", RandomVariableValue (ConstantVariable (1.0))); |
|
895 onoff.SetAttribute ("OffTime", RandomVariableValue (ConstantVariable (0.0))); |
|
896 onoff.SetAttribute ("DataRate", DataRateValue (DataRate (5000))); |
|
897 |
|
898 ApplicationContainer apps = onoff.Install (c.Get (0)); |
|
899 apps.Start (Seconds (1.0)); |
|
900 apps.Stop (Seconds (10.0)); |
|
901 |
|
902 PacketSinkHelper sink = PacketSinkHelper ("ns3::Ipv4RawSocketFactory", dst); |
|
903 apps = sink.Install (c.Get (3)); |
|
904 apps.Start (Seconds (0.0)); |
|
905 apps.Stop (Seconds (12.0)); |
|
906 |
|
907 // Trace receptions |
|
908 Config::ConnectWithoutContext ("/NodeList/3/ApplicationList/0/$ns3::PacketSink/Rx", |
|
909 MakeCallback (&CsmaRawIpSocketTestCase::SinkRx, this)); |
|
910 |
|
911 Simulator::Run (); |
|
912 Simulator::Destroy (); |
|
913 |
|
914 // We should have sent and received 10 packets |
|
915 NS_TEST_ASSERT_MSG_EQ (m_count, 10, "Node 3 should have received 10 packets"); |
|
916 |
|
917 return GetErrorStatus (); |
|
918 } |
|
919 |
|
920 class CsmaStarTestCase : public TestCase |
|
921 { |
|
922 public: |
|
923 CsmaStarTestCase (); |
|
924 virtual ~CsmaStarTestCase (); |
|
925 |
|
926 private: |
|
927 virtual bool DoRun (void); |
|
928 void SinkRx (Ptr<const Packet> p, const Address &ad); |
|
929 void DropEvent (Ptr<const Packet> p); |
|
930 uint32_t m_count; |
|
931 uint32_t m_drops; |
|
932 }; |
|
933 |
|
934 // Add some help text to this case to describe what it is intended to test |
|
935 CsmaStarTestCase::CsmaStarTestCase () |
|
936 : TestCase ("Star example for Carrier Sense Multiple Access (CSMA) networks"), m_count (0), m_drops (0) |
|
937 { |
|
938 } |
|
939 |
|
940 CsmaStarTestCase::~CsmaStarTestCase () |
|
941 { |
|
942 } |
|
943 |
|
944 void |
|
945 CsmaStarTestCase::SinkRx (Ptr<const Packet> p, const Address& ad) |
|
946 { |
|
947 m_count++; |
|
948 } |
|
949 |
|
950 void |
|
951 CsmaStarTestCase::DropEvent (Ptr<const Packet> p) |
|
952 { |
|
953 m_drops++; |
|
954 } |
|
955 |
|
956 // Network topology (default) |
|
957 // |
|
958 // n2 + + n3 . |
|
959 // | ... |\ /| ... | . |
|
960 // ======= \ / ======= . |
|
961 // CSMA \ / CSMA . |
|
962 // \ / . |
|
963 // n1 +--- n0 ---+ n4 . |
|
964 // | ... | / \ | ... | . |
|
965 // ======= / \ ======= . |
|
966 // CSMA / \ CSMA . |
|
967 // / \ . |
|
968 // n6 + + n5 . |
|
969 // | ... | | ... | . |
|
970 // ======= ======= . |
|
971 // CSMA CSMA . |
|
972 // |
|
973 bool |
|
974 CsmaStarTestCase::DoRun (void) |
|
975 { |
|
976 // |
|
977 // Default number of nodes in the star. |
|
978 // |
|
979 uint32_t nSpokes = 7; |
|
980 |
|
981 CsmaHelper csma; |
|
982 csma.SetChannelAttribute ("DataRate", StringValue ("100Mbps")); |
|
983 csma.SetChannelAttribute ("Delay", StringValue ("1ms")); |
|
984 CsmaStarHelper star (nSpokes, csma); |
|
985 |
|
986 NodeContainer fillNodes; |
|
987 |
|
988 // |
|
989 // Just to be nasy, hang some more nodes off of the CSMA channel for each |
|
990 // spoke, so that there are a total of 16 nodes on each channel. Stash |
|
991 // all of these new devices into a container. |
|
992 // |
|
993 NetDeviceContainer fillDevices; |
|
994 |
|
995 uint32_t nFill = 14; |
|
996 for (uint32_t i = 0; i < star.GetSpokeDevices ().GetN (); ++i) |
|
997 { |
|
998 Ptr<Channel> channel = star.GetSpokeDevices ().Get (i)->GetChannel (); |
|
999 Ptr<CsmaChannel> csmaChannel = channel->GetObject<CsmaChannel> (); |
|
1000 NodeContainer newNodes; |
|
1001 newNodes.Create (nFill); |
|
1002 fillNodes.Add (newNodes); |
|
1003 fillDevices.Add (csma.Install (newNodes, csmaChannel)); |
|
1004 } |
|
1005 |
|
1006 InternetStackHelper internet; |
|
1007 star.InstallStack (internet); |
|
1008 internet.Install (fillNodes); |
|
1009 |
|
1010 star.AssignIpv4Addresses (Ipv4AddressHelper ("10.1.0.0", "255.255.255.0")); |
|
1011 |
|
1012 // |
|
1013 // We assigned addresses to the logical hub and the first "drop" of the |
|
1014 // CSMA network that acts as the spoke, but we also have a number of fill |
|
1015 // devices (nFill) also hanging off the CSMA network. We have got to |
|
1016 // assign addresses to them as well. We put all of the fill devices into |
|
1017 // a single device container, so the first nFill devices are associated |
|
1018 // with the channel connected to spokeDevices.Get (0), the second nFill |
|
1019 // devices afe associated with the channel connected to spokeDevices.Get (1) |
|
1020 // etc. |
|
1021 // |
|
1022 Ipv4AddressHelper address; |
|
1023 for(uint32_t i = 0; i < star.SpokeCount (); ++i) |
|
1024 { |
|
1025 std::ostringstream subnet; |
|
1026 subnet << "10.1." << i << ".0"; |
|
1027 address.SetBase (subnet.str ().c_str (), "255.255.255.0", "0.0.0.3"); |
|
1028 |
|
1029 for (uint32_t j = 0; j < nFill; ++j) |
|
1030 { |
|
1031 address.Assign (fillDevices.Get (i * nFill + j)); |
|
1032 } |
|
1033 } |
|
1034 |
|
1035 // |
|
1036 // Create a packet sink on the star "hub" to receive packets. |
|
1037 // |
|
1038 uint16_t port = 50000; |
|
1039 Address hubLocalAddress (InetSocketAddress (Ipv4Address::GetAny (), port)); |
|
1040 PacketSinkHelper packetSinkHelper ("ns3::TcpSocketFactory", hubLocalAddress); |
|
1041 ApplicationContainer hubApp = packetSinkHelper.Install (star.GetHub ()); |
|
1042 hubApp.Start (Seconds (1.0)); |
|
1043 hubApp.Stop (Seconds (10.0)); |
|
1044 |
|
1045 // |
|
1046 // Create OnOff applications to send TCP to the hub, one on each spoke node. |
|
1047 // |
|
1048 // Make packets be sent about every DefaultPacketSize / DataRate = |
|
1049 // 4096 bits / (5000 bits/second) = 0.82 second. |
|
1050 OnOffHelper onOffHelper ("ns3::TcpSocketFactory", Address ()); |
|
1051 onOffHelper.SetAttribute ("OnTime", RandomVariableValue (ConstantVariable (1))); |
|
1052 onOffHelper.SetAttribute ("OffTime", RandomVariableValue (ConstantVariable (0))); |
|
1053 onOffHelper.SetAttribute ("DataRate", DataRateValue (DataRate (5000))); |
|
1054 |
|
1055 ApplicationContainer spokeApps; |
|
1056 |
|
1057 for (uint32_t i = 0; i < star.SpokeCount (); ++i) |
|
1058 { |
|
1059 AddressValue remoteAddress (InetSocketAddress (star.GetHubIpv4Address (i), port)); |
|
1060 onOffHelper.SetAttribute ("Remote", remoteAddress); |
|
1061 spokeApps.Add (onOffHelper.Install (star.GetSpokeNode (i))); |
|
1062 } |
|
1063 |
|
1064 spokeApps.Start (Seconds (1.0)); |
|
1065 spokeApps.Stop (Seconds (10.0)); |
|
1066 |
|
1067 // |
|
1068 // Because we are evil, we also add OnOff applications to send TCP to the hub |
|
1069 // from the fill devices on each CSMA link. The first nFill nodes in the |
|
1070 // fillNodes container are on the CSMA network talking to the zeroth device |
|
1071 // on the hub node. The next nFill nodes are on the CSMA network talking to |
|
1072 // the first device on the hub node, etc. So the ith fillNode is associated |
|
1073 // with the hub address found on the (i / nFill)th device on the hub node. |
|
1074 // |
|
1075 ApplicationContainer fillApps; |
|
1076 |
|
1077 for (uint32_t i = 0; i < fillNodes.GetN (); ++i) |
|
1078 { |
|
1079 AddressValue remoteAddress (InetSocketAddress (star.GetHubIpv4Address (i / nFill), port)); |
|
1080 onOffHelper.SetAttribute ("Remote", remoteAddress); |
|
1081 fillApps.Add (onOffHelper.Install (fillNodes.Get (i))); |
|
1082 } |
|
1083 |
|
1084 fillApps.Start (Seconds (1.0)); |
|
1085 fillApps.Stop (Seconds (10.0)); |
|
1086 |
|
1087 // |
|
1088 // Turn on global static routing so we can actually be routed across the star. |
|
1089 // |
|
1090 Ipv4GlobalRoutingHelper::PopulateRoutingTables (); |
|
1091 |
|
1092 // Trace receptions |
|
1093 Config::ConnectWithoutContext ("/NodeList/0/ApplicationList/*/$ns3::PacketSink/Rx", |
|
1094 MakeCallback (&CsmaStarTestCase::SinkRx, this)); |
|
1095 |
|
1096 Simulator::Run (); |
|
1097 Simulator::Destroy (); |
|
1098 |
|
1099 // The hub node should have received 10 packets from the nFill + 1 |
|
1100 // nodes on each spoke. |
|
1101 NS_TEST_ASSERT_MSG_EQ (m_count, 10 * ( nSpokes * (nFill + 1)), "Hub node did not receive the proper number of packets"); |
|
1102 |
|
1103 return GetErrorStatus (); |
|
1104 } |
|
1105 |
|
1106 class CsmaSystemTestSuite : public TestSuite |
|
1107 { |
|
1108 public: |
|
1109 CsmaSystemTestSuite (); |
|
1110 }; |
|
1111 |
|
1112 CsmaSystemTestSuite::CsmaSystemTestSuite () |
|
1113 : TestSuite ("csma-system", BVT) |
|
1114 { |
|
1115 AddTestCase (new CsmaBridgeTestCase); |
|
1116 AddTestCase (new CsmaBroadcastTestCase); |
|
1117 AddTestCase (new CsmaMulticastTestCase); |
|
1118 AddTestCase (new CsmaOneSubnetTestCase); |
|
1119 AddTestCase (new CsmaPacketSocketTestCase); |
|
1120 AddTestCase (new CsmaPingTestCase); |
|
1121 AddTestCase (new CsmaRawIpSocketTestCase); |
|
1122 AddTestCase (new CsmaStarTestCase); |
|
1123 } |
|
1124 |
|
1125 // Do not forget to allocate an instance of this TestSuite |
|
1126 static CsmaSystemTestSuite csmaSystemTestSuite; |