A Discrete-Event Network Simulator
API
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Properties Friends Macros Groups Pages
udp-test.cc
Go to the documentation of this file.
1 /* -*- Mode:C++; c-file-style:"gnu"; indent-tabs-mode:nil; -*- */
2 /*
3  * Copyright (c) 2007 Georgia Tech Research Corporation
4  *
5  * This program is free software; you can redistribute it and/or modify
6  * it under the terms of the GNU General Public License version 2 as
7  * published by the Free Software Foundation;
8  *
9  * This program is distributed in the hope that it will be useful,
10  * but WITHOUT ANY WARRANTY; without even the implied warranty of
11  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12  * GNU General Public License for more details.
13  *
14  * You should have received a copy of the GNU General Public License
15  * along with this program; if not, write to the Free Software
16  * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
17  *
18  * Author: Raj Bhattacharjea <raj.b@gatech.edu>
19  */
25 #include "ns3/test.h"
26 #include "ns3/socket-factory.h"
27 #include "ns3/udp-socket-factory.h"
28 #include "ns3/simulator.h"
29 #include "ns3/simple-channel.h"
30 #include "ns3/simple-net-device.h"
31 #include "ns3/drop-tail-queue.h"
32 #include "ns3/socket.h"
33 
34 #include "ns3/log.h"
35 #include "ns3/node.h"
36 #include "ns3/inet-socket-address.h"
37 #include "ns3/inet6-socket-address.h"
38 
39 #include "ns3/arp-l3-protocol.h"
40 #include "ns3/ipv4-l3-protocol.h"
41 #include "ns3/ipv6-l3-protocol.h"
42 #include "ns3/icmpv4-l4-protocol.h"
43 #include "ns3/icmpv6-l4-protocol.h"
44 #include "ns3/udp-l4-protocol.h"
45 #include "ns3/tcp-l4-protocol.h"
46 #include "ns3/ipv4-list-routing.h"
47 #include "ns3/ipv4-static-routing.h"
48 #include "ns3/ipv6-list-routing.h"
49 #include "ns3/ipv6-static-routing.h"
50 
51 #include <string>
52 #include <limits>
53 namespace ns3 {
54 
55 static void
57 {
58  //ARP
59  Ptr<ArpL3Protocol> arp = CreateObject<ArpL3Protocol> ();
60  node->AggregateObject (arp);
61  //IPV4
62  Ptr<Ipv4L3Protocol> ipv4 = CreateObject<Ipv4L3Protocol> ();
63  //Routing for Ipv4
64  Ptr<Ipv4ListRouting> ipv4Routing = CreateObject<Ipv4ListRouting> ();
65  ipv4->SetRoutingProtocol (ipv4Routing);
66  Ptr<Ipv4StaticRouting> ipv4staticRouting = CreateObject<Ipv4StaticRouting> ();
67  ipv4Routing->AddRoutingProtocol (ipv4staticRouting, 0);
68  node->AggregateObject (ipv4);
69  //ICMP
70  Ptr<Icmpv4L4Protocol> icmp = CreateObject<Icmpv4L4Protocol> ();
71  node->AggregateObject (icmp);
72  //UDP
73  Ptr<UdpL4Protocol> udp = CreateObject<UdpL4Protocol> ();
74  node->AggregateObject (udp);
75  //TCP
76  Ptr<TcpL4Protocol> tcp = CreateObject<TcpL4Protocol> ();
77  node->AggregateObject (tcp);
78 }
79 
80 static void
82 {
83  //IPV6
84  Ptr<Ipv6L3Protocol> ipv6 = CreateObject<Ipv6L3Protocol> ();
85  //Routing for Ipv6
86  Ptr<Ipv6ListRouting> ipv6Routing = CreateObject<Ipv6ListRouting> ();
87  ipv6->SetRoutingProtocol (ipv6Routing);
88  Ptr<Ipv6StaticRouting> ipv6staticRouting = CreateObject<Ipv6StaticRouting> ();
89  ipv6Routing->AddRoutingProtocol (ipv6staticRouting, 0);
90  node->AggregateObject (ipv6);
91  //ICMP
92  Ptr<Icmpv6L4Protocol> icmp = CreateObject<Icmpv6L4Protocol> ();
93  node->AggregateObject (icmp);
94  //Ipv6 Extensions
95  ipv6->RegisterExtensions ();
96  ipv6->RegisterOptions ();
97  //UDP
98  Ptr<UdpL4Protocol> udp = CreateObject<UdpL4Protocol> ();
99  node->AggregateObject (udp);
100  //TCP
101  Ptr<TcpL4Protocol> tcp = CreateObject<TcpL4Protocol> ();
102  node->AggregateObject (tcp);
103 }
104 
105 
107 {
108 public:
110  virtual void DoRun (void);
111 
112  void ReceivePkt (Ptr<Socket> socket);
114 };
115 
117  : TestCase ("UDP loopback test")
118 {
119 }
120 
122 {
123  uint32_t availableData;
124  availableData = socket->GetRxAvailable ();
125  m_receivedPacket = socket->Recv (std::numeric_limits<uint32_t>::max (), 0);
126  NS_ASSERT (availableData == m_receivedPacket->GetSize ());
127 }
128 
129 void
131 {
132  Ptr<Node> rxNode = CreateObject<Node> ();
133  AddInternetStack (rxNode);
134 
135  Ptr<SocketFactory> rxSocketFactory = rxNode->GetObject<UdpSocketFactory> ();
136  Ptr<Socket> rxSocket = rxSocketFactory->CreateSocket ();
137  rxSocket->Bind (InetSocketAddress (Ipv4Address::GetAny (), 80));
138  rxSocket->SetRecvCallback (MakeCallback (&UdpSocketLoopbackTest::ReceivePkt, this));
139 
140  Ptr<Socket> txSocket = rxSocketFactory->CreateSocket ();
141  txSocket->SendTo (Create<Packet> (246), 0, InetSocketAddress ("127.0.0.1", 80));
142  Simulator::Run ();
144  NS_TEST_EXPECT_MSG_EQ (m_receivedPacket->GetSize (), 246, "first socket should not receive it (it is bound specifically to the second interface's address");
145 }
146 
148 {
149 public:
151  virtual void DoRun (void);
152 
153  void ReceivePkt (Ptr<Socket> socket);
155 };
156 
158  : TestCase ("UDP6 loopback test")
159 {
160 }
161 
163 {
164  uint32_t availableData;
165  availableData = socket->GetRxAvailable ();
166  m_receivedPacket = socket->Recv (std::numeric_limits<uint32_t>::max (), 0);
167  NS_ASSERT (availableData == m_receivedPacket->GetSize ());
168  //cast availableData to void, to suppress 'availableData' set but not used
169  //compiler warning
170  (void) availableData;
171 }
172 
173 void
175 {
176  Ptr<Node> rxNode = CreateObject<Node> ();
177  AddInternetStack6 (rxNode);
178 
179  Ptr<SocketFactory> rxSocketFactory = rxNode->GetObject<UdpSocketFactory> ();
180  Ptr<Socket> rxSocket = rxSocketFactory->CreateSocket ();
181  rxSocket->Bind (Inet6SocketAddress (Ipv6Address::GetAny (), 80));
182  rxSocket->SetRecvCallback (MakeCallback (&Udp6SocketLoopbackTest::ReceivePkt, this));
183 
184  Ptr<Socket> txSocket = rxSocketFactory->CreateSocket ();
185  txSocket->SendTo (Create<Packet> (246), 0, Inet6SocketAddress ("::1", 80));
186  Simulator::Run ();
188  NS_TEST_EXPECT_MSG_EQ (m_receivedPacket->GetSize (), 246, "first socket should not receive it (it is bound specifically to the second interface's address");
189 }
190 
192 {
195  void DoSendData (Ptr<Socket> socket, std::string to);
196  void SendData (Ptr<Socket> socket, std::string to);
197 
198 public:
199  virtual void DoRun (void);
201 
202  void ReceivePacket (Ptr<Socket> socket, Ptr<Packet> packet, const Address &from);
203  void ReceivePacket2 (Ptr<Socket> socket, Ptr<Packet> packet, const Address &from);
204  void ReceivePkt (Ptr<Socket> socket);
205  void ReceivePkt2 (Ptr<Socket> socket);
206 };
207 
209  : TestCase ("UDP socket implementation")
210 {
211 }
212 
214 {
215  m_receivedPacket = packet;
216 }
217 
219 {
220  m_receivedPacket2 = packet;
221 }
222 
224 {
225  uint32_t availableData;
226  availableData = socket->GetRxAvailable ();
227  m_receivedPacket = socket->Recv (std::numeric_limits<uint32_t>::max (), 0);
228  NS_ASSERT (availableData == m_receivedPacket->GetSize ());
229 }
230 
232 {
233  uint32_t availableData;
234  availableData = socket->GetRxAvailable ();
235  m_receivedPacket2 = socket->Recv (std::numeric_limits<uint32_t>::max (), 0);
236  NS_ASSERT (availableData == m_receivedPacket2->GetSize ());
237 }
238 
239 void
241 {
242  Address realTo = InetSocketAddress (Ipv4Address (to.c_str ()), 1234);
243  NS_TEST_EXPECT_MSG_EQ (socket->SendTo (Create<Packet> (123), 0, realTo),
244  123, "XXX");
245 }
246 
247 void
248 UdpSocketImplTest::SendData (Ptr<Socket> socket, std::string to)
249 {
250  m_receivedPacket = Create<Packet> ();
251  m_receivedPacket2 = Create<Packet> ();
253  &UdpSocketImplTest::DoSendData, this, socket, to);
254  Simulator::Run ();
255 }
256 
257 void
259 {
260  // Create topology
261 
262  // Receiver Node
263  Ptr<Node> rxNode = CreateObject<Node> ();
264  AddInternetStack (rxNode);
265  Ptr<SimpleNetDevice> rxDev1, rxDev2;
266  { // first interface
267  rxDev1 = CreateObject<SimpleNetDevice> ();
269  rxNode->AddDevice (rxDev1);
270  Ptr<Ipv4> ipv4 = rxNode->GetObject<Ipv4> ();
271  uint32_t netdev_idx = ipv4->AddInterface (rxDev1);
272  Ipv4InterfaceAddress ipv4Addr = Ipv4InterfaceAddress (Ipv4Address ("10.0.0.1"), Ipv4Mask (0xffff0000U));
273  ipv4->AddAddress (netdev_idx, ipv4Addr);
274  ipv4->SetUp (netdev_idx);
275  }
276 
277  { // second interface
278  rxDev2 = CreateObject<SimpleNetDevice> ();
280  rxNode->AddDevice (rxDev2);
281  Ptr<Ipv4> ipv4 = rxNode->GetObject<Ipv4> ();
282  uint32_t netdev_idx = ipv4->AddInterface (rxDev2);
283  Ipv4InterfaceAddress ipv4Addr = Ipv4InterfaceAddress (Ipv4Address ("10.0.1.1"), Ipv4Mask (0xffff0000U));
284  ipv4->AddAddress (netdev_idx, ipv4Addr);
285  ipv4->SetUp (netdev_idx);
286  }
287 
288  // Sender Node
289  Ptr<Node> txNode = CreateObject<Node> ();
290  AddInternetStack (txNode);
291  Ptr<SimpleNetDevice> txDev1;
292  {
293  txDev1 = CreateObject<SimpleNetDevice> ();
295  txNode->AddDevice (txDev1);
296  Ptr<Ipv4> ipv4 = txNode->GetObject<Ipv4> ();
297  uint32_t netdev_idx = ipv4->AddInterface (txDev1);
298  Ipv4InterfaceAddress ipv4Addr = Ipv4InterfaceAddress (Ipv4Address ("10.0.0.2"), Ipv4Mask (0xffff0000U));
299  ipv4->AddAddress (netdev_idx, ipv4Addr);
300  ipv4->SetUp (netdev_idx);
301  }
302  Ptr<SimpleNetDevice> txDev2;
303  {
304  txDev2 = CreateObject<SimpleNetDevice> ();
306  txNode->AddDevice (txDev2);
307  Ptr<Ipv4> ipv4 = txNode->GetObject<Ipv4> ();
308  uint32_t netdev_idx = ipv4->AddInterface (txDev2);
309  Ipv4InterfaceAddress ipv4Addr = Ipv4InterfaceAddress (Ipv4Address ("10.0.1.2"), Ipv4Mask (0xffff0000U));
310  ipv4->AddAddress (netdev_idx, ipv4Addr);
311  ipv4->SetUp (netdev_idx);
312  }
313 
314  // link the two nodes
315  Ptr<SimpleChannel> channel1 = CreateObject<SimpleChannel> ();
316  rxDev1->SetChannel (channel1);
317  txDev1->SetChannel (channel1);
318 
319  Ptr<SimpleChannel> channel2 = CreateObject<SimpleChannel> ();
320  rxDev2->SetChannel (channel2);
321  txDev2->SetChannel (channel2);
322 
323 
324  // Create the UDP sockets
325  Ptr<SocketFactory> rxSocketFactory = rxNode->GetObject<UdpSocketFactory> ();
326  Ptr<Socket> rxSocket = rxSocketFactory->CreateSocket ();
327  NS_TEST_EXPECT_MSG_EQ (rxSocket->Bind (InetSocketAddress (Ipv4Address ("10.0.0.1"), 1234)), 0, "trivial");
328  rxSocket->SetRecvCallback (MakeCallback (&UdpSocketImplTest::ReceivePkt, this));
329 
330  Ptr<Socket> rxSocket2 = rxSocketFactory->CreateSocket ();
332  NS_TEST_EXPECT_MSG_EQ (rxSocket2->Bind (InetSocketAddress (Ipv4Address ("10.0.1.1"), 1234)), 0, "trivial");
333 
334  Ptr<SocketFactory> txSocketFactory = txNode->GetObject<UdpSocketFactory> ();
335  Ptr<Socket> txSocket = txSocketFactory->CreateSocket ();
336  txSocket->SetAllowBroadcast (true);
337 
338  // ------ Now the tests ------------
339 
340  // Unicast test
341  SendData (txSocket, "10.0.0.1");
342  NS_TEST_EXPECT_MSG_EQ (m_receivedPacket->GetSize (), 123, "trivial");
343  NS_TEST_EXPECT_MSG_EQ (m_receivedPacket2->GetSize (), 0, "second interface should receive it");
344 
347 
348  // Simple broadcast test
349 
350  SendData (txSocket, "255.255.255.255");
351  NS_TEST_EXPECT_MSG_EQ (m_receivedPacket->GetSize (), 123, "trivial");
352  NS_TEST_EXPECT_MSG_EQ (m_receivedPacket2->GetSize (), 0, "second socket should not receive it (it is bound specifically to the second interface's address");
353 
356 
357  // Broadcast test with multiple receiving sockets
358 
359  // When receiving broadcast packets, all sockets sockets bound to
360  // the address/port should receive a copy of the same packet -- if
361  // the socket address matches.
362  rxSocket2->Dispose ();
363  rxSocket2 = rxSocketFactory->CreateSocket ();
365  NS_TEST_EXPECT_MSG_EQ (rxSocket2->Bind (InetSocketAddress (Ipv4Address ("0.0.0.0"), 1234)), 0, "trivial");
366 
367  SendData (txSocket, "255.255.255.255");
368  NS_TEST_EXPECT_MSG_EQ (m_receivedPacket->GetSize (), 123, "trivial");
369  NS_TEST_EXPECT_MSG_EQ (m_receivedPacket2->GetSize (), 123, "trivial");
370 
371  m_receivedPacket = 0;
372  m_receivedPacket2 = 0;
373 
374  // Simple Link-local multicast test
375 
376  txSocket->BindToNetDevice (txDev1);
377  SendData (txSocket, "224.0.0.9");
378  NS_TEST_EXPECT_MSG_EQ (m_receivedPacket->GetSize (), 0, "first socket should not receive it (it is bound specifically to the second interface's address");
379  NS_TEST_EXPECT_MSG_EQ (m_receivedPacket2->GetSize (), 123, "recv2: 224.0.0.9");
380 
381  m_receivedPacket->RemoveAllByteTags ();
383 
385 
386 }
387 
389 {
392  void DoSendData (Ptr<Socket> socket, std::string to);
393  void SendData (Ptr<Socket> socket, std::string to);
394 
395 public:
396  virtual void DoRun (void);
398 
399  void ReceivePacket (Ptr<Socket> socket, Ptr<Packet> packet, const Address &from);
400  void ReceivePacket2 (Ptr<Socket> socket, Ptr<Packet> packet, const Address &from);
401  void ReceivePkt (Ptr<Socket> socket);
402  void ReceivePkt2 (Ptr<Socket> socket);
403 };
404 
406  : TestCase ("UDP6 socket implementation")
407 {
408 }
409 
411 {
412  m_receivedPacket = packet;
413 }
414 
416 {
417  m_receivedPacket2 = packet;
418 }
419 
421 {
422  uint32_t availableData;
423  availableData = socket->GetRxAvailable ();
424  m_receivedPacket = socket->Recv (std::numeric_limits<uint32_t>::max (), 0);
425  NS_ASSERT (availableData == m_receivedPacket->GetSize ());
426  //cast availableData to void, to suppress 'availableData' set but not used
427  //compiler warning
428  (void) availableData;
429 }
430 
432 {
433  uint32_t availableData;
434  availableData = socket->GetRxAvailable ();
435  m_receivedPacket2 = socket->Recv (std::numeric_limits<uint32_t>::max (), 0);
436  NS_ASSERT (availableData == m_receivedPacket2->GetSize ());
437  //cast availableData to void, to suppress 'availableData' set but not used
438  //compiler warning
439  (void) availableData;
440 }
441 
442 void
444 {
445  Address realTo = Inet6SocketAddress (Ipv6Address (to.c_str ()), 1234);
446  NS_TEST_EXPECT_MSG_EQ (socket->SendTo (Create<Packet> (123), 0, realTo),
447  123, "XXX");
448 }
449 
450 void
452 {
453  m_receivedPacket = Create<Packet> ();
454  m_receivedPacket2 = Create<Packet> ();
456  &Udp6SocketImplTest::DoSendData, this, socket, to);
457  Simulator::Run ();
458 }
459 
460 void
462 {
463  // Create topology
464 
465  // Receiver Node
466  Ptr<Node> rxNode = CreateObject<Node> ();
467  AddInternetStack6 (rxNode);
468  Ptr<SimpleNetDevice> rxDev1, rxDev2;
469  { // first interface
470  rxDev1 = CreateObject<SimpleNetDevice> ();
472  rxNode->AddDevice (rxDev1);
473  Ptr<Ipv6> ipv6 = rxNode->GetObject<Ipv6> ();
474  uint32_t netdev_idx = ipv6->AddInterface (rxDev1);
475  Ipv6InterfaceAddress ipv6Addr = Ipv6InterfaceAddress (Ipv6Address ("2001:0100::1"), Ipv6Prefix (64));
476  ipv6->AddAddress (netdev_idx, ipv6Addr);
477  ipv6->SetUp (netdev_idx);
478  }
479  { // second interface
480  rxDev2 = CreateObject<SimpleNetDevice> ();
482  rxNode->AddDevice (rxDev2);
483  Ptr<Ipv6> ipv6 = rxNode->GetObject<Ipv6> ();
484  uint32_t netdev_idx = ipv6->AddInterface (rxDev2);
485  Ipv6InterfaceAddress ipv6Addr = Ipv6InterfaceAddress (Ipv6Address ("2001:0100:1::1"), Ipv6Prefix (64));
486  ipv6->AddAddress (netdev_idx, ipv6Addr);
487  ipv6->SetUp (netdev_idx);
488  }
489 
490  // Sender Node
491  Ptr<Node> txNode = CreateObject<Node> ();
492  AddInternetStack6 (txNode);
493  Ptr<SimpleNetDevice> txDev1;
494  {
495  txDev1 = CreateObject<SimpleNetDevice> ();
497  txNode->AddDevice (txDev1);
498  Ptr<Ipv6> ipv6 = txNode->GetObject<Ipv6> ();
499  uint32_t netdev_idx = ipv6->AddInterface (txDev1);
500  Ipv6InterfaceAddress ipv6Addr = Ipv6InterfaceAddress (Ipv6Address ("2001:0100::2"), Ipv6Prefix (64));
501  ipv6->AddAddress (netdev_idx, ipv6Addr);
502  ipv6->SetUp (netdev_idx);
503  }
504  Ptr<SimpleNetDevice> txDev2;
505  {
506  txDev2 = CreateObject<SimpleNetDevice> ();
508  txNode->AddDevice (txDev2);
509  Ptr<Ipv6> ipv6 = txNode->GetObject<Ipv6> ();
510  uint32_t netdev_idx = ipv6->AddInterface (txDev2);
511  Ipv6InterfaceAddress ipv6Addr = Ipv6InterfaceAddress (Ipv6Address ("2001:0100:1::2"), Ipv6Prefix (64));
512  ipv6->AddAddress (netdev_idx, ipv6Addr);
513  ipv6->SetUp (netdev_idx);
514  }
515 
516  // link the two nodes
517  Ptr<SimpleChannel> channel1 = CreateObject<SimpleChannel> ();
518  rxDev1->SetChannel (channel1);
519  txDev1->SetChannel (channel1);
520 
521  Ptr<SimpleChannel> channel2 = CreateObject<SimpleChannel> ();
522  rxDev2->SetChannel (channel2);
523  txDev2->SetChannel (channel2);
524 
525 
526  // Create the UDP sockets
527  Ptr<SocketFactory> rxSocketFactory = rxNode->GetObject<UdpSocketFactory> ();
528  Ptr<Socket> rxSocket = rxSocketFactory->CreateSocket ();
529  NS_TEST_EXPECT_MSG_EQ (rxSocket->Bind (Inet6SocketAddress (Ipv6Address ("2001:0100::1"), 1234)), 0, "trivial");
530  rxSocket->SetRecvCallback (MakeCallback (&Udp6SocketImplTest::ReceivePkt, this));
531 
532  Ptr<Socket> rxSocket2 = rxSocketFactory->CreateSocket ();
534  NS_TEST_EXPECT_MSG_EQ (rxSocket2->Bind (Inet6SocketAddress (Ipv6Address ("2001:0100:1::1"), 1234)), 0, "trivial");
535 
536  Ptr<SocketFactory> txSocketFactory = txNode->GetObject<UdpSocketFactory> ();
537  Ptr<Socket> txSocket = txSocketFactory->CreateSocket ();
538  txSocket->SetAllowBroadcast (true);
539  // ------ Now the tests ------------
540 
541  // Unicast test
542  SendData (txSocket, "2001:0100::1");
543  NS_TEST_EXPECT_MSG_EQ (m_receivedPacket->GetSize (), 123, "trivial");
544  NS_TEST_EXPECT_MSG_EQ (m_receivedPacket2->GetSize (), 0, "second interface should receive it");
545 
548 
549  // Simple Link-local multicast test
550 
551  // When receiving broadcast packets, all sockets sockets bound to
552  // the address/port should receive a copy of the same packet -- if
553  // the socket address matches.
554  rxSocket2->Dispose ();
555  rxSocket2 = rxSocketFactory->CreateSocket ();
557  NS_TEST_EXPECT_MSG_EQ (rxSocket2->Bind (Inet6SocketAddress (Ipv6Address ("::"), 1234)), 0, "trivial");
558 
559  txSocket->BindToNetDevice (txDev1);
560  SendData (txSocket, "ff02::1");
561  NS_TEST_EXPECT_MSG_EQ (m_receivedPacket->GetSize (), 0, "first socket should not receive it (it is bound specifically to the second interface's address");
562  NS_TEST_EXPECT_MSG_EQ (m_receivedPacket2->GetSize (), 123, "recv2: ff02::1");
563 
566 
568 
569 }
570 
571 
572 //-----------------------------------------------------------------------------
573 class UdpTestSuite : public TestSuite
574 {
575 public:
577  {
582  }
584 
585 } // namespace ns3