A Discrete-Event Network Simulator
QKDNetSim v2.0 (NS-3 v3.41) @ (+)
API
All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Properties Friends Macros Modules Pages
wifi-test-interference-helper.cc
Go to the documentation of this file.
1 /*
2  * Copyright (c) 2015
3  *
4  * This program is free software; you can redistribute it and/or modify
5  * it under the terms of the GNU General Public License version 2 as
6  * published by the Free Software Foundation;
7  *
8  * This program is distributed in the hope that it will be useful,
9  * but WITHOUT ANY WARRANTY; without even the implied warranty of
10  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
11  * GNU General Public License for more details.
12  *
13  * You should have received a copy of the GNU General Public License
14  * along with this program; if not, write to the Free Software
15  * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
16  *
17  * Author: Sébastien Deronne <sebastien.deronne@gmail.com>
18  */
19 
20 //
21 // This script is used to verify the behavior of InterferenceHelper.
22 //
23 // The scenario consists of two IEEE 802.11 hidden stations and an access point.
24 // The two stations have both a packet to transmit to the access point.
25 //
26 //
27 // (xA,0,0) (0,0,0) (xB,0,0)
28 //
29 // * -----> * <----- *
30 // | | |
31 // STA A AP STA B
32 //
33 //
34 // The program can be configured at run-time by passing command-line arguments.
35 // It enables to configure the delay between the transmission from station A
36 // and the transmission from station B (--delay option). It is also possible to
37 // select the tx power level (--txPowerA and --txPowerB options), the packet size
38 // (--packetSizeA and --packetSizeB options) and the modulation (--txModeA and
39 // --txModeB options) used for the respective transmissions.
40 //
41 // By default, IEEE 802.11a with long preamble type is considered, but those
42 // parameters can be also picked among other IEEE 802.11 flavors and preamble
43 // types available in the simulator (--standard and --preamble options).
44 // Note that the program checks the consistency between the selected standard
45 // the selected preamble type.
46 //
47 // The output of the program displays InterfenceHelper and SpectrumWifiPhy trace
48 // logs associated to the chosen scenario.
49 //
50 
51 #include "ns3/command-line.h"
52 #include "ns3/config.h"
53 #include "ns3/constant-position-mobility-model.h"
54 #include "ns3/double.h"
55 #include "ns3/interference-helper.h"
56 #include "ns3/log.h"
57 #include "ns3/nist-error-rate-model.h"
58 #include "ns3/node.h"
59 #include "ns3/packet.h"
60 #include "ns3/propagation-delay-model.h"
61 #include "ns3/propagation-loss-model.h"
62 #include "ns3/simple-frame-capture-model.h"
63 #include "ns3/simulator.h"
64 #include "ns3/single-model-spectrum-channel.h"
65 #include "ns3/spectrum-wifi-phy.h"
66 #include "ns3/wifi-mac-trailer.h"
67 #include "ns3/wifi-net-device.h"
68 #include "ns3/wifi-psdu.h"
69 
70 using namespace ns3;
71 
72 NS_LOG_COMPONENT_DEFINE("test-interference-helper");
73 
74 bool checkResults = false;
75 bool expectRxASuccessful = false;
76 bool expectRxBSuccessful = false;
77 
80 {
81  public:
83  struct Input
84  {
85  Input();
87  double xA;
88  double xB;
89  std::string txModeA;
90  std::string txModeB;
91  double txPowerLevelA;
92  double txPowerLevelB;
93  uint32_t packetSizeA;
94  uint32_t packetSizeB;
95  uint16_t channelA;
96  uint16_t channelB;
97  uint16_t widthA;
98  uint16_t widthB;
103  double captureMargin;
104  };
105 
111  void Run(InterferenceExperiment::Input input);
112 
113  private:
119  void PacketDropped(Ptr<const Packet> packet, WifiPhyRxfailureReason reason);
121  void SendA() const;
123  void SendB() const;
127  bool m_droppedA;
128  bool m_droppedB;
129  mutable uint64_t m_uidA;
130  mutable uint64_t m_uidB;
131 };
132 
133 void
135 {
136  WifiMacHeader hdr;
137  hdr.SetType(WIFI_MAC_CTL_ACK); // so that size may not be empty while being as short as possible
138  Ptr<Packet> p =
139  Create<Packet>(m_input.packetSizeA - hdr.GetSerializedSize() - WIFI_MAC_FCS_LENGTH);
140  m_uidA = p->GetUid();
141  Ptr<WifiPsdu> psdu = Create<WifiPsdu>(p, hdr);
142  WifiTxVector txVector;
143  txVector.SetTxPowerLevel(0); // only one TX power level
144  txVector.SetMode(WifiMode(m_input.txModeA));
145  txVector.SetChannelWidth(m_input.widthA);
146  txVector.SetPreambleType(m_input.preamble);
147  m_txA->Send(psdu, txVector);
148 }
149 
150 void
152 {
153  WifiMacHeader hdr;
154  hdr.SetType(WIFI_MAC_CTL_ACK); // so that size may not be empty while being as short as possible
155  Ptr<Packet> p =
156  Create<Packet>(m_input.packetSizeB - hdr.GetSerializedSize() - WIFI_MAC_FCS_LENGTH);
157  m_uidB = p->GetUid();
158  Ptr<WifiPsdu> psdu = Create<WifiPsdu>(p, hdr);
159  WifiTxVector txVector;
160  txVector.SetTxPowerLevel(0); // only one TX power level
161  txVector.SetMode(WifiMode(m_input.txModeB));
162  txVector.SetChannelWidth(m_input.widthB);
163  txVector.SetPreambleType(m_input.preamble);
164  m_txB->Send(psdu, txVector);
165 }
166 
167 void
169 {
170  if (packet->GetUid() == m_uidA)
171  {
172  m_droppedA = true;
173  }
174  else if (packet->GetUid() == m_uidB)
175  {
176  m_droppedB = true;
177  }
178  else
179  {
180  NS_LOG_ERROR("Unknown packet!");
181  exit(1);
182  }
183 }
184 
186  : m_droppedA(false),
187  m_droppedB(false),
188  m_uidA(0),
189  m_uidB(0)
190 {
191 }
192 
194  : interval(MicroSeconds(0)),
195  xA(-5),
196  xB(5),
197  txModeA("OfdmRate54Mbps"),
198  txModeB("OfdmRate54Mbps"),
199  txPowerLevelA(16.0206),
200  txPowerLevelB(16.0206),
201  packetSizeA(1500),
202  packetSizeB(1500),
203  channelA(36),
204  channelB(36),
205  widthA(20),
206  widthB(20),
207  standard(WIFI_STANDARD_80211a),
208  band(WIFI_PHY_BAND_5GHZ),
209  preamble(WIFI_PREAMBLE_LONG),
210  captureEnabled(false),
211  captureMargin(0)
212 {
213 }
214 
215 void
217 {
218  m_input = input;
219 
220  double maxRange = std::max(std::abs(input.xA), input.xB);
221  Config::SetDefault("ns3::RangePropagationLossModel::MaxRange", DoubleValue(maxRange));
222 
223  Ptr<SingleModelSpectrumChannel> channel = CreateObject<SingleModelSpectrumChannel>();
224  channel->SetPropagationDelayModel(CreateObject<ConstantSpeedPropagationDelayModel>());
225  Ptr<RangePropagationLossModel> loss = CreateObject<RangePropagationLossModel>();
226  channel->AddPropagationLossModel(loss);
227 
228  Ptr<MobilityModel> posTxA = CreateObject<ConstantPositionMobilityModel>();
229  posTxA->SetPosition(Vector(input.xA, 0.0, 0.0));
230  Ptr<MobilityModel> posTxB = CreateObject<ConstantPositionMobilityModel>();
231  posTxB->SetPosition(Vector(input.xB, 0.0, 0.0));
232  Ptr<MobilityModel> posRx = CreateObject<ConstantPositionMobilityModel>();
233  posRx->SetPosition(Vector(0.0, 0.0, 0.0));
234 
235  Ptr<Node> nodeA = CreateObject<Node>();
236  Ptr<WifiNetDevice> devA = CreateObject<WifiNetDevice>();
237  m_txA = CreateObject<SpectrumWifiPhy>();
238  m_txA->SetDevice(devA);
241 
242  Ptr<Node> nodeB = CreateObject<Node>();
243  Ptr<WifiNetDevice> devB = CreateObject<WifiNetDevice>();
244  m_txB = CreateObject<SpectrumWifiPhy>();
245  m_txB->SetDevice(devB);
248 
249  Ptr<Node> nodeRx = CreateObject<Node>();
250  Ptr<WifiNetDevice> devRx = CreateObject<WifiNetDevice>();
251  Ptr<SpectrumWifiPhy> rx = CreateObject<SpectrumWifiPhy>();
252  rx->SetDevice(devRx);
253 
254  Ptr<InterferenceHelper> interferenceTxA = CreateObject<InterferenceHelper>();
255  m_txA->SetInterferenceHelper(interferenceTxA);
256  Ptr<ErrorRateModel> errorTxA = CreateObject<NistErrorRateModel>();
257  m_txA->SetErrorRateModel(errorTxA);
258  Ptr<InterferenceHelper> interferenceTxB = CreateObject<InterferenceHelper>();
259  m_txB->SetInterferenceHelper(interferenceTxB);
260  Ptr<ErrorRateModel> errorTxB = CreateObject<NistErrorRateModel>();
261  m_txB->SetErrorRateModel(errorTxB);
262  Ptr<InterferenceHelper> interferenceRx = CreateObject<InterferenceHelper>();
263  rx->SetInterferenceHelper(interferenceRx);
264  Ptr<ErrorRateModel> errorRx = CreateObject<NistErrorRateModel>();
265  rx->SetErrorRateModel(errorRx);
268  rx->AddChannel(channel);
269  m_txA->SetMobility(posTxA);
270  m_txB->SetMobility(posTxB);
271  rx->SetMobility(posRx);
272  if (input.captureEnabled)
273  {
274  Ptr<SimpleFrameCaptureModel> frameCaptureModel = CreateObject<SimpleFrameCaptureModel>();
275  frameCaptureModel->SetMargin(input.captureMargin);
276  rx->SetFrameCaptureModel(frameCaptureModel);
277  }
278 
281  rx->ConfigureStandard(input.standard);
282 
283  devA->SetPhy(m_txA);
284  nodeA->AddDevice(devA);
285  devB->SetPhy(m_txB);
286  nodeB->AddDevice(devB);
287  devRx->SetPhy(rx);
288  nodeRx->AddDevice(devRx);
289 
293  WifiPhy::ChannelTuple{std::max(input.channelA, input.channelB), 0, input.band, 0});
294 
295  rx->TraceConnectWithoutContext("PhyRxDrop",
297 
298  Simulator::Schedule(Seconds(0), &InterferenceExperiment::SendA, this);
299  Simulator::Schedule(Seconds(0) + input.interval, &InterferenceExperiment::SendB, this);
300 
301  Simulator::Run();
302  Simulator::Destroy();
303  m_txB->Dispose();
304  m_txA->Dispose();
305  rx->Dispose();
306 
308  {
309  NS_LOG_ERROR("Results are not expected!");
310  exit(1);
311  }
312 }
313 
314 int
315 main(int argc, char* argv[])
316 {
318  std::string str_standard = "WIFI_PHY_STANDARD_80211a";
319  std::string str_preamble = "WIFI_PREAMBLE_LONG";
320  uint64_t delay = 0; // microseconds
321 
322  CommandLine cmd(__FILE__);
323  cmd.AddValue("delay",
324  "Delay in microseconds between frame transmission from sender A and frame "
325  "transmission from sender B",
326  delay);
327  cmd.AddValue("xA", "The position of transmitter A (< 0)", input.xA);
328  cmd.AddValue("xB", "The position of transmitter B (> 0)", input.xB);
329  cmd.AddValue("packetSizeA", "Packet size in bytes of transmitter A", input.packetSizeA);
330  cmd.AddValue("packetSizeB", "Packet size in bytes of transmitter B", input.packetSizeB);
331  cmd.AddValue("txPowerA", "TX power level of transmitter A", input.txPowerLevelA);
332  cmd.AddValue("txPowerB", "TX power level of transmitter B", input.txPowerLevelB);
333  cmd.AddValue("txModeA", "Wifi mode used for payload transmission of sender A", input.txModeA);
334  cmd.AddValue("txModeB", "Wifi mode used for payload transmission of sender B", input.txModeB);
335  cmd.AddValue("channelA", "The selected channel number of sender A", input.channelA);
336  cmd.AddValue("channelB", "The selected channel number of sender B", input.channelB);
337  cmd.AddValue("widthA", "The selected channel width (MHz) of sender A", input.widthA);
338  cmd.AddValue("widthB", "The selected channel width (MHz) of sender B", input.widthB);
339  cmd.AddValue("standard", "IEEE 802.11 flavor", str_standard);
340  cmd.AddValue("preamble", "Type of preamble", str_preamble);
341  cmd.AddValue("enableCapture", "Enable/disable physical layer capture", input.captureEnabled);
342  cmd.AddValue("captureMargin", "Margin used for physical layer capture", input.captureMargin);
343  cmd.AddValue("checkResults", "Used to check results at the end of the test", checkResults);
344  cmd.AddValue("expectRxASuccessful",
345  "Indicate whether packet A is expected to be successfully received",
347  cmd.AddValue("expectRxBSuccessful",
348  "Indicate whether packet B is expected to be successfully received",
350  cmd.Parse(argc, argv);
351 
352  input.interval = MicroSeconds(delay);
353 
354  if (input.xA >= 0 || input.xB <= 0)
355  {
356  std::cout << "Value of xA must be smaller than 0 and value of xB must be bigger than 0!"
357  << std::endl;
358  return 0;
359  }
360 
361  if (str_standard == "WIFI_PHY_STANDARD_80211a")
362  {
364  input.band = WIFI_PHY_BAND_5GHZ;
365  }
366  else if (str_standard == "WIFI_PHY_STANDARD_80211b")
367  {
369  input.band = WIFI_PHY_BAND_2_4GHZ;
370  }
371  else if (str_standard == "WIFI_PHY_STANDARD_80211g")
372  {
374  input.band = WIFI_PHY_BAND_2_4GHZ;
375  }
376  else if (str_standard == "WIFI_PHY_STANDARD_80211n_2_4GHZ")
377  {
379  input.band = WIFI_PHY_BAND_2_4GHZ;
380  }
381  else if (str_standard == "WIFI_PHY_STANDARD_80211n_5GHZ")
382  {
384  input.band = WIFI_PHY_BAND_5GHZ;
385  }
386  else if (str_standard == "WIFI_PHY_STANDARD_80211ac")
387  {
389  input.band = WIFI_PHY_BAND_5GHZ;
390  }
391  else if (str_standard == "WIFI_PHY_STANDARD_80211ax_2_4GHZ")
392  {
394  input.band = WIFI_PHY_BAND_2_4GHZ;
395  }
396  else if (str_standard == "WIFI_PHY_STANDARD_80211ax_5GHZ")
397  {
399  input.band = WIFI_PHY_BAND_5GHZ;
400  }
401 
402  if (str_preamble == "WIFI_PREAMBLE_LONG" &&
404  input.standard == WIFI_STANDARD_80211g))
405  {
407  }
408  else if (str_preamble == "WIFI_PREAMBLE_SHORT" &&
410  {
412  }
413  else if (str_preamble == "WIFI_PREAMBLE_HT_MF" && input.standard == WIFI_STANDARD_80211n)
414  {
416  }
417  else if (str_preamble == "WIFI_PREAMBLE_VHT_SU" && input.standard == WIFI_STANDARD_80211ac)
418  {
420  }
421  else if (str_preamble == "WIFI_PREAMBLE_HE_SU" && input.standard == WIFI_STANDARD_80211ax)
422  {
424  }
425  else
426  {
427  std::cout << "Preamble does not exist or is not compatible with the selected standard!"
428  << std::endl;
429  return 0;
430  }
431 
433  experiment.Run(input);
434 
435  return 0;
436 }
#define max(a, b)
Definition: 80211b.c:42
Ptr< SpectrumWifiPhy > m_txA
transmit A function
bool m_droppedB
flag to indicate whether packet B has been dropped
uint64_t m_uidB
UID to use for packet B.
bool m_droppedA
flag to indicate whether packet A has been dropped
void SendB() const
Send B function.
void PacketDropped(Ptr< const Packet > packet, WifiPhyRxfailureReason reason)
Function triggered when a packet is dropped.
Ptr< SpectrumWifiPhy > m_txB
transmit B function
uint64_t m_uidA
UID to use for packet A.
void SendA() const
Send A function.
void Run(InterferenceExperiment::Input input)
Run function.
Parse command-line arguments.
Definition: command-line.h:232
This class can be used to hold variables of floating point type such as 'double' or 'float'.
Definition: double.h:42
void SetPosition(const Vector &position)
uint32_t AddDevice(Ptr< NetDevice > device)
Associate a NetDevice to this node.
Definition: node.cc:138
bool TraceConnectWithoutContext(std::string name, const CallbackBase &cb)
Connect a TraceSource to a Callback without a context.
Definition: object-base.cc:315
void Dispose()
Dispose of this Object.
Definition: object.cc:219
uint64_t GetUid() const
Returns the packet's Uid.
Definition: packet.cc:412
void SetDevice(const Ptr< WifiNetDevice > device) override
Sets the device this PHY is associated with.
void AddChannel(const Ptr< SpectrumChannel > channel, const FrequencyRange &freqRange=WHOLE_WIFI_SPECTRUM)
Attach a SpectrumChannel to use for a given frequency range.
Simulation virtual time values and global simulation resolution.
Definition: nstime.h:105
Implements the IEEE 802.11 MAC header.
uint32_t GetSerializedSize() const override
virtual void SetType(WifiMacType type, bool resetToDsFromDs=true)
Set Type/Subtype values with the correct values depending on the given type.
represent a single transmission mode
Definition: wifi-mode.h:51
void SetPhy(const Ptr< WifiPhy > phy)
virtual void SetInterferenceHelper(const Ptr< InterferenceHelper > helper)
Sets the interference helper.
Definition: wifi-phy.cc:631
void SetErrorRateModel(const Ptr< ErrorRateModel > model)
Sets the error rate model.
Definition: wifi-phy.cc:639
virtual void ConfigureStandard(WifiStandard standard)
Configure the PHY-level parameters for different Wi-Fi standard.
Definition: wifi-phy.cc:961
void SetOperatingChannel(const ChannelTuple &channelTuple)
If the standard for this object has not been set yet, store the given channel settings.
Definition: wifi-phy.cc:1098
void SetTxPowerEnd(double end)
Sets the maximum available transmission power level (dBm).
Definition: wifi-phy.cc:542
std::tuple< uint8_t, uint16_t, WifiPhyBand, uint8_t > ChannelTuple
Tuple identifying an operating channel.
Definition: wifi-phy.h:891
void SetMobility(const Ptr< MobilityModel > mobility)
assign a mobility model to this device
Definition: wifi-phy.cc:619
void SetFrameCaptureModel(const Ptr< FrameCaptureModel > frameCaptureModel)
Sets the frame capture model.
Definition: wifi-phy.cc:653
void SetTxPowerStart(double start)
Sets the minimum available transmission power level (dBm).
Definition: wifi-phy.cc:529
This class mimics the TXVECTOR which is to be passed to the PHY in order to define the parameters whi...
void SetTxPowerLevel(uint8_t powerlevel)
Sets the selected transmission power level.
void SetChannelWidth(uint16_t channelWidth)
Sets the selected channelWidth (in MHz)
void SetMode(WifiMode mode)
Sets the selected payload transmission mode.
void SetPreambleType(WifiPreamble preamble)
Sets the preamble type.
void experiment(std::string queue_disc_type)
void SetDefault(std::string name, const AttributeValue &value)
Definition: config.cc:890
#define NS_LOG_ERROR(msg)
Use NS_LOG to output a message of level LOG_ERROR.
Definition: log.h:254
#define NS_LOG_COMPONENT_DEFINE(name)
Define a Log component with a specific name.
Definition: log.h:202
Time MicroSeconds(uint64_t value)
Construct a Time in the indicated unit.
Definition: nstime.h:1350
Time Seconds(double value)
Construct a Time in the indicated unit.
Definition: nstime.h:1326
WifiStandard
Identifies the IEEE 802.11 specifications that a Wifi device can be configured to use.
WifiPhyRxfailureReason
Enumeration of the possible reception failure reasons.
WifiPreamble
The type of preamble to be used by an IEEE 802.11 transmission.
WifiPhyBand
Identifies the PHY band.
Definition: wifi-phy-band.h:33
@ WIFI_STANDARD_80211a
@ WIFI_STANDARD_80211n
@ WIFI_STANDARD_80211g
@ WIFI_STANDARD_80211ax
@ WIFI_STANDARD_80211ac
@ WIFI_STANDARD_80211b
@ WIFI_PREAMBLE_LONG
@ WIFI_PREAMBLE_HE_SU
@ WIFI_PREAMBLE_VHT_SU
@ WIFI_PREAMBLE_SHORT
@ WIFI_PREAMBLE_HT_MF
@ WIFI_PHY_BAND_2_4GHZ
The 2.4 GHz band.
Definition: wifi-phy-band.h:35
@ WIFI_PHY_BAND_5GHZ
The 5 GHz band.
Definition: wifi-phy-band.h:37
Every class exported by the ns3 library is enclosed in the ns3 namespace.
static const uint16_t WIFI_MAC_FCS_LENGTH
The length in octets of the IEEE 802.11 MAC FCS field.
Callback< R, Args... > MakeCallback(R(T::*memPtr)(Args...), OBJ objPtr)
Build Callbacks for class method members which take varying numbers of arguments and potentially retu...
Definition: callback.h:704
@ WIFI_MAC_CTL_ACK
cmd
Definition: second.py:40
channel
Definition: third.py:88
double txPowerLevelA
transmit power level A
double txPowerLevelB
transmit power level B
bool captureEnabled
whether physical layer capture is enabled
double captureMargin
margin used for physical layer capture
bool expectRxASuccessful
True if Rx from A is expected to be successful.
bool expectRxBSuccessful
True if Rx from B is expected to be successful.
bool checkResults
True if results have to be checked.