A Discrete-Event Network Simulator
API
Loading...
Searching...
No Matches
complete-network-example.cc
Go to the documentation of this file.
1/*
2 * Copyright (c) 2017 University of Padova
3 *
4 * SPDX-License-Identifier: GPL-2.0-only
5 *
6 * Author: Davide Magrin <magrinda@dei.unipd.it>
7 */
8
9/*
10 * This script simulates a complex scenario with multiple gateways and end
11 * devices. The metric of interest for this script is the throughput of the
12 * network.
13 */
14
15#include "ns3/buildings-module.h"
16#include "ns3/core-module.h"
17#include "ns3/lorawan-module.h"
18#include "ns3/mobility-helper.h"
19#include "ns3/point-to-point-helper.h"
20
21using namespace ns3;
22using namespace lorawan;
23
24NS_LOG_COMPONENT_DEFINE("ComplexLorawanNetworkExample");
25
26// Network settings
27int nDevices = 200; //!< Number of end device nodes to create
28int nGateways = 1; //!< Number of gateway nodes to create
29double radiusMeters = 6400; //!< Radius (m) of the deployment
30double simulationTimeSeconds = 600; //!< Scenario duration (s) in simulated time
31
32// Channel model
33bool realisticChannelModel = false; //!< Whether to use a more realistic channel model with
34 //!< Buildings and correlated shadowing
35
36int appPeriodSeconds = 600; //!< Duration (s) of the inter-transmission time of end devices
37
38// Output control
39bool printBuildingInfo = true; //!< Whether to print building information
40
41int
42main(int argc, char* argv[])
43{
44 CommandLine cmd(__FILE__);
45 cmd.AddValue("nDevices", "Number of end devices to include in the simulation", nDevices);
46 cmd.AddValue("radius", "The radius (m) of the area to simulate", radiusMeters);
47 cmd.AddValue("realisticChannel",
48 "Whether to use a more realistic channel model",
50 cmd.AddValue("simulationTime", "The time (s) for which to simulate", simulationTimeSeconds);
51 cmd.AddValue("appPeriod",
52 "The period in seconds to be used by periodically transmitting applications",
54 cmd.AddValue("print", "Whether or not to print building information", printBuildingInfo);
55 cmd.Parse(argc, argv);
56
57 // Set up logging
58 LogComponentEnable("ComplexLorawanNetworkExample", LOG_LEVEL_ALL);
59 // LogComponentEnable("LoraChannel", LOG_LEVEL_INFO);
60 // LogComponentEnable("LoraPhy", LOG_LEVEL_ALL);
61 // LogComponentEnable("EndDeviceLoraPhy", LOG_LEVEL_ALL);
62 // LogComponentEnable("GatewayLoraPhy", LOG_LEVEL_ALL);
63 // LogComponentEnable("LoraInterferenceHelper", LOG_LEVEL_ALL);
64 // LogComponentEnable("LorawanMac", LOG_LEVEL_ALL);
65 // LogComponentEnable("EndDeviceLorawanMac", LOG_LEVEL_ALL);
66 // LogComponentEnable("ClassAEndDeviceLorawanMac", LOG_LEVEL_ALL);
67 // LogComponentEnable("GatewayLorawanMac", LOG_LEVEL_ALL);
68 // LogComponentEnable("LogicalLoraChannelHelper", LOG_LEVEL_ALL);
69 // LogComponentEnable("LogicalLoraChannel", LOG_LEVEL_ALL);
70 // LogComponentEnable("LoraHelper", LOG_LEVEL_ALL);
71 // LogComponentEnable("LoraPhyHelper", LOG_LEVEL_ALL);
72 // LogComponentEnable("LorawanMacHelper", LOG_LEVEL_ALL);
73 // LogComponentEnable("PeriodicSenderHelper", LOG_LEVEL_ALL);
74 // LogComponentEnable("PeriodicSender", LOG_LEVEL_ALL);
75 // LogComponentEnable("LorawanMacHeader", LOG_LEVEL_ALL);
76 // LogComponentEnable("LoraFrameHeader", LOG_LEVEL_ALL);
77 // LogComponentEnable("NetworkScheduler", LOG_LEVEL_ALL);
78 // LogComponentEnable("NetworkServer", LOG_LEVEL_ALL);
79 // LogComponentEnable("NetworkStatus", LOG_LEVEL_ALL);
80 // LogComponentEnable("NetworkController", LOG_LEVEL_ALL);
81
82 /***********
83 * Setup *
84 ***********/
85
86 // Create the time value from the period
87 Time appPeriod = Seconds(appPeriodSeconds);
88
89 // Mobility
90 MobilityHelper mobility;
91 mobility.SetPositionAllocator("ns3::UniformDiscPositionAllocator",
92 "rho",
94 "X",
95 DoubleValue(0.0),
96 "Y",
97 DoubleValue(0.0));
98 mobility.SetMobilityModel("ns3::ConstantPositionMobilityModel");
99
100 /************************
101 * Create the channel *
102 ************************/
103
104 // Create the lora channel object
106 loss->SetPathLossExponent(3.76);
107 loss->SetReference(1, 7.7);
108
110 {
111 // Create the correlated shadowing component
114
115 // Aggregate shadowing to the logdistance loss
116 loss->SetNext(shadowing);
117
118 // Add the effect to the channel propagation loss
120
121 shadowing->SetNext(buildingLoss);
122 }
123
125
126 Ptr<LoraChannel> channel = CreateObject<LoraChannel>(loss, delay);
127
128 /************************
129 * Create the helpers *
130 ************************/
131
132 // Create the LoraPhyHelper
133 LoraPhyHelper phyHelper = LoraPhyHelper();
134 phyHelper.SetChannel(channel);
135
136 // Create the LorawanMacHelper
138
139 // Create the LoraHelper
140 LoraHelper helper = LoraHelper();
141 helper.EnablePacketTracking(); // Output filename
142 // helper.EnableSimulationTimePrinting ();
143
144 // Create the NetworkServerHelper
146
147 // Create the ForwarderHelper
148 ForwarderHelper forHelper = ForwarderHelper();
149
150 /************************
151 * Create End Devices *
152 ************************/
153
154 // Create a set of nodes
155 NodeContainer endDevices;
156 endDevices.Create(nDevices);
157
158 // Assign a mobility model to each node
159 mobility.Install(endDevices);
160
161 // Make it so that nodes are at a certain height > 0
162 for (auto j = endDevices.Begin(); j != endDevices.End(); ++j)
163 {
164 Ptr<MobilityModel> mobility = (*j)->GetObject<MobilityModel>();
165 Vector position = mobility->GetPosition();
166 position.z = 1.2;
167 mobility->SetPosition(position);
168 }
169
170 // Create the LoraNetDevices of the end devices
171 uint8_t nwkId = 54;
172 uint32_t nwkAddr = 1864;
175
176 // Create the LoraNetDevices of the end devices
177 macHelper.SetAddressGenerator(addrGen);
180 helper.Install(phyHelper, macHelper, endDevices);
181
182 // Now end devices are connected to the channel
183
184 // Connect trace sources
185 for (auto j = endDevices.Begin(); j != endDevices.End(); ++j)
186 {
187 Ptr<Node> node = *j;
188 Ptr<LoraNetDevice> loraNetDevice = DynamicCast<LoraNetDevice>(node->GetDevice(0));
189 Ptr<LoraPhy> phy = loraNetDevice->GetPhy();
190 }
191
192 /*********************
193 * Create Gateways *
194 *********************/
195
196 // Create the gateway nodes (allocate them uniformly on the disc)
197 NodeContainer gateways;
198 gateways.Create(nGateways);
199
201 // Make it so that nodes are at a certain height > 0
202 allocator->Add(Vector(0.0, 0.0, 15.0));
203 mobility.SetPositionAllocator(allocator);
204 mobility.Install(gateways);
205
206 // Create a netdevice for each gateway
209 helper.Install(phyHelper, macHelper, gateways);
210
211 /**********************
212 * Handle buildings *
213 **********************/
214
215 double xLength = 130;
216 double deltaX = 32;
217 double yLength = 64;
218 double deltaY = 17;
219 int gridWidth = 2 * radiusMeters / (xLength + deltaX);
220 int gridHeight = 2 * radiusMeters / (yLength + deltaY);
222 {
223 gridWidth = 0;
224 gridHeight = 0;
225 }
226 Ptr<GridBuildingAllocator> gridBuildingAllocator;
227 gridBuildingAllocator = CreateObject<GridBuildingAllocator>();
228 gridBuildingAllocator->SetAttribute("GridWidth", UintegerValue(gridWidth));
229 gridBuildingAllocator->SetAttribute("LengthX", DoubleValue(xLength));
230 gridBuildingAllocator->SetAttribute("LengthY", DoubleValue(yLength));
231 gridBuildingAllocator->SetAttribute("DeltaX", DoubleValue(deltaX));
232 gridBuildingAllocator->SetAttribute("DeltaY", DoubleValue(deltaY));
233 gridBuildingAllocator->SetAttribute("Height", DoubleValue(6));
234 gridBuildingAllocator->SetBuildingAttribute("NRoomsX", UintegerValue(2));
235 gridBuildingAllocator->SetBuildingAttribute("NRoomsY", UintegerValue(4));
236 gridBuildingAllocator->SetBuildingAttribute("NFloors", UintegerValue(2));
237 gridBuildingAllocator->SetAttribute(
238 "MinX",
239 DoubleValue(-gridWidth * (xLength + deltaX) / 2 + deltaX / 2));
240 gridBuildingAllocator->SetAttribute(
241 "MinY",
242 DoubleValue(-gridHeight * (yLength + deltaY) / 2 + deltaY / 2));
243 BuildingContainer bContainer = gridBuildingAllocator->Create(gridWidth * gridHeight);
244
245 BuildingsHelper::Install(endDevices);
246 BuildingsHelper::Install(gateways);
247
248 // Print the buildings
250 {
251 std::ofstream myfile;
252 myfile.open("buildings.txt");
253 std::vector<Ptr<Building>>::const_iterator it;
254 int j = 1;
255 for (it = bContainer.Begin(); it != bContainer.End(); ++it, ++j)
256 {
257 Box boundaries = (*it)->GetBoundaries();
258 myfile << "set object " << j << " rect from " << boundaries.xMin << ","
259 << boundaries.yMin << " to " << boundaries.xMax << "," << boundaries.yMax
260 << std::endl;
261 }
262 myfile.close();
263 }
264
265 /**********************************************
266 * Set up the end device's spreading factor *
267 **********************************************/
268
269 LorawanMacHelper::SetSpreadingFactorsUp(endDevices, gateways, channel);
270
271 NS_LOG_DEBUG("Completed configuration");
272
273 /*********************************************
274 * Install applications on the end devices *
275 *********************************************/
276
277 Time appStopTime = Seconds(simulationTimeSeconds);
280 appHelper.SetPacketSize(23);
283 DoubleValue(0),
284 "Max",
285 DoubleValue(10));
286 ApplicationContainer appContainer = appHelper.Install(endDevices);
287
288 appContainer.Start(Time(0));
289 appContainer.Stop(appStopTime);
290
291 /**************************
292 * Create network server *
293 ***************************/
294
295 // Create the network server node
296 Ptr<Node> networkServer = CreateObject<Node>();
297
298 // PointToPoint links between gateways and server
300 p2p.SetDeviceAttribute("DataRate", StringValue("5Mbps"));
301 p2p.SetChannelAttribute("Delay", StringValue("2ms"));
302 // Store network server app registration details for later
303 P2PGwRegistration_t gwRegistration;
304 for (auto gw = gateways.Begin(); gw != gateways.End(); ++gw)
305 {
306 auto container = p2p.Install(networkServer, *gw);
307 auto serverP2PNetDev = DynamicCast<PointToPointNetDevice>(container.Get(0));
308 gwRegistration.emplace_back(serverP2PNetDev, *gw);
309 }
310
311 // Create a network server for the network
312 nsHelper.SetGatewaysP2P(gwRegistration);
313 nsHelper.SetEndDevices(endDevices);
314 nsHelper.Install(networkServer);
315
316 // Create a forwarder for each gateway
317 forHelper.Install(gateways);
318
319 ////////////////
320 // Simulation //
321 ////////////////
322
323 Simulator::Stop(appStopTime + Hours(1));
324
325 NS_LOG_INFO("Running simulation...");
327
329
330 ///////////////////////////
331 // Print results to file //
332 ///////////////////////////
333 NS_LOG_INFO("Computing performance metrics...");
334
335 LoraPacketTracker& tracker = helper.GetPacketTracker();
336 std::cout << tracker.CountMacPacketsGlobally(Time(0), appStopTime + Hours(1)) << std::endl;
337
338 return 0;
339}
holds a vector of ns3::Application pointers.
void Start(Time start) const
Start all of the Applications in this container at the start time given as a parameter.
void Stop(Time stop) const
Arrange for all of the Applications in this container to Stop() at the Time given as a parameter.
a 3d box
Definition box.h:24
double yMax
The y coordinate of the top bound of the box.
Definition box.h:105
double xMin
The x coordinate of the left bound of the box.
Definition box.h:99
double yMin
The y coordinate of the bottom bound of the box.
Definition box.h:103
double xMax
The x coordinate of the right bound of the box.
Definition box.h:101
keep track of a set of building pointers.
Iterator End() const
Get an iterator which indicates past-the-last Building in the container.
Iterator Begin() const
Get an iterator which refers to the first Building in the container.
static void Install(Ptr< Node > node)
Install the MobilityBuildingInfo to a node.
Parse command-line arguments.
This class can be used to hold variables of floating point type such as 'double' or 'float'.
Definition double.h:31
Helper class used to assign positions and mobility models to nodes.
Keep track of the current position and velocity of an object.
keep track of a set of node pointers.
Iterator End() const
Get an iterator which indicates past-the-last Node in the container.
void Create(uint32_t n)
Create n nodes and append pointers to them to the end of this NodeContainer.
Iterator Begin() const
Get an iterator which refers to the first Node in the container.
Build a set of PointToPointNetDevice objects.
Smart pointer class similar to boost::intrusive_ptr.
Definition ptr.h:70
static void Destroy()
Execute the events scheduled with ScheduleDestroy().
Definition simulator.cc:125
static void Run()
Run the simulation.
Definition simulator.cc:161
static void Stop()
Tell the Simulator the calling event should be the last one executed.
Definition simulator.cc:169
Hold variables of type string.
Definition string.h:45
Simulation virtual time values and global simulation resolution.
Definition nstime.h:95
Hold an unsigned integer type.
Definition uinteger.h:34
This class can be used to install Forwarder applications on a set of gateways.
ApplicationContainer Install(NodeContainer c) const
Install a Forwarder application on each node of the input container configured with all the attribute...
Helps to create LoraNetDevice objects.
Definition lora-helper.h:34
void EnablePacketTracking()
Enable tracking of packets via trace sources.
LoraPacketTracker & GetPacketTracker()
Get a reference to the Packet Tracker object.
virtual NetDeviceContainer Install(const LoraPhyHelper &phyHelper, const LorawanMacHelper &macHelper, NodeContainer c) const
Install LoraNetDevices on a list of nodes.
Tracks and stores packets sent in the simulation and provides aggregation functionality.
std::string CountMacPacketsGlobally(Time startTime, Time stopTime)
In a time interval, count packets to evaluate the global performance at MAC level of the whole networ...
Helper to install LoraPhy instances on multiple Nodes.
void SetDeviceType(enum DeviceType dt)
Set the kind of PHY this helper will create.
void SetChannel(Ptr< LoraChannel > channel)
Set the LoraChannel to connect the PHYs to.
Helper class for configuring and installing the LorawanMac class on devices and gateways.
void SetDeviceType(enum DeviceType dt)
Set the kind of MAC this helper will create.
void SetAddressGenerator(Ptr< LoraDeviceAddressGenerator > addrGen)
Set the address generator to use for creation of these nodes.
static std::vector< int > SetSpreadingFactorsUp(NodeContainer endDevices, NodeContainer gateways, Ptr< LoraChannel > channel)
Initialize the end devices' data rate parameter.
This class can install a NetworkServer application on a node.
void SetGatewaysP2P(const P2PGwRegistration_t &registration)
Register gateways connected with point-to-point to this network server.
void SetEndDevices(NodeContainer endDevices)
Set which end devices will be managed by this network server.
ApplicationContainer Install(Ptr< Node > node)
Create one lorawan network server application on the Node.
This class can be used to install PeriodicSender applications on a wide range of nodes.
void SetPeriod(Time period)
Set the period to be used by the applications created by this helper.
void SetPacketSize(uint8_t size)
Set the base value for applications packet size in bytes.
ApplicationContainer Install(NodeContainer c) const
Install a PeriodicSender application on each node of the input container configured with all the attr...
double simulationTimeSeconds
Scenario duration (s) in simulated time.
int nDevices
Number of end device nodes to create.
bool realisticChannelModel
Whether to use a more realistic channel model with buildings and correlated shadowing.
int nGateways
Number of gateway nodes to create.
double radiusMeters
Radius (m) of the deployment.
bool printBuildingInfo
Whether to print building information.
int appPeriodSeconds
Duration (s) of the inter-transmission time of end devices.
#define NS_LOG_COMPONENT_DEFINE(name)
Define a Log component with a specific name.
Definition log.h:194
#define NS_LOG_DEBUG(msg)
Use NS_LOG to output a message of level LOG_DEBUG.
Definition log.h:260
#define NS_LOG_INFO(msg)
Use NS_LOG to output a message of level LOG_INFO.
Definition log.h:267
Ptr< T > CreateObject(Args &&... args)
Create an object by type, with varying number of constructor parameters.
Definition object.h:627
Ptr< T > CreateObjectWithAttributes(Args... args)
Allocate an Object on the heap and initialize with a set of attributes.
Time Seconds(double value)
Construct a Time in the indicated unit.
Definition nstime.h:1273
Time Hours(double value)
Construct a Time in the indicated unit.
Definition nstime.h:1244
std::list< std::pair< Ptr< PointToPointNetDevice >, Ptr< Node > > > P2PGwRegistration_t
Store network server app registration details for gateway nodes having a P2P link with the network se...
Every class exported by the ns3 library is enclosed in the ns3 namespace.
void LogComponentEnable(const std::string &name, LogLevel level)
Enable the logging output associated with that log component.
Definition log.cc:279
Ptr< T1 > DynamicCast(const Ptr< T2 > &p)
Cast a Ptr.
Definition ptr.h:605
@ LOG_LEVEL_ALL
Print everything.
Definition log.h:108