A Discrete-Event Network Simulator
API
node.cc
Go to the documentation of this file.
1 /* -*- Mode:C++; c-file-style:"gnu"; indent-tabs-mode:nil; -*- */
2 /*
3  * Copyright (c) 2006 Georgia Tech Research Corporation, INRIA
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  * Authors: George F. Riley<riley@ece.gatech.edu>
19  * Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
20  */
21 
22 #include "node.h"
23 #include "node-list.h"
24 #include "net-device.h"
25 #include "application.h"
26 #include "ns3/packet.h"
27 #include "ns3/simulator.h"
28 #include "ns3/object-vector.h"
29 #include "ns3/uinteger.h"
30 #include "ns3/log.h"
31 #include "ns3/assert.h"
32 #include "ns3/global-value.h"
33 #include "ns3/boolean.h"
34 
35 namespace ns3 {
36 
38 
40 
46 static GlobalValue g_checksumEnabled = GlobalValue ("ChecksumEnabled",
47  "A global switch to enable all checksums for all protocols",
48  BooleanValue (false),
50 
51 TypeId
53 {
54  static TypeId tid = TypeId ("ns3::Node")
55  .SetParent<Object> ()
56  .SetGroupName("Network")
57  .AddConstructor<Node> ()
58  .AddAttribute ("DeviceList", "The list of devices associated to this Node.",
61  MakeObjectVectorChecker<NetDevice> ())
62  .AddAttribute ("ApplicationList", "The list of applications associated to this Node.",
65  MakeObjectVectorChecker<Application> ())
66  .AddAttribute ("Id", "The id (unique integer) of this Node.",
67  TypeId::ATTR_GET, // allow only getting it.
68  UintegerValue (0),
70  MakeUintegerChecker<uint32_t> ())
71  .AddAttribute ("SystemId", "The systemId of this node: a unique integer used for parallel simulations.",
73  UintegerValue (0),
75  MakeUintegerChecker<uint32_t> ())
76  ;
77  return tid;
78 }
79 
81  : m_id (0),
82  m_sid (0)
83 {
84  NS_LOG_FUNCTION (this);
85  Construct ();
86 }
87 
88 Node::Node(uint32_t sid)
89  : m_id (0),
90  m_sid (sid)
91 {
92  NS_LOG_FUNCTION (this << sid);
93  Construct ();
94 }
95 
96 void
98 {
99  NS_LOG_FUNCTION (this);
100  m_id = NodeList::Add (this);
101 }
102 
104 {
105  NS_LOG_FUNCTION (this);
106 }
107 
108 uint32_t
109 Node::GetId (void) const
110 {
111  NS_LOG_FUNCTION (this);
112  return m_id;
113 }
114 
115 Time
116 Node::GetLocalTime (void) const
117 {
118  NS_LOG_FUNCTION (this);
119  return Simulator::Now ();
120 }
121 
122 uint32_t
123 Node::GetSystemId (void) const
124 {
125  NS_LOG_FUNCTION (this);
126  return m_sid;
127 }
128 
129 uint32_t
131 {
132  NS_LOG_FUNCTION (this << device);
133  uint32_t index = m_devices.size ();
134  m_devices.push_back (device);
135  device->SetNode (this);
136  device->SetIfIndex (index);
137  device->SetReceiveCallback (MakeCallback (&Node::NonPromiscReceiveFromDevice, this));
139  &NetDevice::Initialize, device);
140  NotifyDeviceAdded (device);
141  return index;
142 }
144 Node::GetDevice (uint32_t index) const
145 {
146  NS_LOG_FUNCTION (this << index);
147  NS_ASSERT_MSG (index < m_devices.size (), "Device index " << index <<
148  " is out of range (only have " << m_devices.size () << " devices).");
149  return m_devices[index];
150 }
151 uint32_t
152 Node::GetNDevices (void) const
153 {
154  NS_LOG_FUNCTION (this);
155  return m_devices.size ();
156 }
157 
158 uint32_t
160 {
161  NS_LOG_FUNCTION (this << application);
162  uint32_t index = m_applications.size ();
163  m_applications.push_back (application);
164  application->SetNode (this);
166  &Application::Initialize, application);
167  return index;
168 }
170 Node::GetApplication (uint32_t index) const
171 {
172  NS_LOG_FUNCTION (this << index);
173  NS_ASSERT_MSG (index < m_applications.size (), "Application index " << index <<
174  " is out of range (only have " << m_applications.size () << " applications).");
175  return m_applications[index];
176 }
177 uint32_t
179 {
180  NS_LOG_FUNCTION (this);
181  return m_applications.size ();
182 }
183 
184 void
186 {
187  NS_LOG_FUNCTION (this);
188  m_deviceAdditionListeners.clear ();
189  m_handlers.clear ();
190  for (std::vector<Ptr<NetDevice> >::iterator i = m_devices.begin ();
191  i != m_devices.end (); i++)
192  {
193  Ptr<NetDevice> device = *i;
194  device->Dispose ();
195  *i = 0;
196  }
197  m_devices.clear ();
198  for (std::vector<Ptr<Application> >::iterator i = m_applications.begin ();
199  i != m_applications.end (); i++)
200  {
201  Ptr<Application> application = *i;
202  application->Dispose ();
203  *i = 0;
204  }
205  m_applications.clear ();
207 }
208 void
210 {
211  NS_LOG_FUNCTION (this);
212  for (std::vector<Ptr<NetDevice> >::iterator i = m_devices.begin ();
213  i != m_devices.end (); i++)
214  {
215  Ptr<NetDevice> device = *i;
216  device->Initialize ();
217  }
218  for (std::vector<Ptr<Application> >::iterator i = m_applications.begin ();
219  i != m_applications.end (); i++)
220  {
221  Ptr<Application> application = *i;
222  application->Initialize ();
223  }
224 
226 }
227 
228 void
230  uint16_t protocolType,
231  Ptr<NetDevice> device,
232  bool promiscuous)
233 {
234  NS_LOG_FUNCTION (this << &handler << protocolType << device << promiscuous);
235  struct Node::ProtocolHandlerEntry entry;
236  entry.handler = handler;
237  entry.protocol = protocolType;
238  entry.device = device;
239  entry.promiscuous = promiscuous;
240 
241  // On demand enable promiscuous mode in netdevices
242  if (promiscuous)
243  {
244  if (device == 0)
245  {
246  for (std::vector<Ptr<NetDevice> >::iterator i = m_devices.begin ();
247  i != m_devices.end (); i++)
248  {
249  Ptr<NetDevice> dev = *i;
250  dev->SetPromiscReceiveCallback (MakeCallback (&Node::PromiscReceiveFromDevice, this));
251  }
252  }
253  else
254  {
255  device->SetPromiscReceiveCallback (MakeCallback (&Node::PromiscReceiveFromDevice, this));
256  }
257  }
258 
259  m_handlers.push_back (entry);
260 }
261 
262 void
264 {
265  NS_LOG_FUNCTION (this << &handler);
266  for (ProtocolHandlerList::iterator i = m_handlers.begin ();
267  i != m_handlers.end (); i++)
268  {
269  if (i->handler.IsEqual (handler))
270  {
271  m_handlers.erase (i);
272  break;
273  }
274  }
275 }
276 
277 bool
279 {
281  BooleanValue val;
283  return val.Get ();
284 }
285 
286 bool
288  const Address &from, const Address &to, NetDevice::PacketType packetType)
289 {
290  NS_LOG_FUNCTION (this << device << packet << protocol << &from << &to << packetType);
291  return ReceiveFromDevice (device, packet, protocol, from, to, packetType, true);
292 }
293 
294 bool
296  const Address &from)
297 {
298  NS_LOG_FUNCTION (this << device << packet << protocol << &from);
299  return ReceiveFromDevice (device, packet, protocol, from, device->GetAddress (), NetDevice::PacketType (0), false);
300 }
301 
302 bool
303 Node::ReceiveFromDevice (Ptr<NetDevice> device, Ptr<const Packet> packet, uint16_t protocol,
304  const Address &from, const Address &to, NetDevice::PacketType packetType, bool promiscuous)
305 {
306  NS_LOG_FUNCTION (this << device << packet << protocol << &from << &to << packetType << promiscuous);
307  NS_ASSERT_MSG (Simulator::GetContext () == GetId (), "Received packet with erroneous context ; " <<
308  "make sure the channels in use are correctly updating events context " <<
309  "when transferring events from one node to another.");
310  NS_LOG_DEBUG ("Node " << GetId () << " ReceiveFromDevice: dev "
311  << device->GetIfIndex () << " (type=" << device->GetInstanceTypeId ().GetName ()
312  << ") Packet UID " << packet->GetUid ());
313  bool found = false;
314 
315  for (ProtocolHandlerList::iterator i = m_handlers.begin ();
316  i != m_handlers.end (); i++)
317  {
318  if (i->device == 0 ||
319  (i->device != 0 && i->device == device))
320  {
321  if (i->protocol == 0 ||
322  i->protocol == protocol)
323  {
324  if (promiscuous == i->promiscuous)
325  {
326  i->handler (device, packet, protocol, from, to, packetType);
327  found = true;
328  }
329  }
330  }
331  }
332  return found;
333 }
334 void
336 {
337  NS_LOG_FUNCTION (this << &listener);
338  m_deviceAdditionListeners.push_back (listener);
339  // and, then, notify the new listener about all existing devices.
340  for (std::vector<Ptr<NetDevice> >::const_iterator i = m_devices.begin ();
341  i != m_devices.end (); ++i)
342  {
343  listener (*i);
344  }
345 }
346 void
348 {
349  NS_LOG_FUNCTION (this << &listener);
350  for (DeviceAdditionListenerList::iterator i = m_deviceAdditionListeners.begin ();
351  i != m_deviceAdditionListeners.end (); i++)
352  {
353  if ((*i).IsEqual (listener))
354  {
355  m_deviceAdditionListeners.erase (i);
356  break;
357  }
358  }
359 }
360 
361 void
363 {
364  NS_LOG_FUNCTION (this << device);
365  for (DeviceAdditionListenerList::iterator i = m_deviceAdditionListeners.begin ();
366  i != m_deviceAdditionListeners.end (); i++)
367  {
368  (*i) (device);
369  }
370 }
371 
372 
373 } // namespace ns3
void Dispose(void)
Dispose of this Object.
Definition: object.cc:214
uint32_t AddApplication(Ptr< Application > application)
Associate an Application to this Node.
Definition: node.cc:159
virtual void DoInitialize(void)
Initialize() implementation.
Definition: object.cc:353
uint64_t GetUid(void) const
Returns the packet&#39;s Uid.
Definition: packet.cc:390
Simulation virtual time values and global simulation resolution.
Definition: nstime.h:103
void GetValue(AttributeValue &value) const
Get the value.
Smart pointer class similar to boost::intrusive_ptr.
Definition: ptr.h:73
#define NS_LOG_FUNCTION(parameters)
If log level LOG_FUNCTION is enabled, this macro will output all input parameters separated by "...
AttributeValue implementation for Boolean.
Definition: boolean.h:36
uint32_t GetId(void) const
Definition: node.cc:109
virtual void DoInitialize(void)
Initialize() implementation.
Definition: node.cc:209
#define NS_OBJECT_ENSURE_REGISTERED(type)
Register an Object subclass with the TypeId system.
Definition: object-base.h:45
DeviceAdditionListenerList m_deviceAdditionListeners
Device addition listeners in the node.
Definition: node.h:290
Ptr< NetDevice > GetDevice(uint32_t index) const
Retrieve the index-th NetDevice associated to this node.
Definition: node.cc:144
static bool ChecksumEnabled(void)
Definition: node.cc:278
void NotifyDeviceAdded(Ptr< NetDevice > device)
Notifies all the DeviceAdditionListener about the new device added.
Definition: node.cc:362
static uint32_t GetContext(void)
Get the current simulation context.
Definition: simulator.cc:300
ProtocolHandler handler
the protocol handler
Definition: node.h:274
Ptr< const AttributeAccessor > MakeObjectVectorAccessor(U T::*memberVariable)
MakeAccessorHelper implementation for ObjectVector.
Definition: object-vector.h:81
#define NS_LOG_COMPONENT_DEFINE(name)
Define a Log component with a specific name.
Definition: log.h:205
std::vector< Ptr< NetDevice > > m_devices
Devices associated to this node.
Definition: node.h:287
virtual void DoDispose(void)
Destructor implementation.
Definition: object.cc:346
#define NS_LOG_FUNCTION_NOARGS()
Output the name of the function.
Hold a so-called &#39;global value&#39;.
Definition: global-value.h:73
void UnregisterProtocolHandler(ProtocolHandler handler)
Definition: node.cc:263
a polymophic address class
Definition: address.h:90
The attribute can be read.
Definition: type-id.h:64
bool NonPromiscReceiveFromDevice(Ptr< NetDevice > device, Ptr< const Packet > packet, uint16_t protocol, const Address &from)
Receive a packet from a device in non-promiscuous mode.
Definition: node.cc:295
uint32_t m_sid
System id for this node.
Definition: node.h:286
virtual void DoDispose(void)
The dispose method.
Definition: node.cc:185
Ptr< NetDevice > device
the NetDevice
Definition: node.h:275
Hold an unsigned integer type.
Definition: uinteger.h:44
static uint32_t Add(Ptr< Node > node)
Definition: node-list.cc:223
Ptr< Application > GetApplication(uint32_t index) const
Retrieve the index-th Application associated to this node.
Definition: node.cc:170
uint16_t protocol
the protocol number
Definition: node.h:276
Time GetLocalTime(void) const
In the future, ns3 nodes may have clock that returned a local time different from the virtual time Si...
Definition: node.cc:116
bool Get(void) const
Definition: boolean.cc:51
static void ScheduleWithContext(uint32_t context, Time const &delay, FUNC f, Ts &&... args)
Schedule an event with the given context.
Definition: simulator.h:572
ProtocolHandlerList m_handlers
Protocol handlers in the node.
Definition: node.h:289
void RegisterDeviceAdditionListener(DeviceAdditionListener listener)
Definition: node.cc:335
Every class exported by the ns3 library is enclosed in the ns3 namespace.
static GlobalValue g_checksumEnabled
A global switch to enable all checksums for all protocols.
Definition: node.cc:46
uint32_t GetSystemId(void) const
Definition: node.cc:123
The attribute can be written.
Definition: type-id.h:65
void SetNode(Ptr< Node > node)
Definition: application.cc:111
std::vector< Ptr< Application > > m_applications
Applications associated to this node.
Definition: node.h:288
Protocol handler entry.
Definition: node.h:273
static Time Now(void)
Return the current simulation virtual time.
Definition: simulator.cc:195
uint32_t m_id
Node id for this node.
Definition: node.h:285
void RegisterProtocolHandler(ProtocolHandler handler, uint16_t protocolType, Ptr< NetDevice > device, bool promiscuous=false)
Definition: node.cc:229
#define NS_ASSERT_MSG(condition, message)
At runtime, in debugging builds, if this condition is not true, the program prints the message to out...
Definition: assert.h:88
static TypeId GetTypeId(void)
Get the type ID.
Definition: node.cc:52
bool ReceiveFromDevice(Ptr< NetDevice > device, Ptr< const Packet >, uint16_t protocol, const Address &from, const Address &to, NetDevice::PacketType packetType, bool promisc)
Receive a packet from a device.
Definition: node.cc:303
uint32_t AddDevice(Ptr< NetDevice > device)
Associate a NetDevice to this node.
Definition: node.cc:130
void UnregisterDeviceAdditionListener(DeviceAdditionListener listener)
Definition: node.cc:347
virtual ~Node()
Definition: node.cc:103
A network Node.
Definition: node.h:56
#define NS_LOG_DEBUG(msg)
Use NS_LOG to output a message of level LOG_DEBUG.
Definition: log.h:273
Time Seconds(double value)
Construct a Time in the indicated unit.
Definition: nstime.h:1288
Ptr< const AttributeChecker > MakeBooleanChecker(void)
Definition: boolean.cc:121
uint32_t GetNApplications(void) const
Definition: node.cc:178
A base class which provides memory management and object aggregation.
Definition: object.h:87
PacketType
Packet types are used as they are in Linux.
Definition: net-device.h:296
Container for a set of ns3::Object pointers.
Ptr< const AttributeAccessor > MakeUintegerAccessor(T1 a1)
Create an AttributeAccessor for a class data member, or a lone class get functor or set method...
Definition: uinteger.h:45
a unique identifier for an interface.
Definition: type-id.h:58
void Construct(void)
Finish node&#39;s construction by setting the correct node ID.
Definition: node.cc:97
TypeId SetParent(TypeId tid)
Set the parent TypeId.
Definition: type-id.cc:923
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 Initialize(void)
Invoke DoInitialize on all Objects aggregated to this one.
Definition: object.cc:183
uint32_t GetNDevices(void) const
Definition: node.cc:152
bool promiscuous
true if it is a promiscuous handler
Definition: node.h:277
bool PromiscReceiveFromDevice(Ptr< NetDevice > device, Ptr< const Packet > packet, uint16_t protocol, const Address &from, const Address &to, NetDevice::PacketType packetType)
Receive a packet from a device in promiscuous mode.
Definition: node.cc:287
Node()
Definition: node.cc:80