A Discrete-Event Network Simulator
API
ipv4-forwarding-test.cc
Go to the documentation of this file.
1 /* -*- Mode:C++; c-file-style:"gnu"; indent-tabs-mode:nil; -*- */
2 /*
3  * Copyright (c) 2013 Universita' di Firenze
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: Tommaso Pecorella <tommaso.pecorella@unifi.it>
19  */
20 
21 #include "ns3/test.h"
22 #include "ns3/socket-factory.h"
23 #include "ns3/udp-socket-factory.h"
24 #include "ns3/simulator.h"
25 #include "ns3/simple-channel.h"
26 #include "ns3/simple-net-device.h"
27 #include "ns3/drop-tail-queue.h"
28 #include "ns3/socket.h"
29 #include "ns3/boolean.h"
30 
31 #include "ns3/log.h"
32 #include "ns3/node.h"
33 #include "ns3/inet-socket-address.h"
34 
35 #include "ns3/arp-l3-protocol.h"
36 #include "ns3/ipv4-l3-protocol.h"
37 #include "ns3/icmpv4-l4-protocol.h"
38 #include "ns3/udp-l4-protocol.h"
39 #include "ns3/ipv4-static-routing.h"
40 
41 #include "ns3/traffic-control-layer.h"
42 
43 #include <string>
44 #include <limits>
45 
46 using namespace ns3;
47 
48 static void
50 {
51  //ARP
52  Ptr<ArpL3Protocol> arp = CreateObject<ArpL3Protocol> ();
53  node->AggregateObject (arp);
54  //IPV4
55  Ptr<Ipv4L3Protocol> ipv4 = CreateObject<Ipv4L3Protocol> ();
56  //Routing for Ipv4
57  Ptr<Ipv4StaticRouting> ipv4Routing = CreateObject<Ipv4StaticRouting> ();
58  ipv4->SetRoutingProtocol (ipv4Routing);
59  node->AggregateObject (ipv4);
60  node->AggregateObject (ipv4Routing);
61  //ICMP
62  Ptr<Icmpv4L4Protocol> icmp = CreateObject<Icmpv4L4Protocol> ();
63  node->AggregateObject (icmp);
64  //UDP
65  Ptr<UdpL4Protocol> udp = CreateObject<UdpL4Protocol> ();
66  node->AggregateObject (udp);
67  //Traffic Control
68  Ptr<TrafficControlLayer> tc = CreateObject<TrafficControlLayer> ();
69  node->AggregateObject (tc);
70 }
71 
72 
74 {
76  void DoSendData (Ptr<Socket> socket, std::string to);
77  void SendData (Ptr<Socket> socket, std::string to);
78 
79 public:
80  virtual void DoRun (void);
82 
83  void ReceivePkt (Ptr<Socket> socket);
84 };
85 
87  : TestCase ("UDP socket implementation")
88 {
89 }
90 
92 {
93  uint32_t availableData;
94  availableData = socket->GetRxAvailable ();
96  NS_ASSERT (availableData == m_receivedPacket->GetSize ());
97 }
98 
99 void
101 {
102  Address realTo = InetSocketAddress (Ipv4Address (to.c_str ()), 1234);
103  NS_TEST_EXPECT_MSG_EQ (socket->SendTo (Create<Packet> (123), 0, realTo),
104  123, "100");
105 }
106 
107 void
109 {
110  m_receivedPacket = Create<Packet> ();
111  Simulator::ScheduleWithContext (socket->GetNode ()->GetId (), Seconds (0),
112  &Ipv4ForwardingTest::DoSendData, this, socket, to);
113  Simulator::Run ();
114 }
115 
116 void
118 {
119  // Create topology
120 
121  // Receiver Node
122  Ptr<Node> rxNode = CreateObject<Node> ();
123  AddInternetStack (rxNode);
124  Ptr<SimpleNetDevice> rxDev;
125  { // first interface
126  rxDev = CreateObject<SimpleNetDevice> ();
127  rxDev->SetAddress (Mac48Address::ConvertFrom (Mac48Address::Allocate ()));
128  rxNode->AddDevice (rxDev);
129  Ptr<Ipv4> ipv4 = rxNode->GetObject<Ipv4> ();
130  uint32_t netdev_idx = ipv4->AddInterface (rxDev);
131  Ipv4InterfaceAddress ipv4Addr = Ipv4InterfaceAddress (Ipv4Address ("10.0.0.2"), Ipv4Mask (0xffff0000U));
132  ipv4->AddAddress (netdev_idx, ipv4Addr);
133  ipv4->SetUp (netdev_idx);
134  }
135 
136  // Forwarding Node
137  Ptr<Node> fwNode = CreateObject<Node> ();
138  AddInternetStack (fwNode);
139  Ptr<SimpleNetDevice> fwDev1, fwDev2;
140  { // first interface
141  fwDev1 = CreateObject<SimpleNetDevice> ();
142  fwDev1->SetAddress (Mac48Address::ConvertFrom (Mac48Address::Allocate ()));
143  fwNode->AddDevice (fwDev1);
144  Ptr<Ipv4> ipv4 = fwNode->GetObject<Ipv4> ();
145  uint32_t netdev_idx = ipv4->AddInterface (fwDev1);
146  Ipv4InterfaceAddress ipv4Addr = Ipv4InterfaceAddress (Ipv4Address ("10.0.0.1"), Ipv4Mask (0xffff0000U));
147  ipv4->AddAddress (netdev_idx, ipv4Addr);
148  ipv4->SetUp (netdev_idx);
149  }
150 
151  { // second interface
152  fwDev2 = CreateObject<SimpleNetDevice> ();
153  fwDev2->SetAddress (Mac48Address::ConvertFrom (Mac48Address::Allocate ()));
154  fwNode->AddDevice (fwDev2);
155  Ptr<Ipv4> ipv4 = fwNode->GetObject<Ipv4> ();
156  uint32_t netdev_idx = ipv4->AddInterface (fwDev2);
157  Ipv4InterfaceAddress ipv4Addr = Ipv4InterfaceAddress (Ipv4Address ("10.1.0.1"), Ipv4Mask (0xffff0000U));
158  ipv4->AddAddress (netdev_idx, ipv4Addr);
159  ipv4->SetUp (netdev_idx);
160  }
161 
162  // Sender Node
163  Ptr<Node> txNode = CreateObject<Node> ();
164  AddInternetStack (txNode);
165  Ptr<SimpleNetDevice> txDev;
166  {
167  txDev = CreateObject<SimpleNetDevice> ();
168  txDev->SetAddress (Mac48Address::ConvertFrom (Mac48Address::Allocate ()));
169  txNode->AddDevice (txDev);
170  Ptr<Ipv4> ipv4 = txNode->GetObject<Ipv4> ();
171  uint32_t netdev_idx = ipv4->AddInterface (txDev);
172  Ipv4InterfaceAddress ipv4Addr = Ipv4InterfaceAddress (Ipv4Address ("10.1.0.2"), Ipv4Mask (0xffff0000U));
173  ipv4->AddAddress (netdev_idx, ipv4Addr);
174  ipv4->SetUp (netdev_idx);
175  Ptr<Ipv4StaticRouting> ipv4StaticRouting = txNode->GetObject<Ipv4StaticRouting> ();
176  ipv4StaticRouting->SetDefaultRoute(Ipv4Address("10.1.0.1"), netdev_idx);
177  }
178 
179  // link the two nodes
180  Ptr<SimpleChannel> channel1 = CreateObject<SimpleChannel> ();
181  rxDev->SetChannel (channel1);
182  fwDev1->SetChannel (channel1);
183 
184  Ptr<SimpleChannel> channel2 = CreateObject<SimpleChannel> ();
185  fwDev2->SetChannel (channel2);
186  txDev->SetChannel (channel2);
187 
188  // Create the UDP sockets
189  Ptr<SocketFactory> rxSocketFactory = rxNode->GetObject<UdpSocketFactory> ();
190  Ptr<Socket> rxSocket = rxSocketFactory->CreateSocket ();
191  NS_TEST_EXPECT_MSG_EQ (rxSocket->Bind (InetSocketAddress (Ipv4Address ("10.0.0.2"), 1234)), 0, "trivial");
192  rxSocket->SetRecvCallback (MakeCallback (&Ipv4ForwardingTest::ReceivePkt, this));
193 
194  Ptr<SocketFactory> txSocketFactory = txNode->GetObject<UdpSocketFactory> ();
195  Ptr<Socket> txSocket = txSocketFactory->CreateSocket ();
196  txSocket->SetAllowBroadcast (true);
197 
198  // ------ Now the tests ------------
199 
200  // Unicast test
201  SendData (txSocket, "10.0.0.2");
202  NS_TEST_EXPECT_MSG_EQ (m_receivedPacket->GetSize (), 123, "IPv4 Forwarding on");
203 
205  m_receivedPacket = 0;
206 
207  Ptr<Ipv4> ipv4 = fwNode->GetObject<Ipv4> ();
208  ipv4->SetAttribute("IpForward", BooleanValue (false));
209  SendData (txSocket, "10.0.0.2");
210  NS_TEST_EXPECT_MSG_EQ (m_receivedPacket->GetSize (), 0, "IPv4 Forwarding off");
211 
212  Simulator::Destroy ();
213 
214 }
215 
216 
217 //-----------------------------------------------------------------------------
218 //-----------------------------------------------------------------------------
220 {
221 public:
222  Ipv4ForwardingTestSuite () : TestSuite ("ipv4-forwarding", UNIT)
223  {
224  AddTestCase (new Ipv4ForwardingTest, TestCase::QUICK);
225  }
virtual uint32_t AddInterface(Ptr< NetDevice > device)=0
an Inet address class
AttributeValue implementation for Boolean.
Definition: boolean.h:34
void DoSendData(Ptr< Socket > socket, std::string to)
void SetDefaultRoute(Ipv4Address nextHop, uint32_t interface, uint32_t metric=0)
Add a default route to the static routing table.
Ptr< T > GetObject(void) const
Get a pointer to the requested aggregated Object.
Definition: object.h:462
virtual bool SetAllowBroadcast(bool allowBroadcast)=0
Configure whether broadcast datagram transmissions are allowed.
a class to represent an Ipv4 address mask
Definition: ipv4-address.h:257
Ptr< Packet > m_receivedPacket
A suite of tests to run.
Definition: test.h:1333
void AggregateObject(Ptr< Object > other)
Aggregate two Objects together.
Definition: object.cc:252
#define NS_ASSERT(condition)
At runtime, in debugging builds, if this condition is not true, the program prints the source file...
Definition: assert.h:67
#define NS_TEST_EXPECT_MSG_EQ(actual, limit, msg)
Test that an actual and expected (limit) value are equal and report if not.
Definition: test.h:278
uint32_t GetSize(void) const
Returns the the size in bytes of the packet (including the zero-filled initial payload).
Definition: packet.h:792
virtual Ptr< Socket > CreateSocket(void)=0
encapsulates test code
Definition: test.h:1147
This test suite implements a Unit Test.
Definition: test.h:1343
virtual void DoRun(void)
Implementation to actually run this TestCase.
a polymophic address class
Definition: address.h:90
void SendData(Ptr< Socket > socket, std::string to)
#define max(a, b)
Definition: 80211b.c:45
void AddTestCase(TestCase *testCase, enum TestDuration duration)
Add an individual child TestCase to this test suite.
Definition: test.cc:298
virtual void SetUp(uint32_t interface)=0
Callback< R > MakeCallback(R(T::*memPtr)(void), OBJ objPtr)
Definition: callback.h:1489
Access to the IPv4 forwarding table, interfaces, and configuration.
Definition: ipv4.h:76
Every class exported by the ns3 library is enclosed in the ns3 namespace.
Static routing protocol for IP version 4 stacks.
virtual Ptr< Packet > Recv(uint32_t maxSize, uint32_t flags)=0
Read data from the socket.
static void AddInternetStack(Ptr< Node > node)
Ipv4 addresses are stored in host order in this class.
Definition: ipv4-address.h:40
void ReceivePkt(Ptr< Socket > socket)
uint32_t AddDevice(Ptr< NetDevice > device)
Associate a NetDevice to this node.
Definition: node.cc:128
uint32_t GetId(void) const
Definition: node.cc:107
a class to store IPv4 address information on an interface
virtual Ptr< Node > GetNode(void) const =0
Return the node this socket is associated with.
virtual void SetAddress(Address address)
Set the address of this interface.
Time Seconds(double value)
Construct a Time in the indicated unit.
Definition: nstime.h:895
void RemoveAllByteTags(void)
Remove all byte tags stored in this packet.
Definition: packet.cc:349
virtual bool AddAddress(uint32_t interface, Ipv4InterfaceAddress address)=0
virtual int SendTo(Ptr< Packet > p, uint32_t flags, const Address &toAddress)=0
Send data to a specified peer.
API to create UDP socket instances.
Ipv4ForwardingTestSuite g_ipv4forwardingTestSuite
void SetChannel(Ptr< SimpleChannel > channel)
Attach a channel to this net device.
void SetAttribute(std::string name, const AttributeValue &value)
Set a single attribute, raising fatal errors if unsuccessful.
Definition: object-base.cc:191
virtual uint32_t GetRxAvailable(void) const =0
Return number of bytes which can be returned from one or multiple calls to Recv.
void SetRoutingProtocol(Ptr< Ipv4RoutingProtocol > routingProtocol)
Register a new routing protocol to be used by this Ipv4 stack.