A Discrete-Event Network Simulator
API
wifi-phy.cc
Go to the documentation of this file.
1 /* -*- Mode:C++; c-file-style:"gnu"; indent-tabs-mode:nil; -*- */
2 /*
3  * Copyright (c) 2005,2006 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: Mathieu Lacage <mathieu.lacage@sophia.inria.fr>
19  * Sébastien Deronne <sebastien.deronne@gmail.com>
20  */
21 
22 #include "ns3/simulator.h"
23 #include "ns3/log.h"
24 #include "ns3/pointer.h"
25 #include "ns3/mobility-model.h"
26 #include "ns3/random-variable-stream.h"
27 #include "ns3/error-model.h"
28 #include "wifi-phy.h"
29 #include "ampdu-tag.h"
30 #include "wifi-utils.h"
31 #include "frame-capture-model.h"
34 #include "error-rate-model.h"
35 #include "wifi-net-device.h"
36 #include "ht-configuration.h"
37 #include "he-configuration.h"
38 #include "mpdu-aggregator.h"
39 #include "wifi-psdu.h"
40 #include "wifi-ppdu.h"
41 
42 namespace ns3 {
43 
44 NS_LOG_COMPONENT_DEFINE ("WifiPhy");
45 
46 /****************************************************************
47  * The actual WifiPhy class
48  ****************************************************************/
49 
51 
61 {
62  // 802.11b uses width of 22, while OFDM modes use width of 20
63  { std::make_pair (1, WIFI_PHY_STANDARD_80211b), std::make_pair (2412, 22) },
64  { std::make_pair (1, WIFI_PHY_STANDARD_UNSPECIFIED), std::make_pair (2412, 20) },
65  { std::make_pair (2, WIFI_PHY_STANDARD_80211b), std::make_pair (2417, 22) },
66  { std::make_pair (2, WIFI_PHY_STANDARD_UNSPECIFIED), std::make_pair (2417, 20) },
67  { std::make_pair (3, WIFI_PHY_STANDARD_80211b), std::make_pair (2422, 22) },
68  { std::make_pair (3, WIFI_PHY_STANDARD_UNSPECIFIED), std::make_pair (2422, 20) },
69  { std::make_pair (4, WIFI_PHY_STANDARD_80211b), std::make_pair (2427, 22) },
70  { std::make_pair (4, WIFI_PHY_STANDARD_UNSPECIFIED), std::make_pair (2427, 20) },
71  { std::make_pair (5, WIFI_PHY_STANDARD_80211b), std::make_pair (2432, 22) },
72  { std::make_pair (5, WIFI_PHY_STANDARD_UNSPECIFIED), std::make_pair (2432, 20) },
73  { std::make_pair (6, WIFI_PHY_STANDARD_80211b), std::make_pair (2437, 22) },
74  { std::make_pair (6, WIFI_PHY_STANDARD_UNSPECIFIED), std::make_pair (2437, 20) },
75  { std::make_pair (7, WIFI_PHY_STANDARD_80211b), std::make_pair (2442, 22) },
76  { std::make_pair (7, WIFI_PHY_STANDARD_UNSPECIFIED), std::make_pair (2442, 20) },
77  { std::make_pair (8, WIFI_PHY_STANDARD_80211b), std::make_pair (2447, 22) },
78  { std::make_pair (8, WIFI_PHY_STANDARD_UNSPECIFIED), std::make_pair (2447, 20) },
79  { std::make_pair (9, WIFI_PHY_STANDARD_80211b), std::make_pair (2452, 22) },
80  { std::make_pair (9, WIFI_PHY_STANDARD_UNSPECIFIED), std::make_pair (2452, 20) },
81  { std::make_pair (10, WIFI_PHY_STANDARD_80211b), std::make_pair (2457, 22) },
82  { std::make_pair (10, WIFI_PHY_STANDARD_UNSPECIFIED), std::make_pair (2457, 20) },
83  { std::make_pair (11, WIFI_PHY_STANDARD_80211b), std::make_pair (2462, 22) },
84  { std::make_pair (11, WIFI_PHY_STANDARD_UNSPECIFIED), std::make_pair (2462, 20) },
85  { std::make_pair (12, WIFI_PHY_STANDARD_80211b), std::make_pair (2467, 22) },
86  { std::make_pair (12, WIFI_PHY_STANDARD_UNSPECIFIED), std::make_pair (2467, 20) },
87  { std::make_pair (13, WIFI_PHY_STANDARD_80211b), std::make_pair (2472, 22) },
88  { std::make_pair (13, WIFI_PHY_STANDARD_UNSPECIFIED), std::make_pair (2472, 20) },
89  // Only defined for 802.11b
90  { std::make_pair (14, WIFI_PHY_STANDARD_80211b), std::make_pair (2484, 22) },
91 
92  // Now the 5GHz channels; UNSPECIFIED for 802.11a/n/ac/ax channels
93  // 20 MHz channels
94  { std::make_pair (36, WIFI_PHY_STANDARD_UNSPECIFIED), std::make_pair (5180, 20) },
95  { std::make_pair (40, WIFI_PHY_STANDARD_UNSPECIFIED), std::make_pair (5200, 20) },
96  { std::make_pair (44, WIFI_PHY_STANDARD_UNSPECIFIED), std::make_pair (5220, 20) },
97  { std::make_pair (48, WIFI_PHY_STANDARD_UNSPECIFIED), std::make_pair (5240, 20) },
98  { std::make_pair (52, WIFI_PHY_STANDARD_UNSPECIFIED), std::make_pair (5260, 20) },
99  { std::make_pair (56, WIFI_PHY_STANDARD_UNSPECIFIED), std::make_pair (5280, 20) },
100  { std::make_pair (60, WIFI_PHY_STANDARD_UNSPECIFIED), std::make_pair (5300, 20) },
101  { std::make_pair (64, WIFI_PHY_STANDARD_UNSPECIFIED), std::make_pair (5320, 20) },
102  { std::make_pair (100, WIFI_PHY_STANDARD_UNSPECIFIED), std::make_pair (5500, 20) },
103  { std::make_pair (104, WIFI_PHY_STANDARD_UNSPECIFIED), std::make_pair (5520, 20) },
104  { std::make_pair (108, WIFI_PHY_STANDARD_UNSPECIFIED), std::make_pair (5540, 20) },
105  { std::make_pair (112, WIFI_PHY_STANDARD_UNSPECIFIED), std::make_pair (5560, 20) },
106  { std::make_pair (116, WIFI_PHY_STANDARD_UNSPECIFIED), std::make_pair (5580, 20) },
107  { std::make_pair (120, WIFI_PHY_STANDARD_UNSPECIFIED), std::make_pair (5600, 20) },
108  { std::make_pair (124, WIFI_PHY_STANDARD_UNSPECIFIED), std::make_pair (5620, 20) },
109  { std::make_pair (128, WIFI_PHY_STANDARD_UNSPECIFIED), std::make_pair (5640, 20) },
110  { std::make_pair (132, WIFI_PHY_STANDARD_UNSPECIFIED), std::make_pair (5660, 20) },
111  { std::make_pair (136, WIFI_PHY_STANDARD_UNSPECIFIED), std::make_pair (5680, 20) },
112  { std::make_pair (140, WIFI_PHY_STANDARD_UNSPECIFIED), std::make_pair (5700, 20) },
113  { std::make_pair (144, WIFI_PHY_STANDARD_UNSPECIFIED), std::make_pair (5720, 20) },
114  { std::make_pair (149, WIFI_PHY_STANDARD_UNSPECIFIED), std::make_pair (5745, 20) },
115  { std::make_pair (153, WIFI_PHY_STANDARD_UNSPECIFIED), std::make_pair (5765, 20) },
116  { std::make_pair (157, WIFI_PHY_STANDARD_UNSPECIFIED), std::make_pair (5785, 20) },
117  { std::make_pair (161, WIFI_PHY_STANDARD_UNSPECIFIED), std::make_pair (5805, 20) },
118  { std::make_pair (165, WIFI_PHY_STANDARD_UNSPECIFIED), std::make_pair (5825, 20) },
119  { std::make_pair (169, WIFI_PHY_STANDARD_UNSPECIFIED), std::make_pair (5845, 20) },
120  { std::make_pair (173, WIFI_PHY_STANDARD_UNSPECIFIED), std::make_pair (5865, 20) },
121  { std::make_pair (177, WIFI_PHY_STANDARD_UNSPECIFIED), std::make_pair (5885, 20) },
122  { std::make_pair (181, WIFI_PHY_STANDARD_UNSPECIFIED), std::make_pair (5905, 20) },
123  // 40 MHz channels
124  { std::make_pair (38, WIFI_PHY_STANDARD_UNSPECIFIED), std::make_pair (5190, 40) },
125  { std::make_pair (46, WIFI_PHY_STANDARD_UNSPECIFIED), std::make_pair (5230, 40) },
126  { std::make_pair (54, WIFI_PHY_STANDARD_UNSPECIFIED), std::make_pair (5270, 40) },
127  { std::make_pair (62, WIFI_PHY_STANDARD_UNSPECIFIED), std::make_pair (5310, 40) },
128  { std::make_pair (102, WIFI_PHY_STANDARD_UNSPECIFIED), std::make_pair (5510, 40) },
129  { std::make_pair (110, WIFI_PHY_STANDARD_UNSPECIFIED), std::make_pair (5550, 40) },
130  { std::make_pair (118, WIFI_PHY_STANDARD_UNSPECIFIED), std::make_pair (5590, 40) },
131  { std::make_pair (126, WIFI_PHY_STANDARD_UNSPECIFIED), std::make_pair (5630, 40) },
132  { std::make_pair (134, WIFI_PHY_STANDARD_UNSPECIFIED), std::make_pair (5670, 40) },
133  { std::make_pair (142, WIFI_PHY_STANDARD_UNSPECIFIED), std::make_pair (5710, 40) },
134  { std::make_pair (151, WIFI_PHY_STANDARD_UNSPECIFIED), std::make_pair (5755, 40) },
135  { std::make_pair (159, WIFI_PHY_STANDARD_UNSPECIFIED), std::make_pair (5795, 40) },
136  { std::make_pair (167, WIFI_PHY_STANDARD_UNSPECIFIED), std::make_pair (5835, 40) },
137  { std::make_pair (175, WIFI_PHY_STANDARD_UNSPECIFIED), std::make_pair (5875, 40) },
138  // 80 MHz channels
139  { std::make_pair (42, WIFI_PHY_STANDARD_UNSPECIFIED), std::make_pair (5210, 80) },
140  { std::make_pair (58, WIFI_PHY_STANDARD_UNSPECIFIED), std::make_pair (5290, 80) },
141  { std::make_pair (106, WIFI_PHY_STANDARD_UNSPECIFIED), std::make_pair (5530, 80) },
142  { std::make_pair (122, WIFI_PHY_STANDARD_UNSPECIFIED), std::make_pair (5610, 80) },
143  { std::make_pair (138, WIFI_PHY_STANDARD_UNSPECIFIED), std::make_pair (5690, 80) },
144  { std::make_pair (155, WIFI_PHY_STANDARD_UNSPECIFIED), std::make_pair (5775, 80) },
145  { std::make_pair (171, WIFI_PHY_STANDARD_UNSPECIFIED), std::make_pair (5855, 80) },
146  // 160 MHz channels
147  { std::make_pair (50, WIFI_PHY_STANDARD_UNSPECIFIED), std::make_pair (5250, 160) },
148  { std::make_pair (114, WIFI_PHY_STANDARD_UNSPECIFIED), std::make_pair (5570, 160) },
149  { std::make_pair (163, WIFI_PHY_STANDARD_UNSPECIFIED), std::make_pair (5815, 160) },
150 
151  // 802.11p (10 MHz channels at the 5.855-5.925 band
152  { std::make_pair (172, WIFI_PHY_STANDARD_80211_10MHZ), std::make_pair (5860, 10) },
153  { std::make_pair (174, WIFI_PHY_STANDARD_80211_10MHZ), std::make_pair (5870, 10) },
154  { std::make_pair (176, WIFI_PHY_STANDARD_80211_10MHZ), std::make_pair (5880, 10) },
155  { std::make_pair (178, WIFI_PHY_STANDARD_80211_10MHZ), std::make_pair (5890, 10) },
156  { std::make_pair (180, WIFI_PHY_STANDARD_80211_10MHZ), std::make_pair (5900, 10) },
157  { std::make_pair (182, WIFI_PHY_STANDARD_80211_10MHZ), std::make_pair (5910, 10) },
158  { std::make_pair (184, WIFI_PHY_STANDARD_80211_10MHZ), std::make_pair (5920, 10) }
159 };
160 
161 TypeId
163 {
164  static TypeId tid = TypeId ("ns3::WifiPhy")
165  .SetParent<Object> ()
166  .SetGroupName ("Wifi")
167  .AddAttribute ("Frequency",
168  "The operating center frequency (MHz)",
169  UintegerValue (0),
172  MakeUintegerChecker<uint16_t> ())
173  .AddAttribute ("ChannelWidth",
174  "Whether 5MHz, 10MHz, 20MHz, 22MHz, 40MHz, 80 MHz or 160 MHz.",
175  UintegerValue (20),
178  MakeUintegerChecker<uint16_t> (5, 160))
179  .AddAttribute ("ChannelNumber",
180  "If set to non-zero defined value, will control Frequency and ChannelWidth assignment",
181  UintegerValue (0),
184  MakeUintegerChecker<uint8_t> (0, 196))
185  .AddAttribute ("EnergyDetectionThreshold",
186  "The energy of a received signal should be higher than "
187  "this threshold (dbm) to allow the PHY layer to detect the signal.",
188  DoubleValue (-101.0),
190  MakeDoubleChecker<double> (),
191  TypeId::DEPRECATED, "Replaced by RxSensitivity.")
192  .AddAttribute ("RxSensitivity",
193  "The energy of a received signal should be higher than "
194  "this threshold (dBm) for the PHY to detect the signal.",
195  DoubleValue (-101.0),
198  MakeDoubleChecker<double> ())
199  .AddAttribute ("CcaEdThreshold",
200  "The energy of a non Wi-Fi received signal should be higher than "
201  "this threshold (dbm) to allow the PHY layer to declare CCA BUSY state. "
202  "This check is performed on the 20 MHz primary channel only.",
203  DoubleValue (-62.0),
206  MakeDoubleChecker<double> ())
207  .AddAttribute ("TxGain",
208  "Transmission gain (dB).",
209  DoubleValue (0.0),
212  MakeDoubleChecker<double> ())
213  .AddAttribute ("RxGain",
214  "Reception gain (dB).",
215  DoubleValue (0.0),
218  MakeDoubleChecker<double> ())
219  .AddAttribute ("TxPowerLevels",
220  "Number of transmission power levels available between "
221  "TxPowerStart and TxPowerEnd included.",
222  UintegerValue (1),
224  MakeUintegerChecker<uint8_t> ())
225  .AddAttribute ("TxPowerEnd",
226  "Maximum available transmission level (dbm).",
227  DoubleValue (16.0206),
230  MakeDoubleChecker<double> ())
231  .AddAttribute ("TxPowerStart",
232  "Minimum available transmission level (dbm).",
233  DoubleValue (16.0206),
236  MakeDoubleChecker<double> ())
237  .AddAttribute ("RxNoiseFigure",
238  "Loss (dB) in the Signal-to-Noise-Ratio due to non-idealities in the receiver."
239  " According to Wikipedia (http://en.wikipedia.org/wiki/Noise_figure), this is "
240  "\"the difference in decibels (dB) between"
241  " the noise output of the actual receiver to the noise output of an "
242  " ideal receiver with the same overall gain and bandwidth when the receivers "
243  " are connected to sources at the standard noise temperature T0 (usually 290 K)\".",
244  DoubleValue (7),
246  MakeDoubleChecker<double> ())
247  .AddAttribute ("State",
248  "The state of the PHY layer.",
249  PointerValue (),
251  MakePointerChecker<WifiPhyStateHelper> ())
252  .AddAttribute ("ChannelSwitchDelay",
253  "Delay between two short frames transmitted on different frequencies.",
254  TimeValue (MicroSeconds (250)),
256  MakeTimeChecker ())
257  .AddAttribute ("Antennas",
258  "The number of antennas on the device.",
259  UintegerValue (1),
262  MakeUintegerChecker<uint8_t> (1, 8))
263  .AddAttribute ("MaxSupportedTxSpatialStreams",
264  "The maximum number of supported TX spatial streams."
265  "This parameter is only valuable for 802.11n/ac/ax STAs and APs.",
266  UintegerValue (1),
269  MakeUintegerChecker<uint8_t> (1, 8))
270  .AddAttribute ("MaxSupportedRxSpatialStreams",
271  "The maximum number of supported RX spatial streams."
272  "This parameter is only valuable for 802.11n/ac/ax STAs and APs.",
273  UintegerValue (1),
276  MakeUintegerChecker<uint8_t> (1, 8))
277  .AddAttribute ("ShortGuardEnabled",
278  "Whether or not short guard interval is enabled for HT/VHT transmissions."
279  "This parameter is only valuable for 802.11n/ac/ax STAs and APs.",
280  BooleanValue (false),
284  TypeId::DEPRECATED, "Use the HtConfiguration instead")
285  .AddAttribute ("GuardInterval",
286  "Whether 800ns, 1600ns or 3200ns guard interval is used for HE transmissions."
287  "This parameter is only valuable for 802.11ax STAs and APs.",
288  TimeValue (NanoSeconds (3200)),
291  MakeTimeChecker (NanoSeconds (800), NanoSeconds (3200)),
292  TypeId::DEPRECATED, "Use the HeConfiguration instead")
293  .AddAttribute ("GreenfieldEnabled",
294  "Whether or not Greenfield is enabled."
295  "This parameter is only valuable for 802.11n STAs and APs.",
296  BooleanValue (false),
300  TypeId::DEPRECATED, "Use the HtConfiguration instead")
301  .AddAttribute ("ShortPlcpPreambleSupported",
302  "Whether or not short PLCP preamble is supported."
303  "This parameter is only valuable for 802.11b STAs and APs."
304  "Note: 802.11g APs and STAs always support short PLCP preamble.",
305  BooleanValue (false),
309  .AddAttribute ("FrameCaptureModel",
310  "Ptr to an object that implements the frame capture model",
311  PointerValue (),
313  MakePointerChecker <FrameCaptureModel> ())
314  .AddAttribute ("PreambleDetectionModel",
315  "Ptr to an object that implements the preamble detection model",
316  PointerValue (),
318  MakePointerChecker <PreambleDetectionModel> ())
319  .AddAttribute ("PostReceptionErrorModel",
320  "An optional packet error model can be added to the receive "
321  "packet process after any propagation-based (SNR-based) error "
322  "models have been applied. Typically this is used to force "
323  "specific packet drops, for testing purposes.",
324  PointerValue (),
326  MakePointerChecker<ErrorModel> ())
327  .AddTraceSource ("PhyTxBegin",
328  "Trace source indicating a packet "
329  "has begun transmitting over the channel medium",
331  "ns3::Packet::TracedCallback")
332  .AddTraceSource ("PhyTxPsduBegin",
333  "Trace source indicating a PSDU "
334  "has begun transmitting over the channel medium",
336  "ns3::WifiPhy::PsduTxBeginCallback")
337  .AddTraceSource ("PhyTxEnd",
338  "Trace source indicating a packet "
339  "has been completely transmitted over the channel. "
340  "NOTE: the only official WifiPhy implementation "
341  "available to this date never fires "
342  "this trace source.",
344  "ns3::Packet::TracedCallback")
345  .AddTraceSource ("PhyTxDrop",
346  "Trace source indicating a packet "
347  "has been dropped by the device during transmission",
349  "ns3::Packet::TracedCallback")
350  .AddTraceSource ("PhyRxBegin",
351  "Trace source indicating a packet "
352  "has begun being received from the channel medium "
353  "by the device",
355  "ns3::Packet::TracedCallback")
356  .AddTraceSource ("PhyRxEnd",
357  "Trace source indicating a packet "
358  "has been completely received from the channel medium "
359  "by the device",
361  "ns3::Packet::TracedCallback")
362  .AddTraceSource ("PhyRxDrop",
363  "Trace source indicating a packet "
364  "has been dropped by the device during reception",
366  "ns3::Packet::TracedCallback")
367  .AddTraceSource ("MonitorSnifferRx",
368  "Trace source simulating a wifi device in monitor mode "
369  "sniffing all received frames",
371  "ns3::WifiPhy::MonitorSnifferRxTracedCallback")
372  .AddTraceSource ("MonitorSnifferTx",
373  "Trace source simulating the capability of a wifi device "
374  "in monitor mode to sniff all frames being transmitted",
376  "ns3::WifiPhy::MonitorSnifferTxTracedCallback")
377  .AddTraceSource ("EndOfHePreamble",
378  "Trace source indicating the end of the 802.11ax preamble (after training fields)",
380  "ns3::WifiPhy::EndOfHePreambleTracedCallback")
381  ;
382  return tid;
383 }
384 
386  : m_txMpduReferenceNumber (0xffffffff),
387  m_rxMpduReferenceNumber (0xffffffff),
388  m_endRxEvent (),
389  m_endPlcpRxEvent (),
390  m_endPreambleDetectionEvent (),
391  m_standard (WIFI_PHY_STANDARD_UNSPECIFIED),
392  m_isConstructed (false),
393  m_channelCenterFrequency (0),
394  m_initialFrequency (0),
395  m_frequencyChannelNumberInitialized (false),
396  m_channelWidth (0),
397  m_powerRestricted (false),
398  m_channelAccessRequested (false),
399  m_txSpatialStreams (0),
400  m_rxSpatialStreams (0),
401  m_channelNumber (0),
402  m_initialChannelNumber (0),
403  m_currentEvent (0),
404  m_wifiRadioEnergyModel (0),
405  m_timeLastPreambleDetected (Seconds (0))
406 {
407  NS_LOG_FUNCTION (this);
408  m_random = CreateObject<UniformRandomVariable> ();
409  m_state = CreateObject<WifiPhyStateHelper> ();
410 }
411 
413 {
414  NS_LOG_FUNCTION (this);
415 }
416 
417 void
419 {
420  NS_LOG_FUNCTION (this);
421  m_endRxEvent.Cancel ();
424  m_device = 0;
425  m_mobility = 0;
426  m_state = 0;
429  m_deviceRateSet.clear ();
430  m_deviceMcsSet.clear ();
431  m_mcsIndexMap.clear ();
432 }
433 
434 void
436 {
437  NS_LOG_FUNCTION (this);
438  m_isConstructed = true;
440  {
441  NS_LOG_DEBUG ("Frequency already initialized");
442  return;
443  }
445 }
446 
448 WifiPhy::GetState (void) const
449 {
450  return m_state;
451 }
452 
453 void
455 {
456  m_state->SetReceiveOkCallback (callback);
457 }
458 
459 void
461 {
462  m_state->SetReceiveErrorCallback (callback);
463 }
464 
465 void
467 {
468  m_state->RegisterListener (listener);
469 }
470 
471 void
473 {
474  m_state->UnregisterListener (listener);
475 }
476 
477 void
479 {
481 }
482 
483 void
485 {
486  NS_LOG_FUNCTION (this);
487 
488  NS_ASSERT_MSG (m_frequencyChannelNumberInitialized == false, "Initialization called twice");
489 
490  // If frequency has been set to a non-zero value during attribute
491  // construction phase, the frequency and channel width will drive the
492  // initial configuration. If frequency has not been set, but both
493  // standard and channel number have been set, that pair will instead
494  // drive the configuration, and frequency and channel number will be
495  // aligned
496  if (m_initialFrequency != 0)
497  {
499  }
501  {
503  }
505  {
506  NS_FATAL_ERROR ("Error, ChannelNumber " << +GetChannelNumber () << " was set by user, but neither a standard nor a frequency");
507  }
509 }
510 
511 void
512 WifiPhy::SetEdThreshold (double threshold)
513 {
514  SetRxSensitivity (threshold);
515 }
516 
517 void
518 WifiPhy::SetRxSensitivity (double threshold)
519 {
520  NS_LOG_FUNCTION (this << threshold);
521  m_rxSensitivityW = DbmToW (threshold);
522 }
523 
524 double
526 {
527  return WToDbm (m_rxSensitivityW);
528 }
529 
530 void
531 WifiPhy::SetCcaEdThreshold (double threshold)
532 {
533  NS_LOG_FUNCTION (this << threshold);
534  m_ccaEdThresholdW = DbmToW (threshold);
535 }
536 
537 double
539 {
540  return WToDbm (m_ccaEdThresholdW);
541 }
542 
543 void
544 WifiPhy::SetRxNoiseFigure (double noiseFigureDb)
545 {
546  NS_LOG_FUNCTION (this << noiseFigureDb);
547  m_interference.SetNoiseFigure (DbToRatio (noiseFigureDb));
549 }
550 
551 void
553 {
554  NS_LOG_FUNCTION (this << start);
556 }
557 
558 double
560 {
561  return m_txPowerBaseDbm;
562 }
563 
564 void
566 {
567  NS_LOG_FUNCTION (this << end);
568  m_txPowerEndDbm = end;
569 }
570 
571 double
573 {
574  return m_txPowerEndDbm;
575 }
576 
577 void
579 {
580  NS_LOG_FUNCTION (this << +n);
581  m_nTxPower = n;
582 }
583 
584 uint8_t
586 {
587  return m_nTxPower;
588 }
589 
590 void
591 WifiPhy::SetTxGain (double gain)
592 {
593  NS_LOG_FUNCTION (this << gain);
594  m_txGainDb = gain;
595 }
596 
597 double
598 WifiPhy::GetTxGain (void) const
599 {
600  return m_txGainDb;
601 }
602 
603 void
604 WifiPhy::SetRxGain (double gain)
605 {
606  NS_LOG_FUNCTION (this << gain);
607  m_rxGainDb = gain;
608 }
609 
610 double
611 WifiPhy::GetRxGain (void) const
612 {
613  return m_rxGainDb;
614 }
615 
616 void
617 WifiPhy::SetGreenfield (bool greenfield)
618 {
619  NS_LOG_FUNCTION (this << greenfield);
620  Ptr<WifiNetDevice> device = DynamicCast<WifiNetDevice> (GetDevice ());
621  if (device)
622  {
623  Ptr<HtConfiguration> htConfiguration = device->GetHtConfiguration ();
624  if (htConfiguration)
625  {
626  htConfiguration->SetGreenfieldSupported (greenfield);
627  }
628  }
629  m_greenfield = greenfield;
630 }
631 
632 bool
634 {
635  Ptr<WifiNetDevice> device = DynamicCast<WifiNetDevice> (GetDevice ());
636  if (device)
637  {
638  Ptr<HtConfiguration> htConfiguration = device->GetHtConfiguration ();
639  if (htConfiguration)
640  {
641  return htConfiguration->GetGreenfieldSupported ();
642  }
643  }
644  return m_greenfield;
645 }
646 
647 void
648 WifiPhy::SetShortGuardInterval (bool shortGuardInterval)
649 {
650  NS_LOG_FUNCTION (this << shortGuardInterval);
651  Ptr<WifiNetDevice> device = DynamicCast<WifiNetDevice> (GetDevice ());
652  if (device)
653  {
654  Ptr<HtConfiguration> htConfiguration = device->GetHtConfiguration ();
655  if (htConfiguration)
656  {
657  htConfiguration->SetShortGuardIntervalSupported (shortGuardInterval);
658  }
659  }
660  m_shortGuardInterval = shortGuardInterval;
661 }
662 
663 bool
665 {
666  Ptr<WifiNetDevice> device = DynamicCast<WifiNetDevice> (GetDevice ());
667  if (device)
668  {
669  Ptr<HtConfiguration> htConfiguration = device->GetHtConfiguration ();
670  if (htConfiguration)
671  {
672  return htConfiguration->GetShortGuardIntervalSupported ();
673  }
674  }
675  return m_shortGuardInterval;
676 }
677 
678 void
680 {
681  NS_LOG_FUNCTION (this << guardInterval);
682  NS_ASSERT (guardInterval == NanoSeconds (800) || guardInterval == NanoSeconds (1600) || guardInterval == NanoSeconds (3200));
683  Ptr<WifiNetDevice> device = DynamicCast<WifiNetDevice> (GetDevice ());
684  if (device)
685  {
686  Ptr<HeConfiguration> heConfiguration = device->GetHeConfiguration ();
687  if (heConfiguration)
688  {
689  heConfiguration->SetGuardInterval (guardInterval);
690  }
691  }
692  m_guardInterval = guardInterval;
693 }
694 
695 Time
697 {
698  Ptr<WifiNetDevice> device = DynamicCast<WifiNetDevice> (GetDevice ());
699  if (device)
700  {
701  Ptr<HeConfiguration> heConfiguration = device->GetHeConfiguration ();
702  if (heConfiguration)
703  {
704  return heConfiguration->GetGuardInterval ();
705  }
706  }
707  return m_guardInterval;
708 }
709 
710 void
712 {
713  NS_LOG_FUNCTION (this << enable);
714  m_shortPreamble = enable;
715 }
716 
717 bool
719 {
720  return m_shortPreamble;
721 }
722 
723 void
725 {
726  m_device = device;
727  //TODO: to be removed once deprecated API is cleaned up
728  Ptr<HtConfiguration> htConfiguration = DynamicCast<WifiNetDevice> (device)->GetHtConfiguration ();
729  if (htConfiguration)
730  {
731  htConfiguration->SetShortGuardIntervalSupported (m_shortGuardInterval);
732  htConfiguration->SetGreenfieldSupported (m_greenfield);
733  }
734  Ptr<HeConfiguration> heConfiguration = DynamicCast<WifiNetDevice> (device)->GetHeConfiguration ();
735  if (heConfiguration)
736  {
737  heConfiguration->SetGuardInterval (m_guardInterval);
738  }
739 }
740 
742 WifiPhy::GetDevice (void) const
743 {
744  return m_device;
745 }
746 
747 void
749 {
751 }
752 
755 {
756  if (m_mobility != 0)
757  {
758  return m_mobility;
759  }
760  else
761  {
762  return m_device->GetNode ()->GetObject<MobilityModel> ();
763  }
764 }
765 
766 void
768 {
771 }
772 
773 void
775 {
776  NS_LOG_FUNCTION (this << em);
778 }
779 
780 void
782 {
783  m_frameCaptureModel = model;
784 }
785 
786 void
788 {
789  m_preambleDetectionModel = model;
790 }
791 
792 void
794 {
795  m_wifiRadioEnergyModel = wifiRadioEnergyModel;
796 }
797 
798 double
799 WifiPhy::GetPowerDbm (uint8_t power) const
800 {
802  NS_ASSERT (m_nTxPower > 0);
803  double dbm;
804  if (m_nTxPower > 1)
805  {
806  dbm = m_txPowerBaseDbm + power * (m_txPowerEndDbm - m_txPowerBaseDbm) / (m_nTxPower - 1);
807  }
808  else
809  {
810  NS_ASSERT_MSG (m_txPowerBaseDbm == m_txPowerEndDbm, "cannot have TxPowerEnd != TxPowerStart with TxPowerLevels == 1");
811  dbm = m_txPowerBaseDbm;
812  }
813  return dbm;
814 }
815 
816 Time
818 {
819  return m_channelSwitchDelay;
820 }
821 
822 double
823 WifiPhy::CalculateSnr (WifiTxVector txVector, double ber) const
824 {
825  return m_interference.GetErrorRateModel ()->CalculateSnr (txVector, ber);
826 }
827 
828 void
830 {
831  NS_LOG_FUNCTION (this << standard);
832  switch (standard)
833  {
835  SetChannelWidth (20);
836  SetFrequency (5180);
837  // Channel number should be aligned by SetFrequency () to 36
838  NS_ASSERT (GetChannelNumber () == 36);
839  break;
841  SetChannelWidth (22);
842  SetFrequency (2412);
843  // Channel number should be aligned by SetFrequency () to 1
844  NS_ASSERT (GetChannelNumber () == 1);
845  break;
847  SetChannelWidth (20);
848  SetFrequency (2412);
849  // Channel number should be aligned by SetFrequency () to 1
850  NS_ASSERT (GetChannelNumber () == 1);
851  break;
853  SetChannelWidth (10);
854  SetFrequency (5860);
855  // Channel number should be aligned by SetFrequency () to 172
856  NS_ASSERT (GetChannelNumber () == 172);
857  break;
859  SetChannelWidth (5);
860  SetFrequency (5860);
861  // Channel number should be aligned by SetFrequency () to 0
862  NS_ASSERT (GetChannelNumber () == 0);
863  break;
865  SetChannelWidth (20);
866  SetFrequency (5180);
867  // Channel number should be aligned by SetFrequency () to 36
868  NS_ASSERT (GetChannelNumber () == 36);
869  break;
871  SetChannelWidth (20);
872  SetFrequency (2412);
873  // Channel number should be aligned by SetFrequency () to 1
874  NS_ASSERT (GetChannelNumber () == 1);
875  break;
877  SetChannelWidth (20);
878  SetFrequency (5180);
879  // Channel number should be aligned by SetFrequency () to 36
880  NS_ASSERT (GetChannelNumber () == 36);
881  break;
883  SetChannelWidth (80);
884  SetFrequency (5210);
885  // Channel number should be aligned by SetFrequency () to 42
886  NS_ASSERT (GetChannelNumber () == 42);
887  break;
889  SetChannelWidth (20);
890  SetFrequency (2412);
891  // Channel number should be aligned by SetFrequency () to 1
892  NS_ASSERT (GetChannelNumber () == 1);
893  break;
895  SetChannelWidth (80);
896  SetFrequency (5210);
897  // Channel number should be aligned by SetFrequency () to 42
898  NS_ASSERT (GetChannelNumber () == 42);
899  break;
901  default:
902  NS_LOG_WARN ("Configuring unspecified standard; performing no action");
903  break;
904  }
905 }
906 
907 void
909 {
910  NS_LOG_FUNCTION (this);
911 
920 }
921 
922 void
924 {
925  NS_LOG_FUNCTION (this);
926 
931 }
932 
933 void
935 {
936  NS_LOG_FUNCTION (this);
937  Configure80211b ();
938 
947 }
948 
949 void
951 {
952  NS_LOG_FUNCTION (this);
953 
962 }
963 
964 void
966 {
967  NS_LOG_FUNCTION (this);
968 
977 }
978 
979 void
981 {
982  NS_LOG_FUNCTION (this);
983 
989 }
990 
991 void
993 {
994  NS_LOG_FUNCTION (this << mode);
995 
996  WifiModulationClass modulation = mode.GetModulationClass ();
997  NS_ASSERT (modulation == WIFI_MOD_CLASS_HT || modulation == WIFI_MOD_CLASS_VHT
998  || modulation == WIFI_MOD_CLASS_HE);
999 
1000  m_mcsIndexMap[modulation][mode.GetMcsValue ()] = m_deviceMcsSet.size ();
1001  m_deviceMcsSet.push_back (mode);
1002 }
1003 
1004 void
1006 {
1007  NS_LOG_FUNCTION (this);
1008  m_mcsIndexMap.clear ();
1009  uint8_t index = 0;
1010  for (auto& mode : m_deviceMcsSet)
1011  {
1012  m_mcsIndexMap[mode.GetModulationClass ()][mode.GetMcsValue ()] = index++;
1013  }
1014 }
1015 
1016 void
1018 {
1019  NS_LOG_FUNCTION (this);
1020 
1021  bool htFound = false;
1022  for (std::vector<uint8_t>::size_type i = 0; i < m_bssMembershipSelectorSet.size (); i++)
1023  {
1025  {
1026  htFound = true;
1027  break;
1028  }
1029  }
1030  if (htFound)
1031  {
1032  // erase all HtMcs modes from deviceMcsSet
1033  std::size_t index = m_deviceMcsSet.size () - 1;
1034  for (std::vector<WifiMode>::reverse_iterator rit = m_deviceMcsSet.rbegin (); rit != m_deviceMcsSet.rend (); ++rit, --index)
1035  {
1036  if (m_deviceMcsSet[index].GetModulationClass () == WIFI_MOD_CLASS_HT)
1037  {
1038  m_deviceMcsSet.erase (m_deviceMcsSet.begin () + index);
1039  }
1040  }
1041  RebuildMcsMap ();
1051  {
1060  }
1062  {
1071  }
1073  {
1082  }
1083  }
1084 }
1085 
1086 void
1088 {
1089  NS_LOG_FUNCTION (this);
1090  if (Is2_4Ghz (GetFrequency ()))
1091  {
1092  Configure80211b ();
1093  Configure80211g ();
1094  }
1095  if (Is5Ghz (GetFrequency ()))
1096  {
1097  Configure80211a ();
1098  }
1099  m_bssMembershipSelectorSet.push_back (HT_PHY);
1101 }
1102 
1103 void
1105 {
1106  NS_LOG_FUNCTION (this);
1107  Configure80211n ();
1108 
1119 
1120  m_bssMembershipSelectorSet.push_back (VHT_PHY);
1121 }
1122 
1123 void
1125 {
1126  NS_LOG_FUNCTION (this);
1127  if (Is5Ghz (GetFrequency ()))
1128  {
1129  Configure80211ac ();
1130  }
1131  else
1132  {
1133  Configure80211n ();
1134  }
1135 
1148 
1149  m_bssMembershipSelectorSet.push_back (HE_PHY);
1150 }
1151 
1152 bool
1153 WifiPhy::DefineChannelNumber (uint8_t channelNumber, WifiPhyStandard standard, uint16_t frequency, uint16_t channelWidth)
1154 {
1155  NS_LOG_FUNCTION (this << +channelNumber << standard << frequency << channelWidth);
1156  ChannelNumberStandardPair p = std::make_pair (channelNumber, standard);
1157  ChannelToFrequencyWidthMap::const_iterator it;
1158  it = m_channelToFrequencyWidth.find (p);
1159  if (it != m_channelToFrequencyWidth.end ())
1160  {
1161  NS_LOG_DEBUG ("channel number/standard already defined; returning false");
1162  return false;
1163  }
1164  FrequencyWidthPair f = std::make_pair (frequency, channelWidth);
1166  return true;
1167 }
1168 
1169 uint8_t
1170 WifiPhy::FindChannelNumberForFrequencyWidth (uint16_t frequency, uint16_t width) const
1171 {
1172  NS_LOG_FUNCTION (this << frequency << width);
1173  bool found = false;
1174  FrequencyWidthPair f = std::make_pair (frequency, width);
1175  ChannelToFrequencyWidthMap::const_iterator it = m_channelToFrequencyWidth.begin ();
1176  while (it != m_channelToFrequencyWidth.end ())
1177  {
1178  if (it->second == f)
1179  {
1180  found = true;
1181  break;
1182  }
1183  ++it;
1184  }
1185  if (found)
1186  {
1187  NS_LOG_DEBUG ("Found, returning " << +it->first.first);
1188  return (it->first.first);
1189  }
1190  else
1191  {
1192  NS_LOG_DEBUG ("Not found, returning 0");
1193  return 0;
1194  }
1195 }
1196 
1197 void
1199 {
1200  NS_LOG_FUNCTION (this << standard);
1201  // If the user has configured both Frequency and ChannelNumber, Frequency
1202  // takes precedence
1203  if (GetFrequency () != 0)
1204  {
1205  // If Frequency is already set, then see whether a ChannelNumber can
1206  // be found that matches Frequency and ChannelWidth. If so, configure
1207  // the ChannelNumber to that channel number. If not, set ChannelNumber to zero.
1208  NS_LOG_DEBUG ("Frequency set; checking whether a channel number corresponds");
1209  uint8_t channelNumberSearched = FindChannelNumberForFrequencyWidth (GetFrequency (), GetChannelWidth ());
1210  if (channelNumberSearched)
1211  {
1212  NS_LOG_DEBUG ("Channel number found; setting to " << +channelNumberSearched);
1213  SetChannelNumber (channelNumberSearched);
1214  }
1215  else
1216  {
1217  NS_LOG_DEBUG ("Channel number not found; setting to zero");
1218  SetChannelNumber (0);
1219  }
1220  }
1221  else if (GetChannelNumber () != 0)
1222  {
1223  // If the channel number is known for this particular standard or for
1224  // the unspecified standard, configure using the known values;
1225  // otherwise, this is a configuration error
1226  NS_LOG_DEBUG ("Configuring for channel number " << +GetChannelNumber ());
1228  if (f.first == 0)
1229  {
1230  // the specific pair of number/standard is not known
1231  NS_LOG_DEBUG ("Falling back to check WIFI_PHY_STANDARD_UNSPECIFIED");
1233  }
1234  if (f.first == 0)
1235  {
1236  NS_FATAL_ERROR ("Error, ChannelNumber " << +GetChannelNumber () << " is unknown for this standard");
1237  }
1238  else
1239  {
1240  NS_LOG_DEBUG ("Setting frequency to " << f.first << "; width to " << +f.second);
1241  SetFrequency (f.first);
1242  SetChannelWidth (f.second);
1243  }
1244  }
1245 }
1246 
1247 void
1249 {
1250  NS_LOG_FUNCTION (this << standard);
1251  m_standard = standard;
1252  m_isConstructed = true;
1254  {
1256  }
1257  if (GetFrequency () == 0 && GetChannelNumber () == 0)
1258  {
1259  ConfigureDefaultsForStandard (standard);
1260  }
1261  else
1262  {
1263  // The user has configured either (or both) Frequency or ChannelNumber
1264  ConfigureChannelForStandard (standard);
1265  }
1266  switch (standard)
1267  {
1269  Configure80211a ();
1270  break;
1272  Configure80211b ();
1273  break;
1275  Configure80211g ();
1276  break;
1279  break;
1282  break;
1284  ConfigureHolland ();
1285  break;
1288  Configure80211n ();
1289  break;
1291  Configure80211ac ();
1292  break;
1295  Configure80211ax ();
1296  break;
1298  default:
1299  NS_ASSERT (false);
1300  break;
1301  }
1302 }
1303 
1306 {
1307  return m_standard;
1308 }
1309 
1310 void
1311 WifiPhy::SetFrequency (uint16_t frequency)
1312 {
1313  NS_LOG_FUNCTION (this << frequency);
1314  if (m_isConstructed == false)
1315  {
1316  NS_LOG_DEBUG ("Saving frequency configuration for initialization");
1317  m_initialFrequency = frequency;
1318  return;
1319  }
1320  if (GetFrequency () == frequency)
1321  {
1322  NS_LOG_DEBUG ("No frequency change requested");
1323  return;
1324  }
1325  if (frequency == 0)
1326  {
1327  DoFrequencySwitch (0);
1328  NS_LOG_DEBUG ("Setting frequency and channel number to zero");
1330  m_channelNumber = 0;
1331  return;
1332  }
1333  // If the user has configured both Frequency and ChannelNumber, Frequency
1334  // takes precedence. Lookup the channel number corresponding to the
1335  // requested frequency.
1336  uint8_t nch = FindChannelNumberForFrequencyWidth (frequency, GetChannelWidth ());
1337  if (nch != 0)
1338  {
1339  NS_LOG_DEBUG ("Setting frequency " << frequency << " corresponds to channel " << +nch);
1340  if (DoFrequencySwitch (frequency))
1341  {
1342  NS_LOG_DEBUG ("Channel frequency switched to " << frequency << "; channel number to " << +nch);
1343  m_channelCenterFrequency = frequency;
1344  m_channelNumber = nch;
1345  }
1346  else
1347  {
1348  NS_LOG_DEBUG ("Suppressing reassignment of frequency");
1349  }
1350  }
1351  else
1352  {
1353  NS_LOG_DEBUG ("Channel number is unknown for frequency " << frequency);
1354  if (DoFrequencySwitch (frequency))
1355  {
1356  NS_LOG_DEBUG ("Channel frequency switched to " << frequency << "; channel number to " << 0);
1357  m_channelCenterFrequency = frequency;
1358  m_channelNumber = 0;
1359  }
1360  else
1361  {
1362  NS_LOG_DEBUG ("Suppressing reassignment of frequency");
1363  }
1364  }
1365 }
1366 
1367 uint16_t
1369 {
1370  return m_channelCenterFrequency;
1371 }
1372 
1373 void
1374 WifiPhy::SetChannelWidth (uint16_t channelwidth)
1375 {
1376  NS_LOG_FUNCTION (this << channelwidth);
1377  NS_ASSERT_MSG (channelwidth == 5 || channelwidth == 10 || channelwidth == 20 || channelwidth == 22 || channelwidth == 40 || channelwidth == 80 || channelwidth == 160, "wrong channel width value");
1378  bool changed = (m_channelWidth != channelwidth);
1379  m_channelWidth = channelwidth;
1380  AddSupportedChannelWidth (channelwidth);
1381  if (changed && !m_capabilitiesChangedCallback.IsNull ())
1382  {
1384  }
1385 }
1386 
1387 uint16_t
1389 {
1390  return m_channelWidth;
1391 }
1392 
1393 void
1395 {
1396  NS_ASSERT_MSG (antennas > 0 && antennas <= 4, "unsupported number of antennas");
1397  m_numberOfAntennas = antennas;
1399 }
1400 
1401 uint8_t
1403 {
1404  return m_numberOfAntennas;
1405 }
1406 
1407 void
1409 {
1410  NS_ASSERT (streams <= GetNumberOfAntennas ());
1411  bool changed = (m_txSpatialStreams != streams);
1412  m_txSpatialStreams = streams;
1414  if (changed && !m_capabilitiesChangedCallback.IsNull ())
1415  {
1417  }
1418 }
1419 
1420 uint8_t
1422 {
1423  return m_txSpatialStreams;
1424 }
1425 
1426 void
1428 {
1429  NS_ASSERT (streams <= GetNumberOfAntennas ());
1430  bool changed = (m_rxSpatialStreams != streams);
1431  m_rxSpatialStreams = streams;
1432  if (changed && !m_capabilitiesChangedCallback.IsNull ())
1433  {
1435  }
1436 }
1437 
1438 uint8_t
1440 {
1441  return m_rxSpatialStreams;
1442 }
1443 
1444 uint8_t
1446 {
1447  return static_cast<uint8_t> (m_bssMembershipSelectorSet.size ());
1448 }
1449 
1450 uint8_t
1451 WifiPhy::GetBssMembershipSelector (uint8_t selector) const
1452 {
1453  return m_bssMembershipSelectorSet[selector];
1454 }
1455 
1456 void
1458 {
1459  NS_LOG_FUNCTION (this << width);
1460  for (std::vector<uint32_t>::size_type i = 0; i != m_supportedChannelWidthSet.size (); i++)
1461  {
1462  if (m_supportedChannelWidthSet[i] == width)
1463  {
1464  return;
1465  }
1466  }
1467  NS_LOG_FUNCTION ("Adding " << width << " to supported channel width set");
1468  m_supportedChannelWidthSet.push_back (width);
1469 }
1470 
1471 std::vector<uint16_t>
1473 {
1475 }
1476 
1479 {
1480  ChannelNumberStandardPair p = std::make_pair (channelNumber, standard);
1482  return f;
1483 }
1484 
1485 void
1487 {
1488  NS_LOG_FUNCTION (this << +nch);
1489  if (m_isConstructed == false)
1490  {
1491  NS_LOG_DEBUG ("Saving channel number configuration for initialization");
1492  m_initialChannelNumber = nch;
1493  return;
1494  }
1495  if (GetChannelNumber () == nch)
1496  {
1497  NS_LOG_DEBUG ("No channel change requested");
1498  return;
1499  }
1500  if (nch == 0)
1501  {
1502  // This case corresponds to when there is not a known channel
1503  // number for the requested frequency. There is no need to call
1504  // DoChannelSwitch () because DoFrequencySwitch () should have been
1505  // called by the client
1506  NS_LOG_DEBUG ("Setting channel number to zero");
1507  m_channelNumber = 0;
1508  return;
1509  }
1510 
1511  // First make sure that the channel number is defined for the standard
1512  // in use
1514  if (f.first == 0)
1515  {
1517  }
1518  if (f.first != 0)
1519  {
1520  if (DoChannelSwitch (nch))
1521  {
1522  NS_LOG_DEBUG ("Setting frequency to " << f.first << "; width to " << +f.second);
1523  m_channelCenterFrequency = f.first;
1524  SetChannelWidth (f.second);
1525  m_channelNumber = nch;
1526  }
1527  else
1528  {
1529  // Subclass may have suppressed (e.g. waiting for state change)
1530  NS_LOG_DEBUG ("Channel switch suppressed");
1531  }
1532  }
1533  else
1534  {
1535  NS_FATAL_ERROR ("Frequency not found for channel number " << +nch);
1536  }
1537 }
1538 
1539 uint8_t
1541 {
1542  return m_channelNumber;
1543 }
1544 
1545 bool
1547 {
1548  m_powerRestricted = false;
1549  m_channelAccessRequested = false;
1550  if (!IsInitialized ())
1551  {
1552  //this is not channel switch, this is initialization
1553  NS_LOG_DEBUG ("initialize to channel " << +nch);
1554  return true;
1555  }
1556 
1558  switch (m_state->GetState ())
1559  {
1560  case WifiPhyState::RX:
1561  NS_LOG_DEBUG ("drop packet because of channel switching while reception");
1563  m_endRxEvent.Cancel ();
1565  goto switchChannel;
1566  break;
1567  case WifiPhyState::TX:
1568  NS_LOG_DEBUG ("channel switching postponed until end of current transmission");
1570  break;
1572  case WifiPhyState::IDLE:
1574  {
1576  m_endRxEvent.Cancel ();
1577  }
1578  goto switchChannel;
1579  break;
1580  case WifiPhyState::SLEEP:
1581  NS_LOG_DEBUG ("channel switching ignored in sleep mode");
1582  break;
1583  default:
1584  NS_ASSERT (false);
1585  break;
1586  }
1587 
1588  return false;
1589 
1590 switchChannel:
1591 
1592  NS_LOG_DEBUG ("switching channel " << +GetChannelNumber () << " -> " << +nch);
1593  m_state->SwitchToChannelSwitching (GetChannelSwitchDelay ());
1595  /*
1596  * Needed here to be able to correctly sensed the medium for the first
1597  * time after the switching. The actual switching is not performed until
1598  * after m_channelSwitchDelay. Packets received during the switching
1599  * state are added to the event list and are employed later to figure
1600  * out the state of the medium after the switching.
1601  */
1602  return true;
1603 }
1604 
1605 bool
1606 WifiPhy::DoFrequencySwitch (uint16_t frequency)
1607 {
1608  m_powerRestricted = false;
1609  m_channelAccessRequested = false;
1610  if (!IsInitialized ())
1611  {
1612  //this is not channel switch, this is initialization
1613  NS_LOG_DEBUG ("start at frequency " << frequency);
1614  return true;
1615  }
1616 
1618  switch (m_state->GetState ())
1619  {
1620  case WifiPhyState::RX:
1621  NS_LOG_DEBUG ("drop packet because of channel/frequency switching while reception");
1623  m_endRxEvent.Cancel ();
1625  goto switchFrequency;
1626  break;
1627  case WifiPhyState::TX:
1628  NS_LOG_DEBUG ("channel/frequency switching postponed until end of current transmission");
1630  break;
1632  case WifiPhyState::IDLE:
1634  {
1636  m_endRxEvent.Cancel ();
1637  }
1638  goto switchFrequency;
1639  break;
1640  case WifiPhyState::SLEEP:
1641  NS_LOG_DEBUG ("frequency switching ignored in sleep mode");
1642  break;
1643  default:
1644  NS_ASSERT (false);
1645  break;
1646  }
1647 
1648  return false;
1649 
1650 switchFrequency:
1651 
1652  NS_LOG_DEBUG ("switching frequency " << GetFrequency () << " -> " << frequency);
1653  m_state->SwitchToChannelSwitching (GetChannelSwitchDelay ());
1655  /*
1656  * Needed here to be able to correctly sensed the medium for the first
1657  * time after the switching. The actual switching is not performed until
1658  * after m_channelSwitchDelay. Packets received during the switching
1659  * state are added to the event list and are employed later to figure
1660  * out the state of the medium after the switching.
1661  */
1662  return true;
1663 }
1664 
1665 void
1667 {
1668  NS_LOG_FUNCTION (this);
1669  m_powerRestricted = false;
1670  m_channelAccessRequested = false;
1671  switch (m_state->GetState ())
1672  {
1673  case WifiPhyState::TX:
1674  NS_LOG_DEBUG ("setting sleep mode postponed until end of current transmission");
1676  break;
1677  case WifiPhyState::RX:
1678  NS_LOG_DEBUG ("setting sleep mode postponed until end of current reception");
1680  break;
1682  NS_LOG_DEBUG ("setting sleep mode postponed until end of channel switching");
1684  break;
1686  case WifiPhyState::IDLE:
1687  NS_LOG_DEBUG ("setting sleep mode");
1688  m_state->SwitchToSleep ();
1689  break;
1690  case WifiPhyState::SLEEP:
1691  NS_LOG_DEBUG ("already in sleep mode");
1692  break;
1693  default:
1694  NS_ASSERT (false);
1695  break;
1696  }
1697 }
1698 
1699 void
1701 {
1702  NS_LOG_FUNCTION (this);
1703  m_powerRestricted = false;
1704  m_channelAccessRequested = false;
1706  m_endRxEvent.Cancel ();
1708  m_state->SwitchToOff ();
1709 }
1710 
1711 void
1713 {
1714  NS_LOG_FUNCTION (this);
1715  switch (m_state->GetState ())
1716  {
1717  case WifiPhyState::TX:
1718  case WifiPhyState::RX:
1719  case WifiPhyState::IDLE:
1722  {
1723  NS_LOG_DEBUG ("not in sleep mode, there is nothing to resume");
1724  break;
1725  }
1726  case WifiPhyState::SLEEP:
1727  {
1728  NS_LOG_DEBUG ("resuming from sleep mode");
1730  m_state->SwitchFromSleep (delayUntilCcaEnd);
1731  break;
1732  }
1733  default:
1734  {
1735  NS_ASSERT (false);
1736  break;
1737  }
1738  }
1739 }
1740 
1741 void
1743 {
1744  NS_LOG_FUNCTION (this);
1745  switch (m_state->GetState ())
1746  {
1747  case WifiPhyState::TX:
1748  case WifiPhyState::RX:
1749  case WifiPhyState::IDLE:
1752  case WifiPhyState::SLEEP:
1753  {
1754  NS_LOG_DEBUG ("not in off mode, there is nothing to resume");
1755  break;
1756  }
1757  case WifiPhyState::OFF:
1758  {
1759  NS_LOG_DEBUG ("resuming from off mode");
1761  m_state->SwitchFromOff (delayUntilCcaEnd);
1762  break;
1763  }
1764  default:
1765  {
1766  NS_ASSERT (false);
1767  break;
1768  }
1769  }
1770 }
1771 
1772 WifiMode
1774 {
1775  return WifiPhy::GetHtMcs0 ();
1776 }
1777 
1778 WifiMode
1780 {
1781  return WifiPhy::GetVhtMcs0 ();
1782 }
1783 
1784 WifiMode
1786 {
1787  return WifiPhy::GetHeMcs0 ();
1788 }
1789 
1790 Time
1792 {
1793  return MicroSeconds (4);
1794 }
1795 
1796 Time
1798 {
1799  uint8_t Ndltf, Neltf;
1800  //We suppose here that STBC = 0.
1801  //If STBC > 0, we need a different mapping between Nss and Nltf (IEEE 802.11n-2012 standard, page 1682).
1802  if (txVector.GetNss () < 3)
1803  {
1804  Ndltf = txVector.GetNss ();
1805  }
1806  else if (txVector.GetNss () < 5)
1807  {
1808  Ndltf = 4;
1809  }
1810  else if (txVector.GetNss () < 7)
1811  {
1812  Ndltf = 6;
1813  }
1814  else
1815  {
1816  Ndltf = 8;
1817  }
1818 
1819  if (txVector.GetNess () < 3)
1820  {
1821  Neltf = txVector.GetNess ();
1822  }
1823  else
1824  {
1825  Neltf = 4;
1826  }
1827 
1828  switch (txVector.GetPreambleType ())
1829  {
1830  case WIFI_PREAMBLE_HT_MF:
1831  return MicroSeconds (4 + (4 * Ndltf) + (4 * Neltf));
1832  case WIFI_PREAMBLE_HT_GF:
1833  return MicroSeconds ((4 * Ndltf) + (4 * Neltf));
1834  case WIFI_PREAMBLE_VHT_SU:
1835  case WIFI_PREAMBLE_VHT_MU:
1836  return MicroSeconds (4 + (4 * Ndltf));
1837  case WIFI_PREAMBLE_HE_SU:
1838  case WIFI_PREAMBLE_HE_MU:
1839  return MicroSeconds (4 + (8 * Ndltf));
1840  default:
1841  return MicroSeconds (0);
1842  }
1843 }
1844 
1845 Time
1847 {
1848  switch (preamble)
1849  {
1850  case WIFI_PREAMBLE_HT_MF:
1851  case WIFI_PREAMBLE_HT_GF:
1852  //HT-SIG
1853  return MicroSeconds (8);
1854  default:
1855  //no HT-SIG for non HT
1856  return MicroSeconds (0);
1857  }
1858 }
1859 
1860 Time
1862 {
1863  switch (preamble)
1864  {
1865  case WIFI_PREAMBLE_VHT_SU:
1866  case WIFI_PREAMBLE_HE_SU:
1867  case WIFI_PREAMBLE_VHT_MU:
1868  case WIFI_PREAMBLE_HE_MU:
1869  //VHT-SIG-A1 and HE-SIG-A1
1870  return MicroSeconds (4);
1871  default:
1872  // no SIG-A1
1873  return MicroSeconds (0);
1874  }
1875 }
1876 
1877 Time
1879 {
1880  switch (preamble)
1881  {
1882  case WIFI_PREAMBLE_VHT_SU:
1883  case WIFI_PREAMBLE_HE_SU:
1884  case WIFI_PREAMBLE_VHT_MU:
1885  case WIFI_PREAMBLE_HE_MU:
1886  //VHT-SIG-A2 and HE-SIG-A2
1887  return MicroSeconds (4);
1888  default:
1889  // no SIG-A2
1890  return MicroSeconds (0);
1891  }
1892 }
1893 
1894 Time
1896 {
1897  switch (preamble)
1898  {
1899  case WIFI_PREAMBLE_VHT_MU:
1900  case WIFI_PREAMBLE_HE_MU:
1901  return MicroSeconds (4);
1902  default:
1903  // no SIG-B
1904  return MicroSeconds (0);
1905  }
1906 }
1907 
1908 WifiMode
1910 {
1911  WifiPreamble preamble = txVector.GetPreambleType ();
1912  switch (preamble)
1913  {
1914  case WIFI_PREAMBLE_LONG:
1915  case WIFI_PREAMBLE_SHORT:
1916  {
1917  switch (txVector.GetMode ().GetModulationClass ())
1918  {
1919  case WIFI_MOD_CLASS_OFDM:
1920  {
1921  switch (txVector.GetChannelWidth ())
1922  {
1923  case 5:
1925  case 10:
1927  case 20:
1928  default:
1929  //(Section 18.3.2 "PLCP frame format"; IEEE Std 802.11-2012)
1930  //actually this is only the first part of the PlcpHeader,
1931  //because the last 16 bits of the PlcpHeader are using the
1932  //same mode of the payload
1933  return WifiPhy::GetOfdmRate6Mbps ();
1934  }
1935  }
1937  return WifiPhy::GetErpOfdmRate6Mbps ();
1938  case WIFI_MOD_CLASS_DSSS:
1940  {
1941  if (preamble == WIFI_PREAMBLE_LONG || txVector.GetMode () == WifiPhy::GetDsssRate1Mbps ())
1942  {
1943  //(Section 16.2.3 "PLCP field definitions" and Section 17.2.2.2 "Long PPDU format"; IEEE Std 802.11-2012)
1944  return WifiPhy::GetDsssRate1Mbps ();
1945  }
1946  else
1947  {
1948  //(Section 17.2.2.3 "Short PPDU format"; IEEE Std 802.11-2012)
1949  return WifiPhy::GetDsssRate2Mbps ();
1950  }
1951  }
1952  default:
1953  NS_FATAL_ERROR ("unsupported modulation class");
1954  return WifiMode ();
1955  }
1956  }
1957  case WIFI_PREAMBLE_HT_MF:
1958  case WIFI_PREAMBLE_HT_GF:
1959  case WIFI_PREAMBLE_VHT_SU:
1960  case WIFI_PREAMBLE_VHT_MU:
1961  case WIFI_PREAMBLE_HE_SU:
1963  case WIFI_PREAMBLE_HE_MU:
1964  case WIFI_PREAMBLE_HE_TB:
1965  return WifiPhy::GetOfdmRate6Mbps ();
1966  default:
1967  NS_FATAL_ERROR ("unsupported preamble type");
1968  return WifiMode ();
1969  }
1970 }
1971 
1972 Time
1974 {
1975  WifiPreamble preamble = txVector.GetPreambleType ();
1976  switch (txVector.GetPreambleType ())
1977  {
1978  case WIFI_PREAMBLE_LONG:
1979  case WIFI_PREAMBLE_SHORT:
1980  {
1981  switch (txVector.GetMode ().GetModulationClass ())
1982  {
1983  case WIFI_MOD_CLASS_OFDM:
1984  {
1985  switch (txVector.GetChannelWidth ())
1986  {
1987  case 20:
1988  default:
1989  //(Section 18.3.3 "PLCP preamble (SYNC))" and Figure 18-4 "OFDM training structure"; IEEE Std 802.11-2012)
1990  //also (Section 18.3.2.4 "Timing related parameters" Table 18-5 "Timing-related parameters"; IEEE Std 802.11-2012)
1991  //We return the duration of the SIGNAL field only, since the
1992  //SERVICE field (which strictly speaking belongs to the PLCP
1993  //header, see Section 18.3.2 and Figure 18-1) is sent using the
1994  //payload mode.
1995  return MicroSeconds (4);
1996  case 10:
1997  //(Section 18.3.2.4 "Timing related parameters" Table 18-5 "Timing-related parameters"; IEEE Std 802.11-2012)
1998  return MicroSeconds (8);
1999  case 5:
2000  //(Section 18.3.2.4 "Timing related parameters" Table 18-5 "Timing-related parameters"; IEEE Std 802.11-2012)
2001  return MicroSeconds (16);
2002  }
2003  }
2005  return MicroSeconds (4);
2006  case WIFI_MOD_CLASS_DSSS:
2008  {
2009  if ((preamble == WIFI_PREAMBLE_SHORT) && (txVector.GetMode ().GetDataRate (22) > 1000000))
2010  {
2011  //(Section 17.2.2.3 "Short PPDU format" and Figure 17-2 "Short PPDU format"; IEEE Std 802.11-2012)
2012  return MicroSeconds (24);
2013  }
2014  else
2015  {
2016  //(Section 17.2.2.2 "Long PPDU format" and Figure 17-1 "Short PPDU format"; IEEE Std 802.11-2012)
2017  return MicroSeconds (48);
2018  }
2019  }
2020  default:
2021  NS_FATAL_ERROR ("modulation class is not matching the preamble type");
2022  return MicroSeconds (0);
2023  }
2024  }
2025  case WIFI_PREAMBLE_HT_MF:
2026  case WIFI_PREAMBLE_VHT_SU:
2027  case WIFI_PREAMBLE_VHT_MU:
2028  //L-SIG
2029  return MicroSeconds (4);
2030  case WIFI_PREAMBLE_HE_SU:
2032  case WIFI_PREAMBLE_HE_MU:
2033  case WIFI_PREAMBLE_HE_TB:
2034  //LSIG + R-LSIG
2035  return MicroSeconds (8);
2036  case WIFI_PREAMBLE_HT_GF:
2037  return MicroSeconds (0);
2038  default:
2039  NS_FATAL_ERROR ("unsupported preamble type");
2040  return MicroSeconds (0);
2041  }
2042 }
2043 
2044 Time
2046 {
2047  return MicroSeconds (4);
2048 }
2049 
2050 Time
2052 {
2053  WifiPreamble preamble = txVector.GetPreambleType ();
2054  switch (txVector.GetPreambleType ())
2055  {
2056  case WIFI_PREAMBLE_LONG:
2057  case WIFI_PREAMBLE_SHORT:
2058  {
2059  switch (txVector.GetMode ().GetModulationClass ())
2060  {
2061  case WIFI_MOD_CLASS_OFDM:
2062  {
2063  switch (txVector.GetChannelWidth ())
2064  {
2065  case 20:
2066  default:
2067  //(Section 18.3.3 "PLCP preamble (SYNC))" Figure 18-4 "OFDM training structure"
2068  //also Section 18.3.2.3 "Modulation-dependent parameters" Table 18-4 "Modulation-dependent parameters"; IEEE Std 802.11-2012)
2069  return MicroSeconds (16);
2070  case 10:
2071  //(Section 18.3.3 "PLCP preamble (SYNC))" Figure 18-4 "OFDM training structure"
2072  //also Section 18.3.2.3 "Modulation-dependent parameters" Table 18-4 "Modulation-dependent parameters"; IEEE Std 802.11-2012)
2073  return MicroSeconds (32);
2074  case 5:
2075  //(Section 18.3.3 "PLCP preamble (SYNC))" Figure 18-4 "OFDM training structure"
2076  //also Section 18.3.2.3 "Modulation-dependent parameters" Table 18-4 "Modulation-dependent parameters"; IEEE Std 802.11-2012)
2077  return MicroSeconds (64);
2078  }
2079  }
2081  return MicroSeconds (16);
2082  case WIFI_MOD_CLASS_DSSS:
2084  {
2085  if ((preamble == WIFI_PREAMBLE_SHORT) && (txVector.GetMode ().GetDataRate (22) > 1000000))
2086  {
2087  //(Section 17.2.2.3 "Short PPDU format)" Figure 17-2 "Short PPDU format"; IEEE Std 802.11-2012)
2088  return MicroSeconds (72);
2089  }
2090  else
2091  {
2092  //(Section 17.2.2.2 "Long PPDU format)" Figure 17-1 "Long PPDU format"; IEEE Std 802.11-2012)
2093  return MicroSeconds (144);
2094  }
2095  }
2096  default:
2097  NS_FATAL_ERROR ("modulation class is not matching the preamble type");
2098  return MicroSeconds (0);
2099  }
2100  }
2101  case WIFI_PREAMBLE_HT_MF:
2102  case WIFI_PREAMBLE_VHT_SU:
2103  case WIFI_PREAMBLE_VHT_MU:
2104  case WIFI_PREAMBLE_HE_SU:
2106  case WIFI_PREAMBLE_HE_MU:
2107  case WIFI_PREAMBLE_HE_TB:
2108  //L-STF + L-LTF
2109  return MicroSeconds (16);
2110  case WIFI_PREAMBLE_HT_GF:
2111  //HT-GF-STF + HT-LTF1
2112  return MicroSeconds (16);
2113  default:
2114  NS_FATAL_ERROR ("unsupported preamble type");
2115  return MicroSeconds (0);
2116  }
2117 }
2118 
2119 Time
2120 WifiPhy::GetPayloadDuration (uint32_t size, WifiTxVector txVector, uint16_t frequency, MpduType mpdutype)
2121 {
2122  uint32_t totalAmpduSize;
2123  double totalAmpduNumSymbols;
2124  return GetPayloadDuration (size, txVector, frequency, mpdutype, false, totalAmpduSize, totalAmpduNumSymbols);
2125 }
2126 
2127 Time
2128 WifiPhy::GetPayloadDuration (uint32_t size, WifiTxVector txVector, uint16_t frequency, MpduType mpdutype,
2129  bool incFlag, uint32_t &totalAmpduSize, double &totalAmpduNumSymbols)
2130 {
2131  WifiMode payloadMode = txVector.GetMode ();
2132  NS_LOG_FUNCTION (size << payloadMode);
2133 
2134  double stbc = 1;
2135  if (txVector.IsStbc ()
2136  && (payloadMode.GetModulationClass () == WIFI_MOD_CLASS_HT
2137  || payloadMode.GetModulationClass () == WIFI_MOD_CLASS_VHT))
2138  {
2139  stbc = 2;
2140  }
2141 
2142  double Nes = 1;
2143  //todo: improve logic to reduce the number of if cases
2144  //todo: extend to NSS > 4 for VHT rates
2145  if (payloadMode == GetHtMcs21 ()
2146  || payloadMode == GetHtMcs22 ()
2147  || payloadMode == GetHtMcs23 ()
2148  || payloadMode == GetHtMcs28 ()
2149  || payloadMode == GetHtMcs29 ()
2150  || payloadMode == GetHtMcs30 ()
2151  || payloadMode == GetHtMcs31 ())
2152  {
2153  Nes = 2;
2154  }
2155  if (payloadMode.GetModulationClass () == WIFI_MOD_CLASS_VHT)
2156  {
2157  if (txVector.GetChannelWidth () == 40
2158  && txVector.GetNss () == 3
2159  && payloadMode.GetMcsValue () >= 8)
2160  {
2161  Nes = 2;
2162  }
2163  if (txVector.GetChannelWidth () == 80
2164  && txVector.GetNss () == 2
2165  && payloadMode.GetMcsValue () >= 7)
2166  {
2167  Nes = 2;
2168  }
2169  if (txVector.GetChannelWidth () == 80
2170  && txVector.GetNss () == 3
2171  && payloadMode.GetMcsValue () >= 7)
2172  {
2173  Nes = 2;
2174  }
2175  if (txVector.GetChannelWidth () == 80
2176  && txVector.GetNss () == 3
2177  && payloadMode.GetMcsValue () == 9)
2178  {
2179  Nes = 3;
2180  }
2181  if (txVector.GetChannelWidth () == 80
2182  && txVector.GetNss () == 4
2183  && payloadMode.GetMcsValue () >= 4)
2184  {
2185  Nes = 2;
2186  }
2187  if (txVector.GetChannelWidth () == 80
2188  && txVector.GetNss () == 4
2189  && payloadMode.GetMcsValue () >= 7)
2190  {
2191  Nes = 3;
2192  }
2193  if (txVector.GetChannelWidth () == 160
2194  && payloadMode.GetMcsValue () >= 7)
2195  {
2196  Nes = 2;
2197  }
2198  if (txVector.GetChannelWidth () == 160
2199  && txVector.GetNss () == 2
2200  && payloadMode.GetMcsValue () >= 4)
2201  {
2202  Nes = 2;
2203  }
2204  if (txVector.GetChannelWidth () == 160
2205  && txVector.GetNss () == 2
2206  && payloadMode.GetMcsValue () >= 7)
2207  {
2208  Nes = 3;
2209  }
2210  if (txVector.GetChannelWidth () == 160
2211  && txVector.GetNss () == 3
2212  && payloadMode.GetMcsValue () >= 3)
2213  {
2214  Nes = 2;
2215  }
2216  if (txVector.GetChannelWidth () == 160
2217  && txVector.GetNss () == 3
2218  && payloadMode.GetMcsValue () >= 5)
2219  {
2220  Nes = 3;
2221  }
2222  if (txVector.GetChannelWidth () == 160
2223  && txVector.GetNss () == 3
2224  && payloadMode.GetMcsValue () >= 7)
2225  {
2226  Nes = 4;
2227  }
2228  if (txVector.GetChannelWidth () == 160
2229  && txVector.GetNss () == 4
2230  && payloadMode.GetMcsValue () >= 2)
2231  {
2232  Nes = 2;
2233  }
2234  if (txVector.GetChannelWidth () == 160
2235  && txVector.GetNss () == 4
2236  && payloadMode.GetMcsValue () >= 4)
2237  {
2238  Nes = 3;
2239  }
2240  if (txVector.GetChannelWidth () == 160
2241  && txVector.GetNss () == 4
2242  && payloadMode.GetMcsValue () >= 5)
2243  {
2244  Nes = 4;
2245  }
2246  if (txVector.GetChannelWidth () == 160
2247  && txVector.GetNss () == 4
2248  && payloadMode.GetMcsValue () >= 7)
2249  {
2250  Nes = 6;
2251  }
2252  }
2253 
2254  Time symbolDuration = Seconds (0);
2255  switch (payloadMode.GetModulationClass ())
2256  {
2257  case WIFI_MOD_CLASS_OFDM:
2259  {
2260  //(Section 18.3.2.4 "Timing related parameters" Table 18-5 "Timing-related parameters"; IEEE Std 802.11-2012
2261  //corresponds to T_{SYM} in the table)
2262  switch (txVector.GetChannelWidth ())
2263  {
2264  case 20:
2265  default:
2266  symbolDuration = MicroSeconds (4);
2267  break;
2268  case 10:
2269  symbolDuration = MicroSeconds (8);
2270  break;
2271  case 5:
2272  symbolDuration = MicroSeconds (16);
2273  break;
2274  }
2275  break;
2276  }
2277  case WIFI_MOD_CLASS_HT:
2278  case WIFI_MOD_CLASS_VHT:
2279  {
2280  //if short GI data rate is used then symbol duration is 3.6us else symbol duration is 4us
2281  //In the future has to create a stationmanager that only uses these data rates if sender and receiver support GI
2282  uint16_t gi = txVector.GetGuardInterval ();
2283  NS_ASSERT (gi == 400 || gi == 800);
2284  symbolDuration = NanoSeconds (3200 + gi);
2285  }
2286  break;
2287  case WIFI_MOD_CLASS_HE:
2288  {
2289  //if short GI data rate is used then symbol duration is 3.6us else symbol duration is 4us
2290  //In the future has to create a stationmanager that only uses these data rates if sender and receiver support GI
2291  uint16_t gi = txVector.GetGuardInterval ();
2292  NS_ASSERT (gi == 800 || gi == 1600 || gi == 3200);
2293  symbolDuration = NanoSeconds (12800 + gi);
2294  }
2295  break;
2296  default:
2297  break;
2298  }
2299 
2300  double numDataBitsPerSymbol = payloadMode.GetDataRate (txVector) * symbolDuration.GetNanoSeconds () / 1e9;
2301 
2302  double numSymbols = 0;
2303  if (mpdutype == FIRST_MPDU_IN_AGGREGATE)
2304  {
2305  //First packet in an A-MPDU
2306  numSymbols = (stbc * (16 + size * 8.0 + 6 * Nes) / (stbc * numDataBitsPerSymbol));
2307  if (incFlag == 1)
2308  {
2309  totalAmpduSize += size;
2310  totalAmpduNumSymbols += numSymbols;
2311  }
2312  }
2313  else if (mpdutype == MIDDLE_MPDU_IN_AGGREGATE)
2314  {
2315  //consecutive packets in an A-MPDU
2316  numSymbols = (stbc * size * 8.0) / (stbc * numDataBitsPerSymbol);
2317  if (incFlag == 1)
2318  {
2319  totalAmpduSize += size;
2320  totalAmpduNumSymbols += numSymbols;
2321  }
2322  }
2323  else if (mpdutype == LAST_MPDU_IN_AGGREGATE)
2324  {
2325  //last packet in an A-MPDU
2326  uint32_t totalSize = totalAmpduSize + size;
2327  numSymbols = lrint (stbc * ceil ((16 + totalSize * 8.0 + 6 * Nes) / (stbc * numDataBitsPerSymbol)));
2328  NS_ASSERT (totalAmpduNumSymbols <= numSymbols);
2329  numSymbols -= totalAmpduNumSymbols;
2330  if (incFlag == 1)
2331  {
2332  totalAmpduSize = 0;
2333  totalAmpduNumSymbols = 0;
2334  }
2335  }
2336  else if (mpdutype == NORMAL_MPDU || mpdutype == SINGLE_MPDU)
2337  {
2338  //Not an A-MPDU or single MPDU (i.e. the current payload contains both service and padding)
2339  //The number of OFDM symbols in the data field when BCC encoding
2340  //is used is given in equation 19-32 of the IEEE 802.11-2016 standard.
2341  numSymbols = lrint (stbc * ceil ((16 + size * 8.0 + 6.0 * Nes) / (stbc * numDataBitsPerSymbol)));
2342  }
2343  else
2344  {
2345  NS_FATAL_ERROR ("Unknown MPDU type");
2346  }
2347 
2348  switch (payloadMode.GetModulationClass ())
2349  {
2350  case WIFI_MOD_CLASS_OFDM:
2352  {
2353  //Add signal extension for ERP PHY
2354  if (payloadMode.GetModulationClass () == WIFI_MOD_CLASS_ERP_OFDM)
2355  {
2356  return FemtoSeconds (static_cast<uint64_t> (numSymbols * symbolDuration.GetFemtoSeconds ())) + MicroSeconds (6);
2357  }
2358  else
2359  {
2360  return FemtoSeconds (static_cast<uint64_t> (numSymbols * symbolDuration.GetFemtoSeconds ()));
2361  }
2362  }
2363  case WIFI_MOD_CLASS_HT:
2364  case WIFI_MOD_CLASS_VHT:
2365  {
2366  if (payloadMode.GetModulationClass () == WIFI_MOD_CLASS_HT && Is2_4Ghz (frequency)
2367  && (mpdutype == NORMAL_MPDU || mpdutype == SINGLE_MPDU || mpdutype == LAST_MPDU_IN_AGGREGATE)) //at 2.4 GHz
2368  {
2369  return FemtoSeconds (static_cast<uint64_t> (numSymbols * symbolDuration.GetFemtoSeconds ())) + MicroSeconds (6);
2370  }
2371  else //at 5 GHz
2372  {
2373  return FemtoSeconds (static_cast<uint64_t> (numSymbols * symbolDuration.GetFemtoSeconds ()));
2374  }
2375  }
2376  case WIFI_MOD_CLASS_HE:
2377  {
2378  if (Is2_4Ghz (frequency)
2379  && ((mpdutype == NORMAL_MPDU || mpdutype == SINGLE_MPDU || mpdutype == LAST_MPDU_IN_AGGREGATE))) //at 2.4 GHz
2380  {
2381  return FemtoSeconds (static_cast<uint64_t> (numSymbols * symbolDuration.GetFemtoSeconds ())) + MicroSeconds (6);
2382  }
2383  else //at 5 GHz
2384  {
2385  return FemtoSeconds (static_cast<uint64_t> (numSymbols * symbolDuration.GetFemtoSeconds ()));
2386  }
2387  }
2388  case WIFI_MOD_CLASS_DSSS:
2390  return MicroSeconds (lrint (ceil ((size * 8.0) / (payloadMode.GetDataRate (22) / 1.0e6))));
2391  default:
2392  NS_FATAL_ERROR ("unsupported modulation class");
2393  return MicroSeconds (0);
2394  }
2395 }
2396 
2397 Time
2399 {
2400  WifiPreamble preamble = txVector.GetPreambleType ();
2401  Time duration = GetPlcpPreambleDuration (txVector)
2402  + GetPlcpHeaderDuration (txVector)
2403  + GetPlcpHtSigHeaderDuration (preamble)
2404  + GetPlcpSigA1Duration (preamble)
2405  + GetPlcpSigA2Duration (preamble)
2406  + GetPlcpTrainingSymbolDuration (txVector)
2407  + GetPlcpSigBDuration (preamble);
2408  return duration;
2409 }
2410 
2411 Time
2412 WifiPhy::CalculateTxDuration (uint32_t size, WifiTxVector txVector, uint16_t frequency)
2413 {
2414  Time duration = CalculatePlcpPreambleAndHeaderDuration (txVector)
2415  + GetPayloadDuration (size, txVector, frequency);
2416  return duration;
2417 }
2418 
2419 void
2421 {
2422  for (auto& mpdu : *PeekPointer (psdu))
2423  {
2424  m_phyTxBeginTrace (mpdu->GetProtocolDataUnit (), txPowerW);
2425  }
2426 }
2427 
2428 void
2430 {
2431  for (auto& mpdu : *PeekPointer (psdu))
2432  {
2433  m_phyTxEndTrace (mpdu->GetProtocolDataUnit ());
2434  }
2435 }
2436 
2437 void
2439 {
2440  for (auto& mpdu : *PeekPointer (psdu))
2441  {
2442  m_phyTxDropTrace (mpdu->GetProtocolDataUnit ());
2443  }
2444 }
2445 
2446 void
2448 {
2449  for (auto& mpdu : *PeekPointer (psdu))
2450  {
2451  m_phyRxBeginTrace (mpdu->GetProtocolDataUnit ());
2452  }
2453 }
2454 
2455 void
2457 {
2458  for (auto& mpdu : *PeekPointer (psdu))
2459  {
2460  m_phyRxEndTrace (mpdu->GetProtocolDataUnit ());
2461  }
2462 }
2463 
2464 void
2466 {
2467  for (auto& mpdu : *PeekPointer (psdu))
2468  {
2469  m_phyRxDropTrace (mpdu->GetProtocolDataUnit (), reason);
2470  }
2471 }
2472 
2473 void
2474 WifiPhy::NotifyMonitorSniffRx (Ptr<const WifiPsdu> psdu, uint16_t channelFreqMhz, WifiTxVector txVector,
2475  SignalNoiseDbm signalNoise, std::vector<bool> statusPerMpdu)
2476 {
2477  MpduInfo aMpdu;
2478  if (psdu->IsAggregate ())
2479  {
2480  //Expand A-MPDU
2481  NS_ASSERT_MSG (txVector.IsAggregation (), "TxVector with aggregate flag expected here according to PSDU");
2483  size_t nMpdus = psdu->GetNMpdus ();
2484  NS_ASSERT_MSG (statusPerMpdu.size () == nMpdus, "Should have one reception status per MPDU");
2485  aMpdu.type = (psdu->IsSingle ()) ? SINGLE_MPDU: FIRST_MPDU_IN_AGGREGATE;
2486  for (size_t i = 0; i < nMpdus;)
2487  {
2488  if (statusPerMpdu.at (i)) //packet received without error, hand over to sniffer
2489  {
2490  m_phyMonitorSniffRxTrace (psdu->GetAmpduSubframe (i), channelFreqMhz, txVector, aMpdu, signalNoise);
2491  }
2492  ++i;
2493  aMpdu.type = (i == (nMpdus - 1)) ? LAST_MPDU_IN_AGGREGATE : MIDDLE_MPDU_IN_AGGREGATE;
2494  }
2495  }
2496  else
2497  {
2498  aMpdu.type = NORMAL_MPDU;
2499  NS_ASSERT_MSG (statusPerMpdu.size () == 1, "Should have one reception status for normal MPDU");
2500  m_phyMonitorSniffRxTrace (psdu->GetPacket (), channelFreqMhz, txVector, aMpdu, signalNoise);
2501  }
2502 }
2503 
2504 void
2505 WifiPhy::NotifyMonitorSniffTx (Ptr<const WifiPsdu> psdu, uint16_t channelFreqMhz, WifiTxVector txVector)
2506 {
2507  MpduInfo aMpdu;
2508  if (psdu->IsAggregate ())
2509  {
2510  //Expand A-MPDU
2511  NS_ASSERT_MSG (txVector.IsAggregation (), "TxVector with aggregate flag expected here according to PSDU");
2513  size_t nMpdus = psdu->GetNMpdus ();
2514  aMpdu.type = (psdu->IsSingle ()) ? SINGLE_MPDU: FIRST_MPDU_IN_AGGREGATE;
2515  for (size_t i = 0; i < nMpdus;)
2516  {
2517  m_phyMonitorSniffTxTrace (psdu->GetAmpduSubframe (i), channelFreqMhz, txVector, aMpdu);
2518  ++i;
2519  aMpdu.type = (i == (nMpdus - 1)) ? LAST_MPDU_IN_AGGREGATE : MIDDLE_MPDU_IN_AGGREGATE;
2520  }
2521  }
2522  else
2523  {
2524  aMpdu.type = NORMAL_MPDU;
2525  m_phyMonitorSniffTxTrace (psdu->GetPacket (), channelFreqMhz, txVector, aMpdu);
2526  }
2527 }
2528 
2529 void
2531 {
2532  m_phyEndOfHePreambleTrace (params);
2533 }
2534 
2535 void
2537 {
2538  NS_LOG_FUNCTION (this << *psdu << txVector);
2539  /* Transmission can happen if:
2540  * - we are syncing on a packet. It is the responsibility of the
2541  * MAC layer to avoid doing this but the PHY does nothing to
2542  * prevent it.
2543  * - we are idle
2544  */
2545  NS_ASSERT (!m_state->IsStateTx () && !m_state->IsStateSwitching ());
2546 
2547  if (txVector.GetNss () > GetMaxSupportedTxSpatialStreams ())
2548  {
2549  NS_FATAL_ERROR ("Unsupported number of spatial streams!");
2550  }
2551 
2552  if (m_state->IsStateSleep ())
2553  {
2554  NS_LOG_DEBUG ("Dropping packet because in sleep mode");
2555  NotifyTxDrop (psdu);
2556  return;
2557  }
2558 
2559  Time txDuration = CalculateTxDuration (psdu->GetSize (), txVector, GetFrequency ());
2560  NS_ASSERT (txDuration.IsStrictlyPositive ());
2561 
2562  if (m_currentEvent != 0)
2563  {
2564  MaybeCcaBusyDuration (); //needed to keep busy state afterwards
2565  }
2566 
2568  {
2570  }
2571  if (m_endPlcpRxEvent.IsRunning ())
2572  {
2574  }
2575  if (m_endRxEvent.IsRunning ())
2576  {
2577  m_endRxEvent.Cancel ();
2578  }
2579  if (m_state->IsStateRx ())
2580  {
2582  }
2583 
2584  if (m_powerRestricted)
2585  {
2586  NS_LOG_DEBUG ("Transmitting with power restriction");
2587  }
2588  else
2589  {
2590  NS_LOG_DEBUG ("Transmitting without power restriction");
2591  }
2592 
2593  double txPowerW = DbmToW (GetTxPowerForTransmission (txVector) + GetTxGain ());
2594  NotifyTxBegin (psdu, txPowerW);
2595  m_phyTxPsduBeginTrace (psdu, txVector, txPowerW);
2596  NotifyMonitorSniffTx (psdu, GetFrequency (), txVector);
2597  m_state->SwitchToTx (txDuration, psdu->GetPacket (), GetPowerDbm (txVector.GetTxPowerLevel ()), txVector);
2598 
2599  if (m_state->GetState () == WifiPhyState::OFF)
2600  {
2601  NS_LOG_DEBUG ("Transmission canceled because device is OFF");
2602  return;
2603  }
2604 
2605  Ptr<WifiPpdu> ppdu = Create<WifiPpdu> (psdu, txVector, txDuration, GetFrequency ());
2606 
2607  if (m_wifiRadioEnergyModel != 0 && m_wifiRadioEnergyModel->GetMaximumTimeInState (WifiPhyState::TX) < txDuration)
2608  {
2609  ppdu->SetTruncatedTx ();
2610  }
2611 
2612  StartTx (ppdu);
2613 
2614  m_channelAccessRequested = false;
2615  m_powerRestricted = false;
2616 }
2617 
2618 void
2619 WifiPhy::StartReceiveHeader (Ptr<Event> event, Time headerPayloadDuration)
2620 {
2621  NS_LOG_FUNCTION (this << *event << headerPayloadDuration);
2622  NS_ASSERT (!IsStateRx ());
2624 
2626  double snr = snrPer.snr;
2627  NS_LOG_DEBUG ("snr(dB)=" << RatioToDb (snrPer.snr) << ", per=" << snrPer.per);
2628 
2629  if (!m_preambleDetectionModel || (m_preambleDetectionModel->IsPreambleDetected (event->GetRxPowerW (), snr, m_channelWidth)))
2630  {
2631  m_state->SwitchToRx (headerPayloadDuration);
2632  NotifyRxBegin (event->GetPsdu ());
2633 
2635  WifiTxVector txVector = event->GetTxVector ();
2636 
2637  if ((txVector.GetMode ().GetModulationClass () == WIFI_MOD_CLASS_HT) && (txVector.GetPreambleType () == WIFI_PREAMBLE_HT_GF))
2638  {
2639  //No non-HT PHY header for HT GF
2640  Time remainingPreambleHeaderDuration = CalculatePlcpPreambleAndHeaderDuration (txVector) - GetPreambleDetectionDuration ();
2641  m_endPlcpRxEvent = Simulator::Schedule (remainingPreambleHeaderDuration, &WifiPhy::StartReceivePayload, this, event);
2642  }
2643  else
2644  {
2645  //Schedule end of non-HT PHY header
2646  Time remainingPreambleAndNonHtHeaderDuration = GetPlcpPreambleDuration (txVector) + GetPlcpHeaderDuration (txVector) - GetPreambleDetectionDuration ();
2647  m_endPlcpRxEvent = Simulator::Schedule (remainingPreambleAndNonHtHeaderDuration, &WifiPhy::ContinueReceiveHeader, this, event);
2648  }
2649  }
2650  else
2651  {
2652  NS_LOG_DEBUG ("Drop packet because PHY preamble detection failed");
2653  NotifyRxDrop (event->GetPsdu (), PREAMBLE_DETECT_FAILURE);
2655  m_currentEvent = 0;
2656  }
2657  // Like CCA-SD, CCA-ED is governed by the 4μs CCA window to flag CCA-BUSY
2658  // for any received signal greater than the CCA-ED threshold.
2660 }
2661 
2662 void
2664 {
2665  NS_LOG_FUNCTION (this << *event);
2666  NS_ASSERT (IsStateRx ());
2668 
2671 
2672  if (m_random->GetValue () > snrPer.per) //non-HT PHY header reception succeeded
2673  {
2674  NS_LOG_DEBUG ("Received non-HT PHY header");
2675  WifiTxVector txVector = event->GetTxVector ();
2676  Time remainingPreambleHeaderDuration = CalculatePlcpPreambleAndHeaderDuration (txVector) - GetPlcpPreambleDuration (txVector) - GetPlcpHeaderDuration (txVector);
2677  m_endPlcpRxEvent = Simulator::Schedule (remainingPreambleHeaderDuration, &WifiPhy::StartReceivePayload, this, event);
2678  }
2679  else //non-HT PHY header reception failed
2680  {
2681  NS_LOG_DEBUG ("Abort reception because non-HT PHY header reception failed");
2683  }
2684 }
2685 
2686 void
2688 {
2689  NS_LOG_FUNCTION (this << *ppdu << rxPowerW);
2690  WifiTxVector txVector = ppdu->GetTxVector ();
2691  Time rxDuration = ppdu->GetTxDuration ();
2692  Ptr<const WifiPsdu> psdu = ppdu->GetPsdu ();
2693  Ptr<Event> event = m_interference.Add (ppdu, txVector, rxDuration, rxPowerW);
2694 
2695  if (m_state->GetState () == WifiPhyState::OFF)
2696  {
2697  NS_LOG_DEBUG ("Cannot start RX because device is OFF");
2698  return;
2699  }
2700 
2701  if (ppdu->IsTruncatedTx ())
2702  {
2703  NS_LOG_DEBUG ("Packet reception stopped because transmitter has been switched off");
2704  return;
2705  }
2706 
2707  if (!txVector.GetModeInitialized ())
2708  {
2709  //If SetRate method was not called above when filling in txVector, this means the PHY does support the rate indicated in PHY SIG headers
2710  NS_LOG_DEBUG ("drop packet because of unsupported RX mode");
2712  return;
2713  }
2714 
2715  Time endRx = Simulator::Now () + rxDuration;
2716  switch (m_state->GetState ())
2717  {
2719  NS_LOG_DEBUG ("drop packet because of channel switching");
2720  NotifyRxDrop (psdu, NOT_ALLOWED);
2721  /*
2722  * Packets received on the upcoming channel are added to the event list
2723  * during the switching state. This way the medium can be correctly sensed
2724  * when the device listens to the channel for the first time after the
2725  * switching e.g. after channel switching, the channel may be sensed as
2726  * busy due to other devices' tramissions started before the end of
2727  * the switching.
2728  */
2729  if (endRx > Simulator::Now () + m_state->GetDelayUntilIdle ())
2730  {
2731  //that packet will be noise _after_ the completion of the channel switching.
2733  return;
2734  }
2735  break;
2736  case WifiPhyState::RX:
2737  NS_ASSERT (m_currentEvent != 0);
2738  if (m_frameCaptureModel != 0
2739  && m_frameCaptureModel->IsInCaptureWindow (m_timeLastPreambleDetected)
2740  && m_frameCaptureModel->CaptureNewFrame (m_currentEvent, event))
2741  {
2743  NS_LOG_DEBUG ("Switch to new packet");
2744  StartRx (event, rxPowerW);
2745  }
2746  else
2747  {
2748  NS_LOG_DEBUG ("Drop packet because already in Rx (power=" <<
2749  rxPowerW << "W)");
2750  NotifyRxDrop (psdu, NOT_ALLOWED);
2751  if (endRx > Simulator::Now () + m_state->GetDelayUntilIdle ())
2752  {
2753  //that packet will be noise _after_ the reception of the currently-received packet.
2755  return;
2756  }
2757  }
2758  break;
2759  case WifiPhyState::TX:
2760  NS_LOG_DEBUG ("Drop packet because already in Tx (power=" <<
2761  rxPowerW << "W)");
2762  NotifyRxDrop (psdu, NOT_ALLOWED);
2763  if (endRx > Simulator::Now () + m_state->GetDelayUntilIdle ())
2764  {
2765  //that packet will be noise _after_ the transmission of the currently-transmitted packet.
2767  return;
2768  }
2769  break;
2771  case WifiPhyState::IDLE:
2772  StartRx (event, rxPowerW);
2773  break;
2774  case WifiPhyState::SLEEP:
2775  NS_LOG_DEBUG ("Drop packet because in sleep mode");
2776  NotifyRxDrop (psdu, NOT_ALLOWED);
2777  break;
2778  default:
2779  NS_FATAL_ERROR ("Invalid WifiPhy state.");
2780  break;
2781  }
2782 }
2783 
2784 void
2786 {
2787  //We are here because we have received the first bit of a packet and we are
2788  //not going to be able to synchronize on it
2789  //In this model, CCA becomes busy when the aggregation of all signals as
2790  //tracked by the InterferenceHelper class is higher than the CcaBusyThreshold
2791 
2793  if (!delayUntilCcaEnd.IsZero ())
2794  {
2795  m_state->SwitchMaybeToCcaBusy (delayUntilCcaEnd);
2796  }
2797 }
2798 
2799 void
2801 {
2802  NS_LOG_FUNCTION (this << *event);
2803  NS_ASSERT (IsStateRx ());
2806  WifiTxVector txVector = event->GetTxVector ();
2807  WifiMode txMode = txVector.GetMode ();
2808  bool canReceivePayload;
2809  if (txMode.GetModulationClass () >= WIFI_MOD_CLASS_HT)
2810  {
2812  snrPer = m_interference.CalculateHtPhyHeaderSnrPer (event);
2813  NS_LOG_DEBUG ("snr(dB)=" << RatioToDb (snrPer.snr) << ", per=" << snrPer.per);
2814  canReceivePayload = (m_random->GetValue () > snrPer.per);
2815  }
2816  else
2817  {
2818  //If we are here, this means non-HT PHY header was already successfully received
2819  canReceivePayload = true;
2820  }
2821  if (canReceivePayload) //plcp reception succeeded
2822  {
2823  if (txVector.GetNss () > GetMaxSupportedRxSpatialStreams ())
2824  {
2825  NS_LOG_DEBUG ("Packet reception could not be started because not enough RX antennas");
2826  NotifyRxDrop (event->GetPsdu (), UNSUPPORTED_SETTINGS);
2827  }
2828  else if ((txVector.GetChannelWidth () >= 40) && (txVector.GetChannelWidth () > GetChannelWidth ()))
2829  {
2830  NS_LOG_DEBUG ("Packet reception could not be started because not enough channel width");
2831  NotifyRxDrop (event->GetPsdu (), UNSUPPORTED_SETTINGS);
2832  }
2833  else if (!IsModeSupported (txMode) && !IsMcsSupported (txMode))
2834  {
2835  NS_LOG_DEBUG ("Drop packet because it was sent using an unsupported mode (" << txMode << ")");
2836  NotifyRxDrop (event->GetPsdu (), UNSUPPORTED_SETTINGS);
2837  }
2838  else
2839  {
2840  Time payloadDuration = event->GetEndTime () - event->GetStartTime () - CalculatePlcpPreambleAndHeaderDuration (txVector);
2841  m_endRxEvent = Simulator::Schedule (payloadDuration, &WifiPhy::EndReceive, this, event);
2842  NS_LOG_DEBUG ("Receiving payload");
2843  if (txMode.GetModulationClass () == WIFI_MOD_CLASS_HE)
2844  {
2845  HePreambleParameters params;
2846  params.rssiW = event->GetRxPowerW ();
2847  params.bssColor = event->GetTxVector ().GetBssColor ();
2848  NotifyEndOfHePreamble (params);
2849  }
2850  return;
2851  }
2852  }
2853  else //plcp reception failed
2854  {
2855  NS_LOG_DEBUG ("Drop packet because HT PHY header reception failed");
2856  NotifyRxDrop (event->GetPsdu (), SIG_A_FAILURE);
2857  }
2859  m_currentEvent = 0;
2861 }
2862 
2863 void
2865 {
2866  Time psduDuration = event->GetEndTime () - event->GetStartTime ();
2867  NS_LOG_FUNCTION (this << *event << psduDuration);
2868  NS_ASSERT (event->GetEndTime () == Simulator::Now ());
2869 
2870  double snr = m_interference.CalculateSnr (event);
2871  std::vector<bool> statusPerMpdu;
2872  SignalNoiseDbm signalNoise;
2873 
2874  Ptr<const WifiPsdu> psdu = event->GetPsdu ();
2875  Time relativeStart = NanoSeconds (0);
2876  bool receptionOkAtLeastForOneMpdu = false;
2877  std::pair<bool, SignalNoiseDbm> rxInfo;
2878  WifiTxVector txVector = event->GetTxVector ();
2879  size_t nMpdus = psdu->GetNMpdus ();
2880  if (nMpdus > 1)
2881  {
2882  //Extract all MPDUs of the A-MPDU to compute per-MPDU PER stats
2883  Time remainingAmpduDuration = psduDuration;
2884  MpduType mpdutype = FIRST_MPDU_IN_AGGREGATE;
2885  auto mpdu = psdu->begin ();
2886  uint32_t totalAmpduSize = 0;
2887  double totalAmpduNumSymbols = 0.0;
2888  for (size_t i = 0; i < nMpdus && mpdu != psdu->end (); ++mpdu)
2889  {
2890  Time mpduDuration = GetPayloadDuration (psdu->GetAmpduSubframeSize (i), txVector,
2891  GetFrequency (), mpdutype, true, totalAmpduSize, totalAmpduNumSymbols);
2892  remainingAmpduDuration -= mpduDuration;
2893  if (i == (nMpdus - 1) && !remainingAmpduDuration.IsZero ()) //no more MPDU coming
2894  {
2895  mpduDuration += remainingAmpduDuration; //apply a correction just in case rounding had induced slight shift
2896  }
2897  rxInfo = GetReceptionStatus (Create<WifiPsdu> (*mpdu, false),
2898  event, relativeStart, mpduDuration);
2899  NS_LOG_DEBUG ("Extracted MPDU #" << i << ": duration: " << mpduDuration.GetNanoSeconds () << "ns" <<
2900  ", correct reception: " << rxInfo.first <<
2901  ", Signal/Noise: " << rxInfo.second.signal << "/" << rxInfo.second.noise << "dBm");
2902  signalNoise = rxInfo.second; //same information for all MPDUs
2903  statusPerMpdu.push_back (rxInfo.first);
2904  receptionOkAtLeastForOneMpdu |= rxInfo.first;
2905 
2906  //Prepare next iteration
2907  ++i;
2908  relativeStart += mpduDuration;
2909  mpdutype = (i == (nMpdus - 1)) ? LAST_MPDU_IN_AGGREGATE : MIDDLE_MPDU_IN_AGGREGATE;
2910  }
2911  }
2912  else
2913  {
2914  rxInfo = GetReceptionStatus (psdu, event, relativeStart, psduDuration);
2915  signalNoise = rxInfo.second; //same information for all MPDUs
2916  statusPerMpdu.push_back (rxInfo.first);
2917  receptionOkAtLeastForOneMpdu = rxInfo.first;
2918  }
2919 
2920  if (receptionOkAtLeastForOneMpdu)
2921  {
2922  NotifyMonitorSniffRx (psdu, GetFrequency (), txVector, signalNoise, statusPerMpdu);
2923  m_state->SwitchFromRxEndOk (Copy (psdu), snr, txVector, statusPerMpdu);
2924  }
2925  else
2926  {
2927  m_state->SwitchFromRxEndError (Copy (psdu), snr);
2928  }
2929 
2931  m_currentEvent = 0;
2933 }
2934 
2935 std::pair<bool, SignalNoiseDbm>
2936 WifiPhy::GetReceptionStatus (Ptr<const WifiPsdu> psdu, Ptr<Event> event, Time relativeMpduStart, Time mpduDuration)
2937 {
2938  NS_LOG_FUNCTION (this << *psdu << *event << relativeMpduStart << mpduDuration);
2940  snrPer = m_interference.CalculatePayloadSnrPer (event, std::make_pair (relativeMpduStart, relativeMpduStart + mpduDuration));
2941 
2942  NS_LOG_DEBUG ("mode=" << (event->GetTxVector ().GetMode ().GetDataRate (event->GetTxVector ())) <<
2943  ", snr(dB)=" << RatioToDb (snrPer.snr) << ", per=" << snrPer.per << ", size=" << psdu->GetSize () <<
2944  ", relativeStart = " << relativeMpduStart.GetNanoSeconds () << "ns, duration = " << mpduDuration.GetNanoSeconds () << "ns");
2945 
2946  // There are two error checks: PER and receive error model check.
2947  // PER check models is typical for Wi-Fi and is based on signal modulation;
2948  // Receive error model is optional, if we have an error model and
2949  // it indicates that the packet is corrupt, drop the packet.
2950  SignalNoiseDbm signalNoise;
2951  signalNoise.signal = WToDbm (event->GetRxPowerW ());
2952  signalNoise.noise = WToDbm (event->GetRxPowerW () / snrPer.snr);
2953  if (m_random->GetValue () > snrPer.per &&
2954  !(m_postReceptionErrorModel && m_postReceptionErrorModel->IsCorrupt (psdu->GetPacket ()->Copy ())))
2955  {
2956  NS_LOG_DEBUG ("Reception succeeded: " << psdu);
2957  NotifyRxEnd (psdu);
2958  return std::make_pair (true, signalNoise);
2959  }
2960  else
2961  {
2962  NS_LOG_DEBUG ("Reception failed: " << psdu);
2963  NotifyRxDrop (psdu, ERRONEOUS_FRAME);
2964  return std::make_pair (false, signalNoise);
2965  }
2966 }
2967 
2968 void
2970 {
2971  NS_LOG_FUNCTION (this);
2973  {
2974  m_powerRestricted = false;
2975  }
2976 }
2977 
2978 void
2980 {
2981  NS_LOG_FUNCTION (this);
2982  m_channelAccessRequested = true;
2983 }
2984 
2985 // Clause 15 rates (DSSS)
2986 
2987 WifiMode
2989 {
2990  static WifiMode mode =
2991  WifiModeFactory::CreateWifiMode ("DsssRate1Mbps",
2993  true,
2995  2);
2996  return mode;
2997 }
2998 
2999 WifiMode
3001 {
3002  static WifiMode mode =
3003  WifiModeFactory::CreateWifiMode ("DsssRate2Mbps",
3005  true,
3007  4);
3008  return mode;
3009 }
3010 
3011 
3012 // Clause 18 rates (HR/DSSS)
3013 
3014 WifiMode
3016 {
3017  static WifiMode mode =
3018  WifiModeFactory::CreateWifiMode ("DsssRate5_5Mbps",
3020  true,
3022  16);
3023  return mode;
3024 }
3025 
3026 WifiMode
3028 {
3029  static WifiMode mode =
3030  WifiModeFactory::CreateWifiMode ("DsssRate11Mbps",
3032  true,
3034  256);
3035  return mode;
3036 }
3037 
3038 
3039 // Clause 19.5 rates (ERP-OFDM)
3040 
3041 WifiMode
3043 {
3044  static WifiMode mode =
3045  WifiModeFactory::CreateWifiMode ("ErpOfdmRate6Mbps",
3047  true,
3049  2);
3050  return mode;
3051 }
3052 
3053 WifiMode
3055 {
3056  static WifiMode mode =
3057  WifiModeFactory::CreateWifiMode ("ErpOfdmRate9Mbps",
3059  false,
3061  2);
3062  return mode;
3063 }
3064 
3065 WifiMode
3067 {
3068  static WifiMode mode =
3069  WifiModeFactory::CreateWifiMode ("ErpOfdmRate12Mbps",
3071  true,
3073  4);
3074  return mode;
3075 }
3076 
3077 WifiMode
3079 {
3080  static WifiMode mode =
3081  WifiModeFactory::CreateWifiMode ("ErpOfdmRate18Mbps",
3083  false,
3085  4);
3086  return mode;
3087 }
3088 
3089 WifiMode
3091 {
3092  static WifiMode mode =
3093  WifiModeFactory::CreateWifiMode ("ErpOfdmRate24Mbps",
3095  true,
3097  16);
3098  return mode;
3099 }
3100 
3101 WifiMode
3103 {
3104  static WifiMode mode =
3105  WifiModeFactory::CreateWifiMode ("ErpOfdmRate36Mbps",
3107  false,
3109  16);
3110  return mode;
3111 }
3112 
3113 WifiMode
3115 {
3116  static WifiMode mode =
3117  WifiModeFactory::CreateWifiMode ("ErpOfdmRate48Mbps",
3119  false,
3121  64);
3122  return mode;
3123 }
3124 
3125 WifiMode
3127 {
3128  static WifiMode mode =
3129  WifiModeFactory::CreateWifiMode ("ErpOfdmRate54Mbps",
3131  false,
3133  64);
3134  return mode;
3135 }
3136 
3137 
3138 // Clause 17 rates (OFDM)
3139 
3140 WifiMode
3142 {
3143  static WifiMode mode =
3144  WifiModeFactory::CreateWifiMode ("OfdmRate6Mbps",
3146  true,
3148  2);
3149  return mode;
3150 }
3151 
3152 WifiMode
3154 {
3155  static WifiMode mode =
3156  WifiModeFactory::CreateWifiMode ("OfdmRate9Mbps",
3158  false,
3160  2);
3161  return mode;
3162 }
3163 
3164 WifiMode
3166 {
3167  static WifiMode mode =
3168  WifiModeFactory::CreateWifiMode ("OfdmRate12Mbps",
3170  true,
3172  4);
3173  return mode;
3174 }
3175 
3176 WifiMode
3178 {
3179  static WifiMode mode =
3180  WifiModeFactory::CreateWifiMode ("OfdmRate18Mbps",
3182  false,
3184  4);
3185  return mode;
3186 }
3187 
3188 WifiMode
3190 {
3191  static WifiMode mode =
3192  WifiModeFactory::CreateWifiMode ("OfdmRate24Mbps",
3194  true,
3196  16);
3197  return mode;
3198 }
3199 
3200 WifiMode
3202 {
3203  static WifiMode mode =
3204  WifiModeFactory::CreateWifiMode ("OfdmRate36Mbps",
3206  false,
3208  16);
3209  return mode;
3210 }
3211 
3212 WifiMode
3214 {
3215  static WifiMode mode =
3216  WifiModeFactory::CreateWifiMode ("OfdmRate48Mbps",
3218  false,
3220  64);
3221  return mode;
3222 }
3223 
3224 WifiMode
3226 {
3227  static WifiMode mode =
3228  WifiModeFactory::CreateWifiMode ("OfdmRate54Mbps",
3230  false,
3232  64);
3233  return mode;
3234 }
3235 
3236 
3237 // 10 MHz channel rates
3238 
3239 WifiMode
3241 {
3242  static WifiMode mode =
3243  WifiModeFactory::CreateWifiMode ("OfdmRate3MbpsBW10MHz",
3245  true,
3247  2);
3248  return mode;
3249 }
3250 
3251 WifiMode
3253 {
3254  static WifiMode mode =
3255  WifiModeFactory::CreateWifiMode ("OfdmRate4_5MbpsBW10MHz",
3257  false,
3259  2);
3260  return mode;
3261 }
3262 
3263 WifiMode
3265 {
3266  static WifiMode mode =
3267  WifiModeFactory::CreateWifiMode ("OfdmRate6MbpsBW10MHz",
3269  true,
3271  4);
3272  return mode;
3273 }
3274 
3275 WifiMode
3277 {
3278  static WifiMode mode =
3279  WifiModeFactory::CreateWifiMode ("OfdmRate9MbpsBW10MHz",
3281  false,
3283  4);
3284  return mode;
3285 }
3286 
3287 WifiMode
3289 {
3290  static WifiMode mode =
3291  WifiModeFactory::CreateWifiMode ("OfdmRate12MbpsBW10MHz",
3293  true,
3295  16);
3296  return mode;
3297 }
3298 
3299 WifiMode
3301 {
3302  static WifiMode mode =
3303  WifiModeFactory::CreateWifiMode ("OfdmRate18MbpsBW10MHz",
3305  false,
3307  16);
3308  return mode;
3309 }
3310 
3311 WifiMode
3313 {
3314  static WifiMode mode =
3315  WifiModeFactory::CreateWifiMode ("OfdmRate24MbpsBW10MHz",
3317  false,
3319  64);
3320  return mode;
3321 }
3322 
3323 WifiMode
3325 {
3326  static WifiMode mode =
3327  WifiModeFactory::CreateWifiMode ("OfdmRate27MbpsBW10MHz",
3329  false,
3331  64);
3332  return mode;
3333 }
3334 
3335 
3336 // 5 MHz channel rates
3337 
3338 WifiMode
3340 {
3341  static WifiMode mode =
3342  WifiModeFactory::CreateWifiMode ("OfdmRate1_5MbpsBW5MHz",
3344  true,
3346  2);
3347  return mode;
3348 }
3349 
3350 WifiMode
3352 {
3353  static WifiMode mode =
3354  WifiModeFactory::CreateWifiMode ("OfdmRate2_25MbpsBW5MHz",
3356  false,
3358  2);
3359  return mode;
3360 }
3361 
3362 WifiMode
3364 {
3365  static WifiMode mode =
3366  WifiModeFactory::CreateWifiMode ("OfdmRate3MbpsBW5MHz",
3368  true,
3370  4);
3371  return mode;
3372 }
3373 
3374 WifiMode
3376 {
3377  static WifiMode mode =
3378  WifiModeFactory::CreateWifiMode ("OfdmRate4_5MbpsBW5MHz",
3380  false,
3382  4);
3383  return mode;
3384 }
3385 
3386 WifiMode
3388 {
3389  static WifiMode mode =
3390  WifiModeFactory::CreateWifiMode ("OfdmRate6MbpsBW5MHz",
3392  true,
3394  16);
3395  return mode;
3396 }
3397 
3398 WifiMode
3400 {
3401  static WifiMode mode =
3402  WifiModeFactory::CreateWifiMode ("OfdmRate9MbpsBW5MHz",
3404  false,
3406  16);
3407  return mode;
3408 }
3409 
3410 WifiMode
3412 {
3413  static WifiMode mode =
3414  WifiModeFactory::CreateWifiMode ("OfdmRate12MbpsBW5MHz",
3416  false,
3418  64);
3419  return mode;
3420 }
3421 
3422 WifiMode
3424 {
3425  static WifiMode mode =
3426  WifiModeFactory::CreateWifiMode ("OfdmRate13_5MbpsBW5MHz",
3428  false,
3430  64);
3431  return mode;
3432 }
3433 
3434 
3435 // Clause 20
3436 
3437 WifiMode
3439 {
3440  static WifiMode mcs =
3442  return mcs;
3443 }
3444 
3445 WifiMode
3447 {
3448  static WifiMode mcs =
3450  return mcs;
3451 }
3452 
3453 WifiMode
3455 {
3456  static WifiMode mcs =
3458  return mcs;
3459 }
3460 
3461 WifiMode
3463 {
3464  static WifiMode mcs =
3466  return mcs;
3467 }
3468 
3469 WifiMode
3471 {
3472  static WifiMode mcs =
3474  return mcs;
3475 }
3476 
3477 WifiMode
3479 {
3480  static WifiMode mcs =
3482  return mcs;
3483 }
3484 
3485 WifiMode
3487 {
3488  static WifiMode mcs =
3490  return mcs;
3491 }
3492 
3493 WifiMode
3495 {
3496  static WifiMode mcs =
3498  return mcs;
3499 }
3500 
3501 WifiMode
3503 {
3504  static WifiMode mcs =
3506  return mcs;
3507 }
3508 
3509 WifiMode
3511 {
3512  static WifiMode mcs =
3514  return mcs;
3515 }
3516 
3517 WifiMode
3519 {
3520  static WifiMode mcs =
3522  return mcs;
3523 }
3524 
3525 WifiMode
3527 {
3528  static WifiMode mcs =
3530  return mcs;
3531 }
3532 
3533 WifiMode
3535 {
3536  static WifiMode mcs =
3538  return mcs;
3539 }
3540 
3541 WifiMode
3543 {
3544  static WifiMode mcs =
3546  return mcs;
3547 }
3548 
3549 WifiMode
3551 {
3552  static WifiMode mcs =
3554  return mcs;
3555 }
3556 
3557 WifiMode
3559 {
3560  static WifiMode mcs =
3562  return mcs;
3563 }
3564 
3565 WifiMode
3567 {
3568  static WifiMode mcs =
3570  return mcs;
3571 }
3572 
3573 WifiMode
3575 {
3576  static WifiMode mcs =
3578  return mcs;
3579 }
3580 
3581 WifiMode
3583 {
3584  static WifiMode mcs =
3586  return mcs;
3587 }
3588 
3589 WifiMode
3591 {
3592  static WifiMode mcs =
3594  return mcs;
3595 }
3596 
3597 WifiMode
3599 {
3600  static WifiMode mcs =
3602  return mcs;
3603 }
3604 
3605 WifiMode
3607 {
3608  static WifiMode mcs =
3610  return mcs;
3611 }
3612 
3613 WifiMode
3615 {
3616  static WifiMode mcs =
3618  return mcs;
3619 }
3620 
3621 WifiMode
3623 {
3624  static WifiMode mcs =
3626  return mcs;
3627 }
3628 
3629 WifiMode
3631 {
3632  static WifiMode mcs =
3634  return mcs;
3635 }
3636 
3637 WifiMode
3639 {
3640  static WifiMode mcs =
3642  return mcs;
3643 }
3644 
3645 WifiMode
3647 {
3648  static WifiMode mcs =
3650  return mcs;
3651 }
3652 
3653 WifiMode
3655 {
3656  static WifiMode mcs =
3658  return mcs;
3659 }
3660 
3661 WifiMode
3663 {
3664  static WifiMode mcs =
3666  return mcs;
3667 }
3668 
3669 WifiMode
3671 {
3672  static WifiMode mcs =
3674  return mcs;
3675 }
3676 
3677 WifiMode
3679 {
3680  static WifiMode mcs =
3682  return mcs;
3683 }
3684 
3685 WifiMode
3687 {
3688  static WifiMode mcs =
3690  return mcs;
3691 }
3692 
3693 
3694 // Clause 22
3695 
3696 WifiMode
3698 {
3699  static WifiMode mcs =
3701  return mcs;
3702 }
3703 
3704 WifiMode
3706 {
3707  static WifiMode mcs =
3709  return mcs;
3710 }
3711 
3712 WifiMode
3714 {
3715  static WifiMode mcs =
3717  return mcs;
3718 }
3719 
3720 WifiMode
3722 {
3723  static WifiMode mcs =
3725  return mcs;
3726 }
3727 
3728 WifiMode
3730 {
3731  static WifiMode mcs =
3733  return mcs;
3734 }
3735 
3736 WifiMode
3738 {
3739  static WifiMode mcs =
3741  return mcs;
3742 }
3743 
3744 WifiMode
3746 {
3747  static WifiMode mcs =
3749  return mcs;
3750 }
3751 
3752 WifiMode
3754 {
3755  static WifiMode mcs =
3757  return mcs;
3758 }
3759 
3760 WifiMode
3762 {
3763  static WifiMode mcs =
3765  return mcs;
3766 }
3767 
3768 WifiMode
3770 {
3771  static WifiMode mcs =
3773  return mcs;
3774 }
3775 
3776 // Clause 26
3777 
3778 WifiMode
3780 {
3781  static WifiMode mcs =
3783  return mcs;
3784 }
3785 
3786 WifiMode
3788 {
3789  static WifiMode mcs =
3791  return mcs;
3792 }
3793 
3794 WifiMode
3796 {
3797  static WifiMode mcs =
3799  return mcs;
3800 }
3801 
3802 WifiMode
3804 {
3805  static WifiMode mcs =
3807  return mcs;
3808 }
3809 
3810 WifiMode
3812 {
3813  static WifiMode mcs =
3815  return mcs;
3816 }
3817 
3818 WifiMode
3820 {
3821  static WifiMode mcs =
3823  return mcs;
3824 }
3825 
3826 WifiMode
3828 {
3829  static WifiMode mcs =
3831  return mcs;
3832 }
3833 
3834 WifiMode
3836 {
3837  static WifiMode mcs =
3839  return mcs;
3840 }
3841 
3842 WifiMode
3844 {
3845  static WifiMode mcs =
3847  return mcs;
3848 }
3849 
3850 WifiMode
3852 {
3853  static WifiMode mcs =
3855  return mcs;
3856 }
3857 
3858 WifiMode
3860 {
3861  static WifiMode mcs =
3863  return mcs;
3864 }
3865 
3866 WifiMode
3868 {
3869  static WifiMode mcs =
3871  return mcs;
3872 }
3873 
3874 bool
3876 {
3877  for (uint8_t i = 0; i < GetNModes (); i++)
3878  {
3879  if (mode == GetMode (i))
3880  {
3881  return true;
3882  }
3883  }
3884  return false;
3885 }
3886 
3887 bool
3889 {
3890  WifiModulationClass modulation = mcs.GetModulationClass ();
3891  if (modulation == WIFI_MOD_CLASS_HT || modulation == WIFI_MOD_CLASS_VHT
3892  || modulation == WIFI_MOD_CLASS_HE)
3893  {
3894  return IsMcsSupported (modulation, mcs.GetMcsValue ());
3895  }
3896  return false;
3897 }
3898 
3899 bool
3901 {
3902  if (m_mcsIndexMap.find (mc) == m_mcsIndexMap.end ())
3903  {
3904  return false;
3905  }
3906  if (m_mcsIndexMap.at (mc).find (mcs) == m_mcsIndexMap.at (mc).end ())
3907  {
3908  return false;
3909  }
3910  return true;
3911 }
3912 
3913 uint8_t
3915 {
3916  return static_cast<uint8_t> (m_deviceRateSet.size ());
3917 }
3918 
3919 WifiMode
3920 WifiPhy::GetMode (uint8_t mode) const
3921 {
3922  return m_deviceRateSet[mode];
3923 }
3924 
3925 uint8_t
3926 WifiPhy::GetNMcs (void) const
3927 {
3928  return static_cast<uint8_t> (m_deviceMcsSet.size ());
3929 }
3930 
3931 WifiMode
3932 WifiPhy::GetMcs (uint8_t mcs) const
3933 {
3934  return m_deviceMcsSet[mcs];
3935 }
3936 
3937 WifiMode
3938 WifiPhy::GetMcs (WifiModulationClass modulation, uint8_t mcs) const
3939 {
3940  NS_ASSERT_MSG (IsMcsSupported (modulation, mcs), "Unsupported MCS");
3941  uint8_t index = m_mcsIndexMap.at (modulation).at (mcs);
3942  NS_ASSERT (index < m_deviceMcsSet.size ());
3943  WifiMode mode = m_deviceMcsSet[index];
3944  NS_ASSERT (mode.GetModulationClass () == modulation);
3945  NS_ASSERT (mode.GetMcsValue () == mcs);
3946  return mode;
3947 }
3948 
3949 WifiMode
3950 WifiPhy::GetHtMcs (uint8_t mcs) const
3951 {
3952  return GetMcs (WIFI_MOD_CLASS_HT, mcs);
3953 }
3954 
3955 WifiMode
3956 WifiPhy::GetVhtMcs (uint8_t mcs) const
3957 {
3958  return GetMcs (WIFI_MOD_CLASS_VHT, mcs);
3959 }
3960 
3961 WifiMode
3962 WifiPhy::GetHeMcs (uint8_t mcs) const
3963 {
3964  return GetMcs (WIFI_MOD_CLASS_HE, mcs);
3965 }
3966 
3967 bool
3969 {
3970  return m_state->IsStateCcaBusy ();
3971 }
3972 
3973 bool
3975 {
3976  return m_state->IsStateIdle ();
3977 }
3978 
3979 bool
3981 {
3982  return m_state->IsStateRx ();
3983 }
3984 
3985 bool
3987 {
3988  return m_state->IsStateTx ();
3989 }
3990 
3991 bool
3993 {
3994  return m_state->IsStateSwitching ();
3995 }
3996 
3997 bool
3999 {
4000  return m_state->IsStateSleep ();
4001 }
4002 
4003 bool
4005 {
4006  return m_state->IsStateOff ();
4007 }
4008 
4009 Time
4011 {
4012  return m_state->GetDelayUntilIdle ();
4013 }
4014 
4015 Time
4017 {
4018  return m_state->GetLastRxStartTime ();
4019 }
4020 
4021 void
4023 {
4024  NS_LOG_FUNCTION (this);
4025  //We are here because we have received the first bit of a packet and we are
4026  //not going to be able to synchronize on it
4027  //In this model, CCA becomes busy when the aggregation of all signals as
4028  //tracked by the InterferenceHelper class is higher than the CcaBusyThreshold
4029 
4031  if (!delayUntilCcaEnd.IsZero ())
4032  {
4033  NS_LOG_DEBUG ("Calling SwitchMaybeToCcaBusy for " << delayUntilCcaEnd.As (Time::S));
4034  m_state->SwitchMaybeToCcaBusy (delayUntilCcaEnd);
4035  }
4036 }
4037 
4038 void
4040 {
4041  NS_LOG_FUNCTION (this << reason);
4043  {
4045  }
4046  if (m_endPlcpRxEvent.IsRunning ())
4047  {
4049  }
4050  if (m_endRxEvent.IsRunning ())
4051  {
4052  m_endRxEvent.Cancel ();
4053  }
4054  NotifyRxDrop (m_currentEvent->GetPsdu (), reason);
4056  bool is_failure = (reason != OBSS_PD_CCA_RESET);
4057  m_state->SwitchFromRxAbort (is_failure);
4058  m_currentEvent = 0;
4059 }
4060 
4061 void
4062 WifiPhy::ResetCca (bool powerRestricted, double txPowerMaxSiso, double txPowerMaxMimo)
4063 {
4064  NS_LOG_FUNCTION (this << powerRestricted << txPowerMaxSiso << txPowerMaxMimo);
4065  m_powerRestricted = powerRestricted;
4066  m_txPowerMaxSiso = txPowerMaxSiso;
4067  m_txPowerMaxMimo = txPowerMaxMimo;
4068  NS_ASSERT ((m_currentEvent->GetEndTime () - Simulator::Now ()).IsPositive ());
4071 }
4072 
4073 double
4075 {
4077  if (!m_powerRestricted)
4078  {
4079  return GetPowerDbm (txVector.GetTxPowerLevel ());
4080  }
4081  else
4082  {
4083  if (txVector.GetNss () > 1)
4084  {
4085  return std::min (m_txPowerMaxMimo, GetPowerDbm (txVector.GetTxPowerLevel ()));
4086  }
4087  else
4088  {
4089  return std::min (m_txPowerMaxSiso, GetPowerDbm (txVector.GetTxPowerLevel ()));
4090  }
4091  }
4092 }
4093 
4094 void
4095 WifiPhy::StartRx (Ptr<Event> event, double rxPowerW)
4096 {
4097  NS_LOG_FUNCTION (this << *event << rxPowerW);
4098 
4099  NS_LOG_DEBUG ("sync to signal (power=" << rxPowerW << "W)");
4100  m_interference.NotifyRxStart (); //We need to notify it now so that it starts recording events
4101 
4103  {
4104  Time startOfPreambleDuration = GetPreambleDetectionDuration ();
4105  Time remainingRxDuration = event->GetDuration () - startOfPreambleDuration;
4107  event, remainingRxDuration);
4108  }
4109  else if ((m_frameCaptureModel != 0) && (rxPowerW > m_currentEvent->GetRxPowerW ()))
4110  {
4111  NS_LOG_DEBUG ("Received a stronger signal during preamble detection: drop current packet and switch to new packet");
4116  Time startOfPreambleDuration = GetPreambleDetectionDuration ();
4117  Time remainingRxDuration = event->GetDuration () - startOfPreambleDuration;
4119  event, remainingRxDuration);
4120  }
4121  else
4122  {
4123  NS_LOG_DEBUG ("Drop packet because RX is already decoding preamble");
4124  NotifyRxDrop (event->GetPsdu (), NOT_ALLOWED);
4125  return;
4126  }
4127  m_currentEvent = event;
4128 }
4129 
4130 int64_t
4131 WifiPhy::AssignStreams (int64_t stream)
4132 {
4133  NS_LOG_FUNCTION (this << stream);
4134  m_random->SetStream (stream);
4135  return 1;
4136 }
4137 
4138 } //namespace ns3
4139 
4140 namespace {
4141 
4145 static class Constructor
4146 {
4147 public:
4149  {
4240  }
4241 } g_constructor;
4242 
4243 }
static class anonymous_namespace{wifi-phy.cc}::Constructor g_constructor
the constructor
ERP-OFDM PHY (Clause 19, Section 19.5)
MpduInfo structure.
Definition: wifi-phy.h:76
static WifiMode GetVhtMcs6()
Return MCS 6 from VHT MCS values.
Definition: wifi-phy.cc:3745
void NotifyRxDrop(Ptr< const WifiPsdu > psdu, WifiPhyRxfailureReason reason)
Public method used to fire a PhyRxDrop trace.
Definition: wifi-phy.cc:2465
static WifiMode GetOfdmRate9MbpsBW5MHz()
Return a WifiMode for OFDM at 9Mbps with 5MHz channel spacing.
Definition: wifi-phy.cc:3399
TracedCallback< Ptr< const Packet > > m_phyRxBeginTrace
The trace source fired when a packet begins the reception process from the medium.
Definition: wifi-phy.h:1854
Ptr< NetDevice > m_device
Pointer to the device.
Definition: wifi-phy.h:1988
static WifiMode GetErpOfdmRate24Mbps()
Return a WifiMode for ERP-OFDM at 24Mbps.
Definition: wifi-phy.cc:3090
uint8_t GetNTxPower(void) const
Return the number of available transmission power levels.
Definition: wifi-phy.cc:585
bool IsStateSwitching(void) const
Definition: wifi-phy.cc:3992
static WifiMode GetDsssRate11Mbps()
Return a WifiMode for DSSS at 11Mbps.
Definition: wifi-phy.cc:3027
bool IsStateOff(void) const
Definition: wifi-phy.cc:4004
double signal
in dBm
Definition: wifi-phy.h:71
bool IsAggregation(void) const
Checks whether the PSDU contains A-MPDU.
Simulation virtual time values and global simulation resolution.
Definition: nstime.h:102
static WifiMode GetHeMcs7()
Return MCS 7 from HE MCS values.
Definition: wifi-phy.cc:3835
std::pair< uint8_t, WifiPhyStandard > ChannelNumberStandardPair
A pair of a ChannelNumber and WifiPhyStandard.
Definition: wifi-phy.h:594
static WifiMode GetErpOfdmRate36Mbps()
Return a WifiMode for ERP-OFDM at 36Mbps.
Definition: wifi-phy.cc:3102
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 "...
OFDM PHY for the 5 GHz band (Clause 17 with 5 MHz channel bandwidth)
void SetStream(int64_t stream)
Specifies the stream number for the RngStream.
void SetNTxPower(uint8_t n)
Sets the number of transmission power levels available between the minimum level and the maximum leve...
Definition: wifi-phy.cc:578
uint8_t m_channelNumber
Operating channel number.
Definition: wifi-phy.h:1983
double m_rxGainDb
Reception gain (dB)
Definition: wifi-phy.h:1959
bool DefineChannelNumber(uint8_t channelNumber, WifiPhyStandard standard, uint16_t frequency, uint16_t channelWidth)
Add a channel definition to the WifiPhy.
Definition: wifi-phy.cc:1153
static WifiMode GetVhtMcs8()
Return MCS 8 from VHT MCS values.
Definition: wifi-phy.cc:3761
ERP-OFDM PHY (19.5)
Definition: wifi-mode.h:54
void SetShortPlcpPreambleSupported(bool preamble)
Enable or disable short PLCP preamble.
Definition: wifi-phy.cc:711
AttributeValue implementation for Boolean.
Definition: boolean.h:36
void SetNumberOfReceiveAntennas(uint8_t rx)
Set the number of RX antennas in the receiver corresponding to this interference helper.
Ptr< HeConfiguration > GetHeConfiguration(void) const
double GetRxGain(void) const
Return the reception gain (dB).
Definition: wifi-phy.cc:611
bool IsModeSupported(WifiMode mode) const
Check if the given WifiMode is supported by the PHY.
Definition: wifi-phy.cc:3875
WifiMode GetHeMcs(uint8_t mcs) const
Get the WifiMode object corresponding to the given MCS of the HE modulation class.
Definition: wifi-phy.cc:3962
static WifiMode GetOfdmRate9Mbps()
Return a WifiMode for OFDM at 9Mbps.
Definition: wifi-phy.cc:3153
double GetCcaEdThreshold(void) const
Return the CCA threshold (dBm).
Definition: wifi-phy.cc:538
HT PHY for the 5 GHz band (clause 20)
Ptr< ErrorRateModel > GetErrorRateModel(void) const
Return the error rate model.
static WifiMode GetOfdmRate18MbpsBW10MHz()
Return a WifiMode for OFDM at 18Mbps with 10MHz channel spacing.
Definition: wifi-phy.cc:3300
This class mimics the TXVECTOR which is to be passed to the PHY in order to define the parameters whi...
static WifiMode GetOfdmRate27MbpsBW10MHz()
Return a WifiMode for OFDM at 27Mbps with 10MHz channel spacing.
Definition: wifi-phy.cc:3324
TracedCallback< Ptr< const Packet >, uint16_t, WifiTxVector, MpduInfo, SignalNoiseDbm > m_phyMonitorSniffRxTrace
A trace source that emulates a wifi device in monitor mode sniffing a packet being received...
Definition: wifi-phy.h:1883
double m_txGainDb
Transmission gain (dB)
Definition: wifi-phy.h:1958
WifiMode GetMcs(uint8_t mcs) const
The WifiPhy::GetMcs() method is used (e.g., by a WifiRemoteStationManager) to determine the set of tr...
Definition: wifi-phy.cc:3932
#define NS_OBJECT_ENSURE_REGISTERED(type)
Register an Object subclass with the TypeId system.
Definition: object-base.h:45
static WifiMode GetOfdmRate3MbpsBW5MHz()
Return a WifiMode for OFDM at 3Mbps with 5MHz channel spacing.
Definition: wifi-phy.cc:3363
static WifiMode GetVhtMcs0()
Return MCS 0 from VHT MCS values.
Definition: wifi-phy.cc:3697
void AbortCurrentReception(WifiPhyRxfailureReason reason)
Due to newly arrived signal, the current reception cannot be continued and has to be aborted...
Definition: wifi-phy.cc:4039
void MaybeCcaBusyDuration(void)
Eventually switch to CCA busy.
Definition: wifi-phy.cc:2785
WifiPhyStandard GetStandard(void) const
Get the configured Wi-Fi standard.
Definition: wifi-phy.cc:1305
virtual ~WifiPhy()
Definition: wifi-phy.cc:412
static WifiMode GetDsssRate1Mbps()
Return a WifiMode for DSSS at 1Mbps.
Definition: wifi-phy.cc:2988
NS_ASSERT_MSG(false, "Ipv4AddressGenerator::MaskToIndex(): Impossible")
void ResumeFromOff(void)
Resume from off mode.
Definition: wifi-phy.cc:1742
Ptr< WifiPhyStateHelper > GetState(void) const
Return the WifiPhyStateHelper of this PHY.
Definition: wifi-phy.cc:448
void ResumeFromSleep(void)
Resume from sleep mode.
Definition: wifi-phy.cc:1712
#define min(a, b)
Definition: 80211b.c:42
double m_rxSensitivityW
Receive sensitivity threshold in watts.
Definition: wifi-phy.h:1956
bool GetShortGuardInterval(void) const
Return whether short guard interval is supported.
Definition: wifi-phy.cc:664
bool GetGreenfield(void) const
Return whether Greenfield is supported.
Definition: wifi-phy.cc:633
static WifiMode GetHeMcs5()
Return MCS 5 from HE MCS values.
Definition: wifi-phy.cc:3819
Time m_timeLastPreambleDetected
Record the time the last preamble was detected.
Definition: wifi-phy.h:1996
static WifiMode GetErpOfdmRate18Mbps()
Return a WifiMode for ERP-OFDM at 18Mbps.
Definition: wifi-phy.cc:3078
void SetTxGain(double gain)
Sets the transmission gain (dB).
Definition: wifi-phy.cc:591
void Configure80211ax(void)
Configure WifiPhy with appropriate channel frequency and supported rates for 802.11ax standard...
Definition: wifi-phy.cc:1124
double DbmToW(double dBm)
Convert from dBm to Watts.
Definition: wifi-utils.cc:41
static WifiMode GetHtMcs7()
Return MCS 7 from HT MCS values.
Definition: wifi-phy.cc:3494
void SetRxSensitivity(double threshold)
Sets the receive sensitivity threshold (dBm).
Definition: wifi-phy.cc:518
Ptr< const AttributeAccessor > MakeBooleanAccessor(T1 a1)
Create an AttributeAccessor for a class data member, or a lone class get functor or set method...
Definition: boolean.h:85
virtual void DoDispose(void)
Destructor implementation.
Definition: wifi-phy.cc:418
def start()
Definition: core.py:1855
bool Is2_4Ghz(double frequency)
Definition: wifi-utils.cc:59
void RebuildMcsMap(void)
Rebuild the mapping of MCS values to indices in the device MCS set.
Definition: wifi-phy.cc:1005
TracedCallback< Ptr< const WifiPsdu >, WifiTxVector, double > m_phyTxPsduBeginTrace
The trace source fired when a PSDU begins the transmission process on the medium. ...
Definition: wifi-phy.h:1830
static Time GetPlcpHtSigHeaderDuration(WifiPreamble preamble)
Definition: wifi-phy.cc:1846
static WifiMode GetVhtMcs5()
Return MCS 5 from VHT MCS values.
Definition: wifi-phy.cc:3737
uint8_t GetNBssMembershipSelectors(void) const
The WifiPhy::NBssMembershipSelectors() method is used (e.g., by a WifiRemoteStationManager) to determ...
Definition: wifi-phy.cc:1445
The PHY layer is sleeping.
static WifiMode GetHtMcs22()
Return MCS 22 from HT MCS values.
Definition: wifi-phy.cc:3614
static WifiMode GetHtMcs14()
Return MCS 14 from HT MCS values.
Definition: wifi-phy.cc:3550
static WifiMode GetOfdmRate12Mbps()
Return a WifiMode for OFDM at 12Mbps.
Definition: wifi-phy.cc:3165
TracedCallback< Ptr< const Packet > > m_phyRxEndTrace
The trace source fired when a packet ends the reception process from the medium.
Definition: wifi-phy.h:1862
#define HE_PHY
Definition: wifi-phy.h:35
bool IsStateCcaBusy(void) const
Definition: wifi-phy.cc:3968
void SetReceiveErrorCallback(RxErrorCallback callback)
Definition: wifi-phy.cc:460
static WifiMode GetHtMcs31()
Return MCS 31 from HT MCS values.
Definition: wifi-phy.cc:3686
static WifiMode GetHtMcs21()
Return MCS 21 from HT MCS values.
Definition: wifi-phy.cc:3606
#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
bool IsInitialized(void) const
Check if the object has been initialized.
Definition: object.cc:208
U * PeekPointer(const Ptr< U > &p)
Definition: ptr.h:566
static WifiMode GetHtMcs30()
Return MCS 30 from HT MCS values.
Definition: wifi-phy.cc:3678
#define NS_LOG_COMPONENT_DEFINE(name)
Define a Log component with a specific name.
Definition: log.h:205
void SetErrorRateModel(const Ptr< ErrorRateModel > rate)
Set the error rate model for this interference helper.
std::vector< uint8_t > m_bssMembershipSelectorSet
the BSS membership selector set
Definition: wifi-phy.h:1947
HE PHY for the 2.4 GHz band (clause 26)
std::pair< bool, SignalNoiseDbm > GetReceptionStatus(Ptr< const WifiPsdu > psdu, Ptr< Event > event, Time relativeMpduStart, Time mpduDuration)
Get the reception status for the provided MPDU and notify.
Definition: wifi-phy.cc:2936
static WifiMode GetHtMcs10()
Return MCS 10 from HT MCS values.
Definition: wifi-phy.cc:3518
static WifiMode GetHtMcs26()
Return MCS 26 from HT MCS values.
Definition: wifi-phy.cc:3646
static WifiMode GetOfdmRate1_5MbpsBW5MHz()
Return a WifiMode for OFDM at 1.5Mbps with 5MHz channel spacing.
Definition: wifi-phy.cc:3339
OFDM PHY for the 5 GHz band (Clause 17 with 10 MHz channel bandwidth)
static WifiMode GetHtMcs17()
Return MCS 17 from HT MCS values.
Definition: wifi-phy.cc:3574
static WifiMode GetHtMcs24()
Return MCS 24 from HT MCS values.
Definition: wifi-phy.cc:3630
bool IsStbc(void) const
Check if STBC is used or not.
static WifiMode GetOfdmRate4_5MbpsBW10MHz()
Return a WifiMode for OFDM at 4.5Mbps with 10MHz channel spacing.
Definition: wifi-phy.cc:3252
bool GetModeInitialized(void) const
static WifiMode GetOfdmRate54Mbps()
Return a WifiMode for OFDM at 54Mbps.
Definition: wifi-phy.cc:3225
void SetMobility(const Ptr< MobilityModel > mobility)
assign a mobility model to this device
Definition: wifi-phy.cc:748
void UnregisterListener(WifiPhyListener *listener)
Definition: wifi-phy.cc:472
void SetRxNoiseFigure(double noiseFigureDb)
Sets the RX loss (dB) in the Signal-to-Noise-Ratio due to non-idealities in the receiver.
Definition: wifi-phy.cc:544
WifiMode GetVhtMcs(uint8_t mcs) const
Get the WifiMode object corresponding to the given MCS of the VHT modulation class.
Definition: wifi-phy.cc:3956
#define NS_FATAL_ERROR(msg)
Report a fatal error with a message and terminate.
Definition: fatal-error.h:162
bool IsStrictlyPositive(void) const
Definition: nstime.h:308
static WifiMode GetHeMcs4()
Return MCS 4 from HE MCS values.
Definition: wifi-phy.cc:3811
uint8_t GetNess(void) const
void ConfigureHolland(void)
Configure WifiPhy with appropriate channel frequency and supported rates for holland.
Definition: wifi-phy.cc:980
bool IsStateIdle(void) const
Definition: wifi-phy.cc:3974
uint16_t GetGuardInterval(void) const
bool Is5Ghz(double frequency)
Definition: wifi-utils.cc:65
HT PHY for the 2.4 GHz band (clause 20)
void SetGreenfield(bool greenfield)
Enable or disable Greenfield support.
Definition: wifi-phy.cc:617
VHT PHY (Clause 22)
Definition: wifi-mode.h:60
void Configure80211_10Mhz(void)
Configure WifiPhy with appropriate channel frequency and supported rates for 802.11a standard with 10...
Definition: wifi-phy.cc:950
TimeWithUnit As(const enum Unit unit) const
Attach a unit to a Time, to facilitate output in a specific unit.
Definition: time.cc:389
TracedCallback< Ptr< const Packet >, WifiPhyRxfailureReason > m_phyRxDropTrace
The trace source fired when the phy layer drops a packet it has received.
Definition: wifi-phy.h:1869
HR/DSSS PHY (Clause 18)
Definition: wifi-mode.h:48
std::pair< uint16_t, uint16_t > FrequencyWidthPair
A pair of a center Frequency and a ChannelWidth.
Definition: wifi-phy.h:598
static WifiMode GetHtMcs8()
Return MCS 8 from HT MCS values.
Definition: wifi-phy.cc:3502
uint8_t m_nTxPower
Number of available transmission power levels.
Definition: wifi-phy.h:1962
static WifiMode GetHtMcs18()
Return MCS 18 from HT MCS values.
Definition: wifi-phy.cc:3582
double GetTxPowerForTransmission(WifiTxVector txVector) const
Compute the transmit power (in dBm) for the next transmission.
Definition: wifi-phy.cc:4074
virtual void SetFrequency(uint16_t freq)
Definition: wifi-phy.cc:1311
static WifiMode GetVhtMcs4()
Return MCS 4 from VHT MCS values.
Definition: wifi-phy.cc:3729
static WifiMode GetHtMcs27()
Return MCS 27 from HT MCS values.
Definition: wifi-phy.cc:3654
void SetFrameCaptureModel(const Ptr< FrameCaptureModel > frameCaptureModel)
Sets the frame capture model.
Definition: wifi-phy.cc:781
void ResetCca(bool powerRestricted, double txPowerMaxSiso=0, double txPowerMaxMimo=0)
Reset PHY to IDLE, with some potential TX power restrictions for the next transmission.
Definition: wifi-phy.cc:4062
TracedCallback< Ptr< const Packet >, uint16_t, WifiTxVector, MpduInfo > m_phyMonitorSniffTxTrace
A trace source that emulates a wifi device in monitor mode sniffing a packet being transmitted...
Definition: wifi-phy.h:1897
represent a single transmission modeA WifiMode is implemented by a single integer which is used to lo...
Definition: wifi-mode.h:97
static WifiMode GetOfdmRate36Mbps()
Return a WifiMode for OFDM at 36Mbps.
Definition: wifi-phy.cc:3201
uint8_t m_initialChannelNumber
Initial channel number.
Definition: wifi-phy.h:1984
void NotifyRxEnd(Ptr< const WifiPsdu > psdu)
Public method used to fire a PhyRxEnd trace.
Definition: wifi-phy.cc:2456
static WifiMode GetVhtMcs7()
Return MCS 7 from VHT MCS values.
Definition: wifi-phy.cc:3753
static WifiMode GetOfdmRate6MbpsBW5MHz()
Return a WifiMode for OFDM at 6Mbps with 5MHz channel spacing.
Definition: wifi-phy.cc:3387
bool IsStateSleep(void) const
Definition: wifi-phy.cc:3998
void NotifyEndOfHePreamble(HePreambleParameters params)
Public method used to fire a EndOfHePreamble trace once both HE SIG fields have been received...
Definition: wifi-phy.cc:2530
bool IsExpired(void) const
This method is syntactic sugar for the ns3::Simulator::IsExpired method.
Definition: event-id.cc:59
static WifiMode GetVhtMcs3()
Return MCS 3 from VHT MCS values.
Definition: wifi-phy.cc:3721
void ConfigureDefaultsForStandard(WifiPhyStandard standard)
Configure the PHY-level parameters for different Wi-Fi standard.
Definition: wifi-phy.cc:829
struct InterferenceHelper::SnrPer CalculateNonHtPhyHeaderSnrPer(Ptr< Event > event) const
Calculate the SNIR at the start of the non-HT PHY header and accumulate all SNIR changes in the snir ...
static Time GetPlcpSigA1Duration(WifiPreamble preamble)
Definition: wifi-phy.cc:1861
MpduType
The type of an MPDU.
double GetRxSensitivity(void) const
Return the receive sensitivity threshold (dBm).
Definition: wifi-phy.cc:525
void NotifyTxEnd(Ptr< const WifiPsdu > psdu)
Public method used to fire a PhyTxEnd trace.
Definition: wifi-phy.cc:2429
Ptr< const TraceSourceAccessor > MakeTraceSourceAccessor(T a)
Create a TraceSourceAccessor which will control access to the underlying trace source.
WifiModeList m_deviceMcsSet
the device MCS set
Definition: wifi-phy.h:1943
mobility
Definition: third.py:108
Ptr< const AttributeChecker > MakeTimeChecker(const Time min, const Time max)
Helper to make a Time checker with bounded range.
Definition: time.cc:449
uint16_t m_channelCenterFrequency
Center frequency in MHz.
Definition: wifi-phy.h:1951
void SetDevice(const Ptr< NetDevice > device)
Sets the device this PHY is associated with.
Definition: wifi-phy.cc:724
bool GetShortPlcpPreambleSupported(void) const
Return whether short PLCP preamble is supported.
Definition: wifi-phy.cc:718
static WifiMode GetHtMcs16()
Return MCS 16 from HT MCS values.
Definition: wifi-phy.cc:3566
uint16_t GetChannelWidth(void) const
Definition: wifi-phy.cc:1388
bool m_powerRestricted
Flag whether transmit power is restricted by OBSS PD SR.
Definition: wifi-phy.h:1964
static WifiMode GetErpOfdmRate54Mbps()
Return a WifiMode for ERP-OFDM at 54Mbps.
Definition: wifi-phy.cc:3126
WifiPreamble GetPreambleType(void) const
void AddSupportedChannelWidth(uint16_t channelwidth)
Definition: wifi-phy.cc:1457
static WifiMode GetHtMcs29()
Return MCS 29 from HT MCS values.
Definition: wifi-phy.cc:3670
static WifiMode GetHtMcs11()
Return MCS 11 from HT MCS values.
Definition: wifi-phy.cc:3526
uint8_t GetNMcs(void) const
The WifiPhy::GetNMcs() method is used (e.g., by a WifiRemoteStationManager) to determine the set of t...
Definition: wifi-phy.cc:3926
static Time CalculateTxDuration(uint32_t size, WifiTxVector txVector, uint16_t frequency)
Definition: wifi-phy.cc:2412
WifiPreamble
The type of preamble to be used by an IEEE 802.11 transmission.
Definition: wifi-preamble.h:32
Keep track of the current position and velocity of an object.
static ChannelToFrequencyWidthMap m_channelToFrequencyWidth
the channel to frequency width map
Definition: wifi-phy.h:1980
WifiPhyStandard
Identifies the PHY specification that a Wifi device is configured to use.
The MPDU is not part of an A-MPDU.
double rssiW
RSSI in W.
Definition: wifi-phy.h:85
uint8_t bssColor
BSS color.
Definition: wifi-phy.h:86
The MPDU is the first aggregate in an A-MPDU with multiple MPDUs, but is not the last aggregate...
static Time GetPlcpSigA2Duration(WifiPreamble preamble)
Definition: wifi-phy.cc:1878
HE PHY for the 5 GHz band (clause 26)
bool DoFrequencySwitch(uint16_t frequency)
The default implementation does nothing and returns true.
Definition: wifi-phy.cc:1606
static WifiMode GetHtMcs2()
Return MCS 2 from HT MCS values.
Definition: wifi-phy.cc:3454
Ptr< const AttributeAccessor > MakePointerAccessor(T1 a1)
Create an AttributeAccessor for a class data member, or a lone class get functor or set method...
Definition: pointer.h:227
static EventId Schedule(Time const &delay, MEM mem_ptr, OBJ obj)
Schedule an event to expire after delay.
Definition: simulator.h:1390
Ptr< MobilityModel > m_mobility
Pointer to the mobility model.
Definition: wifi-phy.h:1989
bool IsZero(void) const
Definition: nstime.h:288
AttributeValue implementation for Time.
Definition: nstime.h:1126
void StartRx(Ptr< Event > event, double rxPowerW)
Starting receiving the PPDU after having detected the medium is idle or after a reception switch...
Definition: wifi-phy.cc:4095
static Time GetPlcpPreambleDuration(WifiTxVector txVector)
Definition: wifi-phy.cc:2051
Time NanoSeconds(uint64_t value)
Construct a Time in the indicated unit.
Definition: nstime.h:1088
receive notifications about phy events.
TracedCallback< Ptr< const Packet > > m_phyTxDropTrace
The trace source fired when the phy layer drops a packet as it tries to transmit it.
Definition: wifi-phy.h:1846
Time GetEnergyDuration(double energyW) const
double m_txPowerMaxMimo
MIMO maximum transmit power due to OBSS PD SR power restriction.
Definition: wifi-phy.h:1966
bool m_shortPreamble
Flag if short PLCP preamble is supported.
Definition: wifi-phy.h:1971
static WifiMode GetHeMcs3()
Return MCS 3 from HE MCS values.
Definition: wifi-phy.cc:3803
static Time GetPlcpSigBDuration(WifiPreamble preamble)
Definition: wifi-phy.cc:1895
Hold an unsigned integer type.
Definition: uinteger.h:44
static WifiMode CreateWifiMode(std::string uniqueName, WifiModulationClass modClass, bool isMandatory, WifiCodeRate codingRate, uint16_t constellationSize)
Definition: wifi-mode.cc:688
EventId m_endPlcpRxEvent
the end of PLCP receive event
Definition: wifi-phy.h:1674
static WifiMode GetHtMcs12()
Return MCS 12 from HT MCS values.
Definition: wifi-phy.cc:3534
Ptr< WifiRadioEnergyModel > m_wifiRadioEnergyModel
Wifi radio energy model.
Definition: wifi-phy.h:1994
static WifiMode GetErpOfdmRate48Mbps()
Return a WifiMode for ERP-OFDM at 48Mbps.
Definition: wifi-phy.cc:3114
static Time CalculatePlcpPreambleAndHeaderDuration(WifiTxVector txVector)
Definition: wifi-phy.cc:2398
void SetTxPowerEnd(double end)
Sets the maximum available transmission power level (dBm).
Definition: wifi-phy.cc:565
void SetPreambleDetectionModel(const Ptr< PreambleDetectionModel > preambleDetectionModel)
Sets the preamble detection model.
Definition: wifi-phy.cc:787
The MPDU is part of an A-MPDU with multiple MPDUs, but is neither the first nor the last aggregate...
static WifiMode GetOfdmRate12MbpsBW10MHz()
Return a WifiMode for OFDM at 12Mbps with 10MHz channel spacing.
Definition: wifi-phy.cc:3288
WifiMode GetHtMcs(uint8_t mcs) const
Get the WifiMode object corresponding to the given MCS of the HT modulation class.
Definition: wifi-phy.cc:3950
void NotifyChannelAccessRequested(void)
Notify the PHY that an access to the channel was requested.
Definition: wifi-phy.cc:2979
WifiMode GetMode(void) const
static WifiMode GetHeMcs11()
Return MCS 11 from HE MCS values.
Definition: wifi-phy.cc:3867
The PHY layer has sense the medium busy through the CCA mechanism.
HT PHY (Clause 20)
Definition: wifi-mode.h:58
Time GetDelayUntilIdle(void)
Definition: wifi-phy.cc:4010
uint32_t m_rxMpduReferenceNumber
A-MPDU reference number to identify all received subframes belonging to the same received A-MPDU...
Definition: wifi-phy.h:1671
void Configure80211_5Mhz()
Configure WifiPhy with appropriate channel frequency and supported rates for 802.11a standard with 5M...
Definition: wifi-phy.cc:965
FrequencyWidthPair GetFrequencyWidthForChannelNumberStandard(uint8_t channelNumber, WifiPhyStandard standard) const
Lookup frequency/width pair for channelNumber/standard pair.
Definition: wifi-phy.cc:1478
TracedCallback< HePreambleParameters > m_phyEndOfHePreambleTrace
A trace source that indiates the end of both HE SIG fields as well as training fields for received 80...
Definition: wifi-phy.h:1904
double CalculateSnr(WifiTxVector txVector, double ber) const
Definition: wifi-phy.cc:823
static WifiMode GetOfdmRate18Mbps()
Return a WifiMode for OFDM at 18Mbps.
Definition: wifi-phy.cc:3177
void SetCapabilitiesChangedCallback(Callback< void > callback)
Definition: wifi-phy.cc:478
void SetOffMode(void)
Put in off mode.
Definition: wifi-phy.cc:1700
static WifiMode GetOfdmRate9MbpsBW10MHz()
Return a WifiMode for OFDM at 9Mbps with 10MHz channel spacing.
Definition: wifi-phy.cc:3276
static WifiMode GetOfdmRate12MbpsBW5MHz()
Return a WifiMode for OFDM at 12Mbps with 5MHz channel spacing.
Definition: wifi-phy.cc:3411
WifiModulationClass GetModulationClass() const
Definition: wifi-mode.cc:494
Ptr< PreambleDetectionModel > m_preambleDetectionModel
Preamble detection model.
Definition: wifi-phy.h:1993
double GetPowerDbm(uint8_t power) const
Get the power of the given power level in dBm.
Definition: wifi-phy.cc:799
static WifiMode GetVhtMcs1()
Return MCS 1 from VHT MCS values.
Definition: wifi-phy.cc:3705
EventId m_endPreambleDetectionEvent
the end of preamble detection event
Definition: wifi-phy.h:1675
This is intended to be the configuration used in this paper: Gavin Holland, Nitin Vaidya and Paramvir...
static WifiMode GetOfdmRate48Mbps()
Return a WifiMode for OFDM at 48Mbps.
Definition: wifi-phy.cc:3213
void NotifyRxBegin(Ptr< const WifiPsdu > psdu)
Public method used to fire a PhyRxBegin trace.
Definition: wifi-phy.cc:2447
void SetErrorRateModel(const Ptr< ErrorRateModel > rate)
Sets the error rate model.
Definition: wifi-phy.cc:767
void StartReceivePreamble(Ptr< WifiPpdu > ppdu, double rxPowerW)
Start receiving the PHY preamble of a PPDU (i.e.
Definition: wifi-phy.cc:2687
static WifiMode GetHeMcs9()
Return MCS 9 from HE MCS values.
Definition: wifi-phy.cc:3851
double f(double x, void *params)
Definition: 80211b.c:70
static WifiMode GetHtMcs0()
Return MCS 0 from HT MCS values.
Definition: wifi-phy.cc:3438
Ptr< MobilityModel > GetMobility(void) const
Return the mobility model this PHY is associated with.
Definition: wifi-phy.cc:754
static Time GetPreambleDetectionDuration(void)
Definition: wifi-phy.cc:1791
void SetPostReceptionErrorModel(const Ptr< ErrorModel > em)
Attach a receive ErrorModel to the WifiPhy.
Definition: wifi-phy.cc:774
static TypeId GetTypeId(void)
Get the type ID.
Definition: wifi-phy.cc:162
Time GetChannelSwitchDelay(void) const
Definition: wifi-phy.cc:817
OFDM PHY for the 5 GHz band (Clause 17)
void ContinueReceiveHeader(Ptr< Event > event)
Continue receiving the PHY header of a PPDU (i.e.
Definition: wifi-phy.cc:2663
Every class exported by the ns3 library is enclosed in the ns3 namespace.
void NotifyRxStart()
Notify that RX has started.
Hold objects of type Ptr<T>.
Definition: pointer.h:36
void SetWifiRadioEnergyModel(const Ptr< WifiRadioEnergyModel > wifiRadioEnergyModel)
Sets the wifi radio energy model.
Definition: wifi-phy.cc:793
int64_t GetNanoSeconds(void) const
Get an approximation of the time stored in this instance in the indicated unit.
Definition: nstime.h:367
Time m_guardInterval
Supported HE guard interval (deprecated)
Definition: wifi-phy.h:1973
void EraseEvents(void)
Erase all events.
uint16_t GetFrequency(void) const
Definition: wifi-phy.cc:1368
The PHY layer is IDLE.
uint8_t GetNumberOfAntennas(void) const
Definition: wifi-phy.cc:1402
static WifiMode GetOfdmRate24Mbps()
Return a WifiMode for OFDM at 24Mbps.
Definition: wifi-phy.cc:3189
Ptr< const AttributeChecker > MakeBooleanChecker(void)
Definition: boolean.cc:121
void NotifyTxDrop(Ptr< const WifiPsdu > psdu)
Public method used to fire a PhyTxDrop trace.
Definition: wifi-phy.cc:2438
virtual void SetChannelWidth(uint16_t channelwidth)
Definition: wifi-phy.cc:1374
static WifiMode GetHeMcs1()
Return MCS 1 from HE MCS values.
Definition: wifi-phy.cc:3787
TracedCallback< Ptr< const Packet >, double > m_phyTxBeginTrace
The trace source fired when a packet begins the transmission process on the medium.
Definition: wifi-phy.h:1823
DSSS PHY (Clause 15) and HR/DSSS PHY (Clause 18)
virtual void StartTx(Ptr< WifiPpdu > ppdu)=0
static WifiMode GetHtMcs13()
Return MCS 13 from HT MCS values.
Definition: wifi-phy.cc:3542
void SetShortGuardInterval(bool shortGuardInterval)
Enable or disable support for HT/VHT short guard interval.
Definition: wifi-phy.cc:648
static WifiMode GetHeMcs0()
Return MCS 0 from HE MCS values.
Definition: wifi-phy.cc:3779
struct InterferenceHelper::SnrPer CalculateHtPhyHeaderSnrPer(Ptr< Event > event) const
Calculate the SNIR at the start of the HT PHY header and accumulate all SNIR changes in the snir vect...
static WifiMode GetHeMcs10()
Return MCS 10 from HE MCS values.
Definition: wifi-phy.cc:3859
double GetValue(double min, double max)
Get the next random value, as a double in the specified range .
static WifiMode GetHtMcs20()
Return MCS 20 from HT MCS values.
Definition: wifi-phy.cc:3598
static WifiMode GetHeMcs2()
Return MCS 2 from HE MCS values.
Definition: wifi-phy.cc:3795
static WifiMode GetHtMcs5()
Return MCS 5 from HT MCS values.
Definition: wifi-phy.cc:3478
void SetMaxSupportedRxSpatialStreams(uint8_t streams)
Definition: wifi-phy.cc:1427
double CalculateSnr(Ptr< Event > event) const
Calculate the SNIR for the event (starting from now until the event end).
double m_ccaEdThresholdW
Clear channel assessment (CCA) threshold in watts.
Definition: wifi-phy.h:1957
static WifiMode GetVhtMcs2()
Return MCS 2 from VHT MCS values.
Definition: wifi-phy.cc:3713
virtual void SetChannelNumber(uint8_t id)
Set channel number.
Definition: wifi-phy.cc:1486
static WifiMode GetDsssRate5_5Mbps()
Return a WifiMode for DSSS at 5.5Mbps.
Definition: wifi-phy.cc:3015
void Configure80211ac(void)
Configure WifiPhy with appropriate channel frequency and supported rates for 802.11ac standard...
Definition: wifi-phy.cc:1104
virtual void DoInitialize(void)
Initialize() implementation.
Definition: wifi-phy.cc:435
static WifiMode GetOfdmRate2_25MbpsBW5MHz()
Return a WifiMode for OFDM at 2.25Mbps with 5MHz channel spacing.
Definition: wifi-phy.cc:3351
Ptr< const AttributeAccessor > MakeTimeAccessor(T1 a1)
Create an AttributeAccessor for a class data member, or a lone class get functor or set method...
Definition: nstime.h:1127
double WToDbm(double w)
Convert from Watts to dBm.
Definition: wifi-utils.cc:47
uint8_t GetChannelNumber(void) const
Return current channel number.
Definition: wifi-phy.cc:1540
WifiPhyStandard m_standard
WifiPhyStandard.
Definition: wifi-phy.h:1949
static Time Now(void)
Return the current simulation virtual time.
Definition: simulator.cc:193
void SetGuardInterval(Time guardInterval)
Definition: wifi-phy.cc:679
uint8_t FindChannelNumberForFrequencyWidth(uint16_t frequency, uint16_t width) const
Look for channel number matching the frequency and width.
Definition: wifi-phy.cc:1170
bool m_channelAccessRequested
Flag if channels access has been requested (used for OBSS_PD SR)
Definition: wifi-phy.h:1967
static WifiMode GetErpOfdmRate9Mbps()
Return a WifiMode for ERP-OFDM at 9Mbps.
Definition: wifi-phy.cc:3054
void EndReceive(Ptr< Event > event)
The last symbol of the PPDU has arrived.
Definition: wifi-phy.cc:2864
Ptr< UniformRandomVariable > m_random
Provides uniform random variables.
Definition: wifi-phy.h:1667
Ptr< Event > Add(Ptr< const WifiPpdu > ppdu, WifiTxVector txVector, Time duration, double rxPower)
Add the PPDU-related signal to interference helper.
struct InterferenceHelper::SnrPer CalculatePayloadSnrPer(Ptr< Event > event, std::pair< Time, Time > relativeMpduStartStop) const
Calculate the SNIR at the start of the payload and accumulate all SNIR changes in the snir vector for...
static Time GetPayloadDuration(uint32_t size, WifiTxVector txVector, uint16_t frequency, MpduType mpdutype=NORMAL_MPDU)
Definition: wifi-phy.cc:2120
double DbToRatio(double dB)
Convert from dB to ratio.
Definition: wifi-utils.cc:35
uint8_t m_txSpatialStreams
Number of supported TX spatial streams.
Definition: wifi-phy.h:1976
double GetTxPowerStart(void) const
Return the minimum available transmission power level (dBm).
Definition: wifi-phy.cc:559
double RatioToDb(double ratio)
Convert from ratio to dB.
Definition: wifi-utils.cc:53
Ptr< ErrorModel > m_postReceptionErrorModel
Error model for receive packet events.
Definition: wifi-phy.h:1995
void InitializeFrequencyChannelNumber(void)
post-construction setting of frequency and/or channel number
Definition: wifi-phy.cc:484
std::vector< uint16_t > GetSupportedChannelWidthSet(void) const
Definition: wifi-phy.cc:1472
uint8_t GetNModes(void) const
The WifiPhy::GetNModes() and WifiPhy::GetMode() methods are used (e.g., by a WifiRemoteStationManager...
Definition: wifi-phy.cc:3914
Ptr< FrameCaptureModel > m_frameCaptureModel
Frame capture model.
Definition: wifi-phy.h:1992
Ptr< const AttributeAccessor > MakeDoubleAccessor(T1 a1)
Create an AttributeAccessor for a class data member, or a lone class get functor or set method...
Definition: double.h:42
void SetRxGain(double gain)
Sets the reception gain (dB).
Definition: wifi-phy.cc:604
void Configure80211b(void)
Configure WifiPhy with appropriate channel frequency and supported rates for 802.11b standard...
Definition: wifi-phy.cc:923
No explicit coding (e.g., DSSS rates)
Definition: wifi-mode.h:75
void SetReceiveOkCallback(RxOkCallback callback)
Definition: wifi-phy.cc:454
WifiMode GetMode(uint8_t mode) const
The WifiPhy::GetNModes() and WifiPhy::GetMode() methods are used (e.g., by a WifiRemoteStationManager...
Definition: wifi-phy.cc:3920
uint16_t m_channelWidth
Channel width.
Definition: wifi-phy.h:1954
uint8_t GetBssMembershipSelector(uint8_t selector) const
The WifiPhy::BssMembershipSelector() method is used (e.g., by a WifiRemoteStationManager) to determin...
Definition: wifi-phy.cc:1451
static WifiMode GetErpOfdmRate6Mbps()
Return a WifiMode for ERP-OFDM at 6Mbps.
Definition: wifi-phy.cc:3042
void RegisterListener(WifiPhyListener *listener)
Definition: wifi-phy.cc:466
bool IsStateTx(void) const
Definition: wifi-phy.cc:3986
void ConfigureChannelForStandard(WifiPhyStandard standard)
Configure the PHY-level parameters for different Wi-Fi standard.
Definition: wifi-phy.cc:1198
void SetMaxSupportedTxSpatialStreams(uint8_t streams)
Definition: wifi-phy.cc:1408
The PHY layer is sending a packet.
static WifiMode GetErpOfdmRate12Mbps()
Return a WifiMode for ERP-OFDM at 12Mbps.
Definition: wifi-phy.cc:3066
bool m_greenfield
Flag if GreenField format is supported (deprecated)
Definition: wifi-phy.h:1969
WifiModulationClass
This enumeration defines the modulation classes per (Table 9-4 "Modulation classes"; IEEE 802...
Definition: wifi-mode.h:36
EventId m_endRxEvent
the end of receive event
Definition: wifi-phy.h:1673
Ptr< WifiPhyStateHelper > m_state
Pointer to WifiPhyStateHelper.
Definition: wifi-phy.h:1668
void SetEdThreshold(double threshold)
Sets the energy detection threshold (dBm).
Definition: wifi-phy.cc:512
void Configure80211n(void)
Configure WifiPhy with appropriate channel frequency and supported rates for 802.11n standard...
Definition: wifi-phy.cc:1087
void SetTxPowerStart(double start)
Sets the minimum available transmission power level (dBm).
Definition: wifi-phy.cc:552
double m_txPowerBaseDbm
Minimum transmission power (dBm)
Definition: wifi-phy.h:1960
bool IsMcsSupported(WifiMode mcs) const
Check if the given WifiMode is supported by the PHY.
Definition: wifi-phy.cc:3888
void NotifyRxEnd()
Notify that RX has ended.
void SetNoiseFigure(double value)
Set the noise figure.
#define NS_LOG_WARN(msg)
Use NS_LOG to output a message of level LOG_WARN.
Definition: log.h:265
SignalNoiseDbm structure.
Definition: wifi-phy.h:69
uint32_t mpduRefNumber
MPDU ref number.
Definition: wifi-phy.h:79
bool m_frequencyChannelNumberInitialized
Store initialization state.
Definition: wifi-phy.h:1953
static WifiMode GetHtMcs19()
Return MCS 19 from HT MCS values.
Definition: wifi-phy.cc:3590
InterferenceHelper m_interference
Pointer to InterferenceHelper.
Definition: wifi-phy.h:1666
static WifiMode GetHtMcs6()
Return MCS 6 from HT MCS values.
Definition: wifi-phy.cc:3486
bool m_isConstructed
true when ready to set frequency
Definition: wifi-phy.h:1950
void NotifyTxBegin(Ptr< const WifiPsdu > psdu, double txPowerW)
Public method used to fire a PhyTxBegin trace.
Definition: wifi-phy.cc:2420
The MPDU is the last aggregate in an A-MPDU with muliple MPDUs.
#define NS_LOG_DEBUG(msg)
Use NS_LOG to output a message of level LOG_DEBUG.
Definition: log.h:273
void ConfigureHtDeviceMcsSet(void)
Configure the device Mcs set with the appropriate HtMcs modes for the number of available transmit sp...
Definition: wifi-phy.cc:1017
void PushMcs(WifiMode mode)
Add the given MCS to the device MCS set.
Definition: wifi-phy.cc:992
Time Seconds(double value)
Construct a Time in the indicated unit.
Definition: nstime.h:1064
WifiPhyRxfailureReason
Enumeration of the possible reeception failure reasons.
Definition: wifi-phy.h:53
The PHY layer is receiving a packet.
OFDM PHY (Clause 17)
Definition: wifi-mode.h:56
static WifiMode GetVhtPlcpHeaderMode()
Definition: wifi-phy.cc:1779
static WifiMode GetHtMcs28()
Return MCS 28 from HT MCS values.
Definition: wifi-phy.cc:3662
bool IsRunning(void) const
This method is syntactic sugar for !IsExpired().
Definition: event-id.cc:65
double GetTxPowerEnd(void) const
Return the maximum available transmission power level (dBm).
Definition: wifi-phy.cc:572
static WifiMode GetHtMcs9()
Return MCS 9 from HT MCS values.
Definition: wifi-phy.cc:3510
void EndReceiveInterBss(void)
For HE receptions only, check and possibly modify the transmit power restriction state at the end of ...
Definition: wifi-phy.cc:2969
Attribute or trace source is deprecated; user is warned.
Definition: type-id.h:73
static WifiMode GetHtMcs4()
Return MCS 4 from HT MCS values.
Definition: wifi-phy.cc:3470
void Cancel(void)
This method is syntactic sugar for the ns3::Simulator::Cancel method.
Definition: event-id.cc:53
void StartReceivePayload(Ptr< Event > event)
Start receiving the PSDU (i.e.
Definition: wifi-phy.cc:2800
static WifiMode GetHtMcs25()
Return MCS 25 from HT MCS values.
Definition: wifi-phy.cc:3638
static WifiMode GetHeMcs8()
Return MCS 8 from HE MCS values.
Definition: wifi-phy.cc:3843
The PHY layer is switched off.
void Send(Ptr< const WifiPsdu > psdu, WifiTxVector txVector)
Definition: wifi-phy.cc:2536
void Configure80211g(void)
Configure WifiPhy with appropriate channel frequency and supported rates for 802.11g standard...
Definition: wifi-phy.cc:934
static WifiMode GetHePlcpHeaderMode()
Definition: wifi-phy.cc:1785
Ptr< NetDevice > GetDevice(void) const
Return the device this PHY is associated with.
Definition: wifi-phy.cc:742
uint8_t GetTxPowerLevel(void) const
void NotifyMonitorSniffTx(Ptr< const WifiPsdu > psdu, uint16_t channelFreqMhz, WifiTxVector txVector)
Public method used to fire a MonitorSniffer trace for a wifi PSDU being transmitted.
Definition: wifi-phy.cc:2505
double GetTxGain(void) const
Return the transmission gain (dB).
Definition: wifi-phy.cc:598
void StartReceiveHeader(Ptr< Event > event, Time headerPayloadDuration)
Start receiving the PHY header of a PPDU (i.e.
Definition: wifi-phy.cc:2619
The PHY layer is switching to other channel.
void SetSleepMode(void)
Put in sleep mode.
Definition: wifi-phy.cc:1666
Time MicroSeconds(uint64_t value)
Construct a Time in the indicated unit.
Definition: nstime.h:1080
WifiModeList m_deviceRateSet
This vector holds the set of transmission modes that this WifiPhy(-derived class) can support...
Definition: wifi-phy.h:1942
void SetNumberOfAntennas(uint8_t antennas)
Definition: wifi-phy.cc:1394
uint16_t GetChannelWidth(void) const
second
Definition: nstime.h:114
static WifiMode GetHtMcs1()
Return MCS 1 from HT MCS values.
Definition: wifi-phy.cc:3446
std::map< WifiModulationClass, std::map< uint8_t, uint8_t > > m_mcsIndexMap
Maps MCS values to indices in m_deviceMcsSet, for HT, VHT and HE modulation classes.
Definition: wifi-phy.h:1945
static WifiMode GetHtMcs23()
Return MCS 23 from HT MCS values.
Definition: wifi-phy.cc:3622
A base class which provides memory management and object aggregation.
Definition: object.h:87
Time FemtoSeconds(uint64_t value)
Construct a Time in the indicated unit.
Definition: nstime.h:1104
static WifiMode GetDsssRate2Mbps()
Return a WifiMode for DSSS at 2Mbps.
Definition: wifi-phy.cc:3000
static WifiMode GetVhtMcs9()
Return MCS 9 from VHT MCS values.
Definition: wifi-phy.cc:3769
#define HT_PHY
Definition: wifi-phy.h:37
virtual void ConfigureStandard(WifiPhyStandard standard)
Configure the PHY-level parameters for different Wi-Fi standard.
Definition: wifi-phy.cc:1248
static Time GetStartOfPacketDuration(WifiTxVector txVector)
Definition: wifi-phy.cc:2045
static WifiMode GetOfdmRate6MbpsBW10MHz()
Return a WifiMode for OFDM at 6Mbps with 10MHz channel spacing.
Definition: wifi-phy.cc:3264
int64_t GetFemtoSeconds(void) const
Get an approximation of the time stored in this instance in the indicated unit.
Definition: nstime.h:375
double m_txPowerEndDbm
Maximum transmission power (dBm)
Definition: wifi-phy.h:1961
#define VHT_PHY
Definition: wifi-phy.h:36
bool IsNull(void) const
Check for null implementation.
Definition: callback.h:1372
static WifiMode GetPlcpHeaderMode(WifiTxVector txVector)
Definition: wifi-phy.cc:1909
static Time GetPlcpTrainingSymbolDuration(WifiTxVector txVector)
Definition: wifi-phy.cc:1797
This class can be used to hold variables of floating point type such as &#39;double&#39; or &#39;float&#39;...
Definition: double.h:41
static WifiMode GetOfdmRate24MbpsBW10MHz()
Return a WifiMode for OFDM at 24Mbps with 10MHz channel spacing.
Definition: wifi-phy.cc:3312
The MPDU is a single MPDU.
MpduType type
type
Definition: wifi-phy.h:78
Time m_channelSwitchDelay
Time required to switch between channel.
Definition: wifi-phy.h:1986
static WifiMode GetOfdmRate13_5MbpsBW5MHz()
Return a WifiMode for OFDM at 13.5Mbps with 5MHz channel spacing.
Definition: wifi-phy.cc:3423
uint8_t GetMcsValue(void) const
Definition: wifi-mode.cc:472
Ptr< HtConfiguration > GetHtConfiguration(void) const
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
static WifiMode CreateWifiMcs(std::string uniqueName, uint8_t mcsValue, WifiModulationClass modClass)
Definition: wifi-mode.cc:726
uint8_t m_numberOfAntennas
Number of transmitters.
Definition: wifi-phy.h:1975
static Time GetPlcpHeaderDuration(WifiTxVector txVector)
Definition: wifi-phy.cc:1973
uint8_t GetMaxSupportedTxSpatialStreams(void) const
Definition: wifi-phy.cc:1421
a unique identifier for an interface.
Definition: type-id.h:58
static WifiMode GetHtMcs15()
Return MCS 15 from HT MCS values.
Definition: wifi-phy.cc:3558
Ptr< Event > m_currentEvent
Hold the current event.
Definition: wifi-phy.h:1991
TypeId SetParent(TypeId tid)
Set the parent TypeId.
Definition: type-id.cc:922
Time GetLastRxStartTime(void) const
Return the start time of the last received packet.
Definition: wifi-phy.cc:4016
double m_txPowerMaxSiso
SISO maximum transmit power due to OBSS PD SR power restriction.
Definition: wifi-phy.h:1965
bool IsStateRx(void) const
Definition: wifi-phy.cc:3980
static WifiMode GetHtMcs3()
Return MCS 3 from HT MCS values.
Definition: wifi-phy.cc:3462
uint8_t m_rxSpatialStreams
Number of supported RX spatial streams.
Definition: wifi-phy.h:1977
Ptr< T > Copy(Ptr< T > object)
Return a deep copy of a Ptr.
Definition: ptr.h:690
std::vector< uint16_t > m_supportedChannelWidthSet
Supported channel width.
Definition: wifi-phy.h:1982
static WifiMode GetOfdmRate6Mbps()
Return a WifiMode for OFDM at 6Mbps.
Definition: wifi-phy.cc:3141
void SwitchMaybeToCcaBusy(void)
Check if Phy state should move to CCA busy state based on current state of interference tracker...
Definition: wifi-phy.cc:4022
void SetCcaEdThreshold(double threshold)
Sets the CCA threshold (dBm).
Definition: wifi-phy.cc:531
bool m_shortGuardInterval
Flag if HT/VHT short guard interval is supported (deprecated)
Definition: wifi-phy.h:1970
HE PHY (Clause 26)
Definition: wifi-mode.h:62
uint64_t GetDataRate(uint16_t channelWidth, uint16_t guardInterval, uint8_t nss) const
Definition: wifi-mode.cc:150
virtual int64_t AssignStreams(int64_t stream)
Assign a fixed random variable stream number to the random variables used by this model...
Definition: wifi-phy.cc:4131
DSSS PHY (Clause 15)
Definition: wifi-mode.h:46
static WifiMode GetHeMcs6()
Return MCS 6 from HE MCS values.
Definition: wifi-phy.cc:3827
static WifiMode GetHtPlcpHeaderMode()
Definition: wifi-phy.cc:1773
void NotifyMonitorSniffRx(Ptr< const WifiPsdu > psdu, uint16_t channelFreqMhz, WifiTxVector txVector, SignalNoiseDbm signalNoise, std::vector< bool > statusPerMpdu)
Public method used to fire a MonitorSniffer trace for a wifi PSDU being received. ...
Definition: wifi-phy.cc:2474
static WifiMode GetOfdmRate4_5MbpsBW5MHz()
Return a WifiMode for OFDM at 4.5Mbps with 5MHz channel spacing.
Definition: wifi-phy.cc:3375
uint8_t GetNss(void) const
Callback< void > m_capabilitiesChangedCallback
Callback when PHY capabilities changed.
Definition: wifi-phy.h:1998
void Configure80211a(void)
Configure WifiPhy with appropriate channel frequency and supported rates for 802.11a standard...
Definition: wifi-phy.cc:908
uint8_t GetMaxSupportedRxSpatialStreams(void) const
Definition: wifi-phy.cc:1439
std::map< ChannelNumberStandardPair, FrequencyWidthPair > ChannelToFrequencyWidthMap
channel to frequency width map typedef
Definition: wifi-phy.h:1979
static WifiMode GetOfdmRate3MbpsBW10MHz()
Return a WifiMode for OFDM at 3Mbps with 10MHz channel spacing.
Definition: wifi-phy.cc:3240
TracedCallback< Ptr< const Packet > > m_phyTxEndTrace
The trace source fired when a packet ends the transmission process on the medium. ...
Definition: wifi-phy.h:1838
uint16_t m_initialFrequency
Store frequency until initialization.
Definition: wifi-phy.h:1952
Parameters for receive HE preamble.
Definition: wifi-phy.h:83
bool DoChannelSwitch(uint8_t id)
The default implementation does nothing and returns true.
Definition: wifi-phy.cc:1546
Time GetGuardInterval(void) const
Definition: wifi-phy.cc:696