A Discrete-Event Network Simulator
API
Loading...
Searching...
No Matches
csma-helper.cc
Go to the documentation of this file.
1/*
2 * Copyright (c) 2008 INRIA
3 *
4 * SPDX-License-Identifier: GPL-2.0-only
5 *
6 * Author: Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
7 */
8
9#include "csma-helper.h"
10
11#include "ns3/abort.h"
12#include "ns3/config.h"
13#include "ns3/csma-channel.h"
14#include "ns3/csma-net-device.h"
15#include "ns3/log.h"
16#include "ns3/names.h"
17#include "ns3/net-device-queue-interface.h"
18#include "ns3/object-factory.h"
19#include "ns3/packet.h"
20#include "ns3/simulator.h"
21#include "ns3/trace-helper.h"
22
23#include <string>
24
25namespace ns3
26{
27
28NS_LOG_COMPONENT_DEFINE("CsmaHelper");
29
31{
32 m_queueFactory.SetTypeId("ns3::DropTailQueue<Packet>");
33 m_deviceFactory.SetTypeId("ns3::CsmaNetDevice");
34 m_channelFactory.SetTypeId("ns3::CsmaChannel");
36}
37
38void
40{
41 m_deviceFactory.Set(n1, v1);
42}
43
44void
46{
47 m_channelFactory.Set(n1, v1);
48}
49
50void
55
56void
59 bool promiscuous,
60 bool explicitFilename)
61{
62 //
63 // All of the Pcap enable functions vector through here including the ones
64 // that are wandering through all of devices on perhaps all of the nodes in
65 // the system. We can only deal with devices of type CsmaNetDevice.
66 //
67 Ptr<CsmaNetDevice> device = nd->GetObject<CsmaNetDevice>();
68 if (!device)
69 {
70 NS_LOG_INFO("CsmaHelper::EnablePcapInternal(): Device "
71 << device << " not of type ns3::CsmaNetDevice");
72 return;
73 }
74
75 PcapHelper pcapHelper;
76
77 std::string filename;
78 if (explicitFilename)
79 {
80 filename = prefix;
81 }
82 else
83 {
84 filename = pcapHelper.GetFilenameFromDevice(prefix, device);
85 }
86
88 pcapHelper.CreateFile(filename, std::ios::out, PcapHelper::DLT_EN10MB);
89 if (promiscuous)
90 {
91 pcapHelper.HookDefaultSink<CsmaNetDevice>(device, "PromiscSniffer", file);
92 }
93 else
94 {
95 pcapHelper.HookDefaultSink<CsmaNetDevice>(device, "Sniffer", file);
96 }
97}
98
99void
101 std::string prefix,
103 bool explicitFilename)
104{
105 //
106 // All of the ascii enable functions vector through here including the ones
107 // that are wandering through all of devices on perhaps all of the nodes in
108 // the system. We can only deal with devices of type CsmaNetDevice.
109 //
110 Ptr<CsmaNetDevice> device = nd->GetObject<CsmaNetDevice>();
111 if (!device)
112 {
113 NS_LOG_INFO("CsmaHelper::EnableAsciiInternal(): Device "
114 << device << " not of type ns3::CsmaNetDevice");
115 return;
116 }
117
118 //
119 // Our default trace sinks are going to use packet printing, so we have to
120 // make sure that is turned on.
121 //
123
124 //
125 // If we are not provided an OutputStreamWrapper, we are expected to create
126 // one using the usual trace filename conventions and do a Hook*WithoutContext
127 // since there will be one file per context and therefore the context would
128 // be redundant.
129 //
130 if (!stream)
131 {
132 //
133 // Set up an output stream object to deal with private ofstream copy
134 // constructor and lifetime issues. Let the helper decide the actual
135 // name of the file given the prefix.
136 //
137 AsciiTraceHelper asciiTraceHelper;
138
139 std::string filename;
140 if (explicitFilename)
141 {
142 filename = prefix;
143 }
144 else
145 {
146 filename = asciiTraceHelper.GetFilenameFromDevice(prefix, device);
147 }
148
149 Ptr<OutputStreamWrapper> theStream = asciiTraceHelper.CreateFileStream(filename);
150
151 //
152 // The MacRx trace source provides our "r" event.
153 //
155 "MacRx",
156 theStream);
157
158 //
159 // The "+", '-', and 'd' events are driven by trace sources actually in the
160 // transmit queue.
161 //
162 Ptr<Queue<Packet>> queue = device->GetQueue();
164 "Enqueue",
165 theStream);
166 asciiTraceHelper.HookDefaultDropSinkWithoutContext<Queue<Packet>>(queue, "Drop", theStream);
168 "Dequeue",
169 theStream);
170
171 return;
172 }
173
174 //
175 // If we are provided an OutputStreamWrapper, we are expected to use it, and
176 // to providd a context. We are free to come up with our own context if we
177 // want, and use the AsciiTraceHelper Hook*WithContext functions, but for
178 // compatibility and simplicity, we just use Config::Connect and let it deal
179 // with the context.
180 //
181 // Note that we are going to use the default trace sinks provided by the
182 // ascii trace helper. There is actually no AsciiTraceHelper in sight here,
183 // but the default trace sinks are actually publicly available static
184 // functions that are always there waiting for just such a case.
185 //
186 uint32_t nodeid = nd->GetNode()->GetId();
187 uint32_t deviceid = nd->GetIfIndex();
188 std::ostringstream oss;
189
190 oss << "/NodeList/" << nd->GetNode()->GetId() << "/DeviceList/" << deviceid
191 << "/$ns3::CsmaNetDevice/MacRx";
192 Config::Connect(oss.str(),
194
195 oss.str("");
196 oss << "/NodeList/" << nodeid << "/DeviceList/" << deviceid
197 << "/$ns3::CsmaNetDevice/TxQueue/Enqueue";
198 Config::Connect(oss.str(),
200
201 oss.str("");
202 oss << "/NodeList/" << nodeid << "/DeviceList/" << deviceid
203 << "/$ns3::CsmaNetDevice/TxQueue/Dequeue";
204 Config::Connect(oss.str(),
206
207 oss.str("");
208 oss << "/NodeList/" << nodeid << "/DeviceList/" << deviceid
209 << "/$ns3::CsmaNetDevice/TxQueue/Drop";
210 Config::Connect(oss.str(),
212}
213
216{
218 return Install(node, channel);
219}
220
222CsmaHelper::Install(std::string nodeName) const
223{
224 Ptr<Node> node = Names::Find<Node>(nodeName);
225 return Install(node);
226}
227
230{
231 return NetDeviceContainer(InstallPriv(node, channel));
232}
233
235CsmaHelper::Install(Ptr<Node> node, std::string channelName) const
236{
237 Ptr<CsmaChannel> channel = Names::Find<CsmaChannel>(channelName);
238 return NetDeviceContainer(InstallPriv(node, channel));
239}
240
242CsmaHelper::Install(std::string nodeName, Ptr<CsmaChannel> channel) const
243{
244 Ptr<Node> node = Names::Find<Node>(nodeName);
245 return NetDeviceContainer(InstallPriv(node, channel));
246}
247
249CsmaHelper::Install(std::string nodeName, std::string channelName) const
250{
251 Ptr<Node> node = Names::Find<Node>(nodeName);
252 Ptr<CsmaChannel> channel = Names::Find<CsmaChannel>(channelName);
253 return NetDeviceContainer(InstallPriv(node, channel));
254}
255
258{
260
261 return Install(c, channel);
262}
263
266{
268
269 for (auto i = c.Begin(); i != c.End(); i++)
270 {
271 devs.Add(InstallPriv(*i, channel));
272 }
273
274 return devs;
275}
276
278CsmaHelper::Install(const NodeContainer& c, std::string channelName) const
279{
280 Ptr<CsmaChannel> channel = Names::Find<CsmaChannel>(channelName);
281 return Install(c, channel);
282}
283
284int64_t
286{
287 int64_t currentStream = stream;
288 Ptr<NetDevice> netDevice;
289 for (auto i = c.Begin(); i != c.End(); ++i)
290 {
291 netDevice = (*i);
293 if (csma)
294 {
295 currentStream += csma->AssignStreams(currentStream);
296 }
297 }
298 return (currentStream - stream);
299}
300
303{
305 device->SetAddress(Mac48Address::Allocate());
306 node->AddDevice(device);
308 device->SetQueue(queue);
309 device->Attach(channel);
311 {
312 // Aggregate a NetDeviceQueueInterface object
314 ndqi->GetTxQueue(0)->ConnectQueueTraces(queue);
315 device->AggregateObject(ndqi);
316 }
317 return device;
318}
319
320} // namespace ns3
Manage ASCII trace files for device models.
void HookDefaultDropSinkWithoutContext(Ptr< T > object, std::string traceName, Ptr< OutputStreamWrapper > stream)
Hook a trace source to the default drop operation trace sink that does not accept nor log a trace con...
std::string GetFilenameFromDevice(std::string prefix, Ptr< NetDevice > device, bool useObjectNames=true)
Let the ascii trace helper figure out a reasonable filename to use for an ascii trace file associated...
static void DefaultDropSinkWithContext(Ptr< OutputStreamWrapper > file, std::string context, Ptr< const Packet > p)
Basic Drop default trace sink.
static void DefaultReceiveSinkWithContext(Ptr< OutputStreamWrapper > file, std::string context, Ptr< const Packet > p)
Basic Receive default trace sink.
Ptr< OutputStreamWrapper > CreateFileStream(std::string filename, std::ios::openmode filemode=std::ios::out)
Create and initialize an output stream object we'll use to write the traced bits.
void HookDefaultEnqueueSinkWithoutContext(Ptr< T > object, std::string traceName, Ptr< OutputStreamWrapper > stream)
Hook a trace source to the default enqueue operation trace sink that does not accept nor log a trace ...
void HookDefaultReceiveSinkWithoutContext(Ptr< T > object, std::string traceName, Ptr< OutputStreamWrapper > stream)
Hook a trace source to the default receive operation trace sink that does not accept nor log a trace ...
static void DefaultEnqueueSinkWithContext(Ptr< OutputStreamWrapper > file, std::string context, Ptr< const Packet > p)
Basic Enqueue default trace sink.
void HookDefaultDequeueSinkWithoutContext(Ptr< T > object, std::string traceName, Ptr< OutputStreamWrapper > stream)
Hook a trace source to the default dequeue operation trace sink that does not accept nor log a trace ...
static void DefaultDequeueSinkWithContext(Ptr< OutputStreamWrapper > file, std::string context, Ptr< const Packet > p)
Basic Dequeue default trace sink.
Hold a value for an Attribute.
Definition attribute.h:59
Csma Channel.
ObjectFactory m_channelFactory
factory for the channel
void SetDeviceAttribute(std::string n1, const AttributeValue &v1)
void EnableAsciiInternal(Ptr< OutputStreamWrapper > stream, std::string prefix, Ptr< NetDevice > nd, bool explicitFilename) override
Enable ascii trace output on the indicated net device.
bool m_enableFlowControl
whether to enable flow control
Ptr< NetDevice > InstallPriv(Ptr< Node > node, Ptr< CsmaChannel > channel) const
This method creates an ns3::CsmaNetDevice with the attributes configured by CsmaHelper::SetDeviceAttr...
void SetChannelAttribute(std::string n1, const AttributeValue &v1)
CsmaHelper()
Construct a CsmaHelper.
int64_t AssignStreams(NetDeviceContainer c, int64_t stream)
Assign a fixed random variable stream number to the random variables used by this model.
NetDeviceContainer Install(Ptr< Node > node) const
This method creates an ns3::CsmaChannel with the attributes configured by CsmaHelper::SetChannelAttri...
void DisableFlowControl()
Disable flow control only if you know what you are doing.
ObjectFactory m_queueFactory
factory for the queues
void EnablePcapInternal(std::string prefix, Ptr< NetDevice > nd, bool promiscuous, bool explicitFilename) override
Enable pcap output on the indicated net device.
ObjectFactory m_deviceFactory
factory for the NetDevices
A Device for a Csma Network Link.
Ptr< Queue< Packet > > GetQueue() const
Get a copy of the attached Queue.
static Mac48Address Allocate()
Allocate a new Mac48Address.
static Ptr< T > Find(std::string path)
Given a name path string, look to see if there's an object in the system with that associated to it.
Definition names.h:443
holds a vector of ns3::NetDevice pointers
Iterator Begin() const
Get an iterator which refers to the first NetDevice in the container.
void Add(NetDeviceContainer other)
Append the contents of another NetDeviceContainer to the end of this container.
Iterator End() const
Get an iterator which indicates past-the-last NetDevice in the container.
keep track of a set of node pointers.
Iterator End() const
Get an iterator which indicates past-the-last Node in the container.
Iterator Begin() const
Get an iterator which refers to the first Node in the container.
Ptr< Object > Create() const
Create an Object instance of the configured TypeId.
void Set(const std::string &name, const AttributeValue &value, Args &&... args)
Set an attribute to be set during construction.
void SetTypeId(TypeId tid)
Set the TypeId of the Objects to be created by this factory.
Ptr< T > GetObject() const
Get a pointer to the requested aggregated Object.
Definition object.h:511
static void EnablePrinting()
Enable printing packets metadata.
Definition packet.cc:585
Manage pcap files for device models.
std::string GetFilenameFromDevice(std::string prefix, Ptr< NetDevice > device, bool useObjectNames=true)
Let the pcap helper figure out a reasonable filename to use for a pcap file associated with a device.
Ptr< PcapFileWrapper > CreateFile(std::string filename, std::ios::openmode filemode, DataLinkType dataLinkType, uint32_t snapLen=std::numeric_limits< uint32_t >::max(), int32_t tzCorrection=0)
Create and initialize a pcap file.
void HookDefaultSink(Ptr< T > object, std::string traceName, Ptr< PcapFileWrapper > file)
Hook a trace source to the default trace sink.
Smart pointer class similar to boost::intrusive_ptr.
Template class for packet Queues.
Definition queue.h:257
void Connect(std::string path, const CallbackBase &cb)
Definition config.cc:967
#define NS_LOG_COMPONENT_DEFINE(name)
Define a Log component with a specific name.
Definition log.h:191
#define NS_LOG_INFO(msg)
Use NS_LOG to output a message of level LOG_INFO.
Definition log.h:264
auto MakeBoundCallback(R(*fnPtr)(Args...), BArgs &&... bargs)
Make Callbacks with varying number of bound arguments.
Definition callback.h:745
Ptr< T > CreateObject(Args &&... args)
Create an object by type, with varying number of constructor parameters.
Definition object.h:619
Every class exported by the ns3 library is enclosed in the ns3 namespace.
Ptr< T1 > DynamicCast(const Ptr< T2 > &p)
Cast a Ptr.
Definition ptr.h:580