A Discrete-Event Network Simulator
API
minstrel-wifi-manager.cc
Go to the documentation of this file.
1 /* -*- Mode:C++; c-file-style:"gnu"; indent-tabs-mode:nil; -*- */
2 /*
3  * Copyright (c) 2009 Duy Nguyen
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: Duy Nguyen <duy@soe.ucsc.edu>
19  * Matías Richart <mrichart@fing.edu.uy>
20  *
21  * Some Comments:
22  *
23  * 1) Segment Size is declared for completeness but not used because it has
24  * to do more with the requirement of the specific hardware.
25  *
26  * 2) By default, Minstrel applies the multi-rate retry (the core of Minstrel
27  * algorithm). Otherwise, please use ConstantRateWifiManager instead.
28  *
29  * http://linuxwireless.org/en/developers/Documentation/mac80211/RateControl/minstrel
30  */
31 
32 #include <iomanip>
33 #include "ns3/packet.h"
34 #include "ns3/random-variable-stream.h"
35 #include "ns3/simulator.h"
36 #include "ns3/log.h"
37 #include "minstrel-wifi-manager.h"
38 #include "ns3/wifi-mac.h"
39 #include "ns3/wifi-phy.h"
40 
41 #define Min(a,b) ((a < b) ? a : b)
42 
43 namespace ns3 {
44 
45 NS_LOG_COMPONENT_DEFINE ("MinstrelWifiManager");
46 
47 NS_OBJECT_ENSURE_REGISTERED (MinstrelWifiManager);
48 
49 TypeId
51 {
52  static TypeId tid = TypeId ("ns3::MinstrelWifiManager")
54  .SetGroupName ("Wifi")
55  .AddConstructor<MinstrelWifiManager> ()
56  .AddAttribute ("UpdateStatistics",
57  "The interval between updating statistics table ",
58  TimeValue (Seconds (0.1)),
60  MakeTimeChecker ())
61  .AddAttribute ("LookAroundRate",
62  "The percentage to try other rates",
63  UintegerValue (10),
65  MakeUintegerChecker<uint8_t> ())
66  .AddAttribute ("EWMA",
67  "EWMA level",
68  UintegerValue (75),
70  MakeUintegerChecker<uint8_t> ())
71  .AddAttribute ("SampleColumn",
72  "The number of columns used for sampling",
73  UintegerValue (10),
75  MakeUintegerChecker <uint8_t> ())
76  .AddAttribute ("PacketLength",
77  "The packet length used for calculating mode TxTime",
78  UintegerValue (1200),
80  MakeUintegerChecker <uint32_t> ())
81  .AddAttribute ("PrintStats",
82  "Print statistics table",
83  BooleanValue (false),
86  .AddAttribute ("PrintSamples",
87  "Print samples table",
88  BooleanValue (false),
91  .AddTraceSource ("Rate",
92  "Traced value for rate changes (b/s)",
94  "ns3::TracedValueCallback::Uint64")
95  ;
96  return tid;
97 }
98 
101  m_currentRate (0)
102 {
103  NS_LOG_FUNCTION (this);
104  m_uniformRandomVariable = CreateObject<UniformRandomVariable> ();
105 }
106 
108 {
109  NS_LOG_FUNCTION (this);
110 }
111 
112 void
114 {
115  NS_LOG_FUNCTION (this << phy);
116  for (const auto & mode : phy->GetModeList ())
117  {
118  WifiTxVector txVector;
119  txVector.SetMode (mode);
121  AddCalcTxTime (mode, phy->CalculateTxDuration (m_pktLen, txVector, phy->GetPhyBand ()));
122  }
124 }
125 
126 void
128 {
129  NS_LOG_FUNCTION (this << mac);
131 }
132 
133 void
135 {
136  NS_LOG_FUNCTION (this);
137  if (GetHtSupported ())
138  {
139  NS_FATAL_ERROR ("WifiRemoteStationManager selected does not support HT rates");
140  }
141  if (GetVhtSupported ())
142  {
143  NS_FATAL_ERROR ("WifiRemoteStationManager selected does not support VHT rates");
144  }
145  if (GetHeSupported ())
146  {
147  NS_FATAL_ERROR ("WifiRemoteStationManager selected does not support HE rates");
148  }
149 }
150 
151 int64_t
153 {
154  NS_LOG_FUNCTION (this << stream);
156  return 1;
157 }
158 
159 Time
161 {
162  NS_LOG_FUNCTION (this << mode);
163  auto it = m_calcTxTime.find (mode);
164  NS_ASSERT (it != m_calcTxTime.end ());
165  return it->second;
166 }
167 
168 void
170 {
171  NS_LOG_FUNCTION (this << mode << t);
172  m_calcTxTime.insert (std::make_pair (mode, t));
173 }
174 
177 {
178  NS_LOG_FUNCTION (this);
180 
182  station->m_col = 0;
183  station->m_index = 0;
184  station->m_maxTpRate = 0;
185  station->m_maxTpRate2 = 0;
186  station->m_maxProbRate = 0;
187  station->m_nModes = 0;
188  station->m_totalPacketsCount = 0;
189  station->m_samplePacketsCount = 0;
190  station->m_isSampling = false;
191  station->m_sampleRate = 0;
192  station->m_sampleDeferred = false;
193  station->m_shortRetry = 0;
194  station->m_longRetry = 0;
195  station->m_retry = 0;
196  station->m_txrate = 0;
197  station->m_initialized = false;
198 
199  return station;
200 }
201 
202 void
204 {
205  NS_LOG_FUNCTION (this << station);
206  if (!station->m_initialized && GetNSupported (station) > 1)
207  {
208  //Note: we appear to be doing late initialization of the table
209  //to make sure that the set of supported rates has been initialized
210  //before we perform our own initialization.
211  station->m_nModes = GetNSupported (station);
212  station->m_minstrelTable = MinstrelRate (station->m_nModes);
213  station->m_sampleTable = SampleRate (station->m_nModes, std::vector<uint8_t> (m_sampleCol));
214  InitSampleTable (station);
215  RateInit (station);
216  station->m_initialized = true;
217  }
218 }
219 
235 void
237 {
238  NS_LOG_FUNCTION (this << station);
239  station->m_longRetry++;
240  station->m_minstrelTable[station->m_txrate].numRateAttempt++;
241 
242  NS_LOG_DEBUG ("DoReportDataFailed " << station << " rate " << station->m_txrate << " longRetry " << station->m_longRetry);
243 
244  //for normal rate, we're not currently sampling random rates
245  if (!station->m_isSampling)
246  {
247  NS_LOG_DEBUG ("Failed with normal rate: current=" << station->m_txrate << ", sample=" << station->m_sampleRate << ", maxTp=" << station->m_maxTpRate << ", maxTp2=" << station->m_maxTpRate2 << ", maxProb=" << station->m_maxProbRate);
248  //use best throughput rate
249  if (station->m_longRetry < station->m_minstrelTable[station->m_maxTpRate].adjustedRetryCount)
250  {
251  NS_LOG_DEBUG (" More retries left for the maximum throughput rate.");
252  station->m_txrate = station->m_maxTpRate;
253  }
254 
255  //use second best throughput rate
256  else if (station->m_longRetry <= (station->m_minstrelTable[station->m_maxTpRate].adjustedRetryCount +
257  station->m_minstrelTable[station->m_maxTpRate2].adjustedRetryCount))
258  {
259  NS_LOG_DEBUG (" More retries left for the second maximum throughput rate.");
260  station->m_txrate = station->m_maxTpRate2;
261  }
262 
263  //use best probability rate
264  else if (station->m_longRetry <= (station->m_minstrelTable[station->m_maxTpRate].adjustedRetryCount +
265  station->m_minstrelTable[station->m_maxTpRate2].adjustedRetryCount +
266  station->m_minstrelTable[station->m_maxProbRate].adjustedRetryCount))
267  {
268  NS_LOG_DEBUG (" More retries left for the maximum probability rate.");
269  station->m_txrate = station->m_maxProbRate;
270  }
271 
272  //use lowest base rate
273  else if (station->m_longRetry > (station->m_minstrelTable[station->m_maxTpRate].adjustedRetryCount +
274  station->m_minstrelTable[station->m_maxTpRate2].adjustedRetryCount +
275  station->m_minstrelTable[station->m_maxProbRate].adjustedRetryCount))
276  {
277  NS_LOG_DEBUG (" More retries left for the base rate.");
278  station->m_txrate = 0;
279  }
280  }
281 
282  //for look-around rate, we're currently sampling random rates
283  else
284  {
285  NS_LOG_DEBUG ("Failed with look around rate: current=" << station->m_txrate << ", sample=" << station->m_sampleRate << ", maxTp=" << station->m_maxTpRate << ", maxTp2=" << station->m_maxTpRate2 << ", maxProb=" << station->m_maxProbRate);
286  //current sampling rate is slower than the current best rate
287  if (station->m_sampleDeferred)
288  {
289  NS_LOG_DEBUG ("Look around rate is slower than the maximum throughput rate.");
290  //use best throughput rate
291  if (station->m_longRetry < station->m_minstrelTable[station->m_maxTpRate].adjustedRetryCount)
292  {
293  NS_LOG_DEBUG (" More retries left for the maximum throughput rate.");
294  station->m_txrate = station->m_maxTpRate;
295  }
296 
297  //use random rate
298  else if (station->m_longRetry <= (station->m_minstrelTable[station->m_maxTpRate].adjustedRetryCount +
299  station->m_minstrelTable[station->m_sampleRate].adjustedRetryCount))
300  {
301  NS_LOG_DEBUG (" More retries left for the sampling rate.");
302  station->m_txrate = station->m_sampleRate;
303  }
304 
305  //use max probability rate
306  else if (station->m_longRetry <= (station->m_minstrelTable[station->m_maxTpRate].adjustedRetryCount +
307  station->m_minstrelTable[station->m_sampleRate].adjustedRetryCount +
308  station->m_minstrelTable[station->m_maxProbRate].adjustedRetryCount ))
309  {
310  NS_LOG_DEBUG (" More retries left for the maximum probability rate.");
311  station->m_txrate = station->m_maxProbRate;
312  }
313 
314  //use lowest base rate
315  else if (station->m_longRetry > (station->m_minstrelTable[station->m_maxTpRate].adjustedRetryCount +
316  station->m_minstrelTable[station->m_sampleRate].adjustedRetryCount +
317  station->m_minstrelTable[station->m_maxProbRate].adjustedRetryCount))
318  {
319  NS_LOG_DEBUG (" More retries left for the base rate.");
320  station->m_txrate = 0;
321  }
322  }
323  //current sampling rate is better than current best rate
324  else
325  {
326  NS_LOG_DEBUG ("Look around rate is faster than the maximum throughput rate.");
327  //use random rate
328  if (station->m_longRetry < station->m_minstrelTable[station->m_sampleRate].adjustedRetryCount)
329  {
330  NS_LOG_DEBUG (" More retries left for the sampling rate.");
331  station->m_txrate = station->m_sampleRate;
332  }
333 
334  //use the best throughput rate
335  else if (station->m_longRetry <= (station->m_minstrelTable[station->m_sampleRate].adjustedRetryCount +
336  station->m_minstrelTable[station->m_maxTpRate].adjustedRetryCount))
337  {
338  NS_LOG_DEBUG (" More retries left for the maximum throughput rate.");
339  station->m_txrate = station->m_maxTpRate;
340  }
341 
342  //use the best probability rate
343  else if (station->m_longRetry <= (station->m_minstrelTable[station->m_sampleRate].adjustedRetryCount +
344  station->m_minstrelTable[station->m_maxTpRate].adjustedRetryCount +
345  station->m_minstrelTable[station->m_maxProbRate].adjustedRetryCount))
346  {
347  NS_LOG_DEBUG (" More retries left for the maximum probability rate.");
348  station->m_txrate = station->m_maxProbRate;
349  }
350 
351  //use the lowest base rate
352  else if (station->m_longRetry > (station->m_minstrelTable[station->m_sampleRate].adjustedRetryCount +
353  station->m_minstrelTable[station->m_maxTpRate].adjustedRetryCount +
354  station->m_minstrelTable[station->m_maxProbRate].adjustedRetryCount))
355  {
356  NS_LOG_DEBUG (" More retries left for the base rate.");
357  station->m_txrate = 0;
358  }
359  }
360  }
361 }
362 
365 {
366  NS_LOG_FUNCTION (this << station);
367  uint16_t channelWidth = GetChannelWidth (station);
368  if (channelWidth > 20 && channelWidth != 22)
369  {
370  channelWidth = 20;
371  }
372  if (!station->m_initialized)
373  {
374  CheckInit (station);
375  }
376  WifiMode mode = GetSupported (station, station->m_txrate);
377  uint64_t rate = mode.GetDataRate (channelWidth);
378  if (m_currentRate != rate && !station->m_isSampling)
379  {
380  NS_LOG_DEBUG ("New datarate: " << rate);
381  m_currentRate = rate;
382  }
383  return WifiTxVector (mode, GetDefaultTxPowerLevel (), GetPreambleForTransmission (mode.GetModulationClass (), GetShortPreambleEnabled ()), 800, 1, 1, 0, channelWidth, GetAggregation (station));
384 }
385 
388 {
389  NS_LOG_FUNCTION (this << station);
390  NS_LOG_DEBUG ("DoGetRtsMode m_txrate=" << station->m_txrate);
391  uint16_t channelWidth = GetChannelWidth (station);
392  if (channelWidth > 20 && channelWidth != 22)
393  {
394  channelWidth = 20;
395  }
396  WifiMode mode;
397  if (GetUseNonErpProtection () == false)
398  {
399  mode = GetSupported (station, 0);
400  }
401  else
402  {
403  mode = GetNonErpSupported (station, 0);
404  }
405  return WifiTxVector (mode, GetDefaultTxPowerLevel (), GetPreambleForTransmission (mode.GetModulationClass (), GetShortPreambleEnabled ()), 800, 1, 1, 0, channelWidth, GetAggregation (station));
406 }
407 
408 uint32_t
410 {
411  if (!station->m_isSampling)
412  {
413  return station->m_minstrelTable[station->m_maxTpRate].adjustedRetryCount +
414  station->m_minstrelTable[station->m_maxTpRate2].adjustedRetryCount +
415  station->m_minstrelTable[station->m_maxProbRate].adjustedRetryCount +
416  station->m_minstrelTable[0].adjustedRetryCount;
417  }
418  else
419  {
420  return station->m_minstrelTable[station->m_sampleRate].adjustedRetryCount +
421  station->m_minstrelTable[station->m_maxTpRate].adjustedRetryCount +
422  station->m_minstrelTable[station->m_maxProbRate].adjustedRetryCount +
423  station->m_minstrelTable[0].adjustedRetryCount;
424  }
425 }
426 
427 uint16_t
429 {
430  NS_LOG_FUNCTION (this << station);
431 
432  if (station->m_totalPacketsCount == 0)
433  {
434  return 0;
435  }
436 
437  uint16_t idx = 0;
438  NS_LOG_DEBUG ("Total: " << station->m_totalPacketsCount << " Sample: " << station->m_samplePacketsCount << " Deferred: " << station->m_numSamplesDeferred);
439 
440  int delta = (station->m_totalPacketsCount * m_lookAroundRate / 100) - (station->m_samplePacketsCount + station->m_numSamplesDeferred / 2);
441 
442  NS_LOG_DEBUG ("Decide sampling. Delta: " << delta << " lookAroundRatio: " << m_lookAroundRate);
443 
444  /* delta < 0: no sampling required */
445  if (delta >= 0)
446  {
447  NS_LOG_DEBUG ("Search next sampling rate");
448  uint8_t ratesSupported = station->m_nModes;
449  if (delta > ratesSupported * 2)
450  {
451  /* From Linux implementation:
452  * With multi-rate retry, not every planned sample
453  * attempt actually gets used, due to the way the retry
454  * chain is set up - [max_tp,sample,prob,lowest] for
455  * sample_rate < max_tp.
456  *
457  * If there's too much sampling backlog and the link
458  * starts getting worse, minstrel would start bursting
459  * out lots of sampling frames, which would result
460  * in a large throughput loss. */
461  station->m_samplePacketsCount += (delta - ratesSupported * 2);
462  }
463 
464  //now go through the table and find an index rate
465  idx = GetNextSample (station);
466 
467  NS_LOG_DEBUG ("Sample rate = " << idx << "(" << GetSupported (station, idx) << ")");
468 
469  //error check
470  if (idx >= station->m_nModes)
471  {
472  NS_LOG_DEBUG ("ALERT!!! ERROR");
473  }
474 
475  //set the rate that we're currently sampling
476  station->m_sampleRate = idx;
477 
478  /* From Linux implementation:
479  * Decide if direct ( 1st MRR stage) or indirect (2nd MRR stage)
480  * rate sampling method should be used.
481  * Respect such rates that are not sampled for 20 iterations.
482  */
483  if ((station->m_minstrelTable[idx].perfectTxTime > station->m_minstrelTable[station->m_maxTpRate].perfectTxTime)
484  && (station->m_minstrelTable[idx].numSamplesSkipped < 20))
485  {
486  // If the rate is slower and we have sample it enough, defer to second stage
487  station->m_sampleDeferred = true;
488  station->m_numSamplesDeferred++;
489 
490  //set flag that we are currently sampling
491  station->m_isSampling = true;
492  }
493  else
494  {
495  // if samplieLimit is zero, then don't sample this rate
496  if (!station->m_minstrelTable[idx].sampleLimit)
497  {
498  idx = station->m_maxTpRate;
499  station->m_isSampling = false;
500  }
501  else
502  {
503  //set flag that we are currently sampling
504  station->m_isSampling = true;
505  if (station->m_minstrelTable[idx].sampleLimit > 0)
506  {
507  station->m_minstrelTable[idx].sampleLimit--;
508  }
509  }
510  }
511 
512  //using the best rate instead
513  if (station->m_sampleDeferred)
514  {
515  NS_LOG_DEBUG ("The next look around rate is slower than the maximum throughput rate, continue with the maximum throughput rate: " << station->m_maxTpRate << "(" << GetSupported (station, station->m_maxTpRate) << ")");
516  idx = station->m_maxTpRate;
517  }
518  }
519  //continue using the best rate
520  else
521  {
522  NS_LOG_DEBUG ("Continue using the maximum throughput rate: " << station->m_maxTpRate << "(" << GetSupported (station, station->m_maxTpRate) << ")");
523  idx = station->m_maxTpRate;
524  }
525 
526  NS_LOG_DEBUG ("Rate = " << idx << "(" << GetSupported (station, idx) << ")");
527 
528  return idx;
529 }
530 
531 void
533 {
534  NS_LOG_FUNCTION (this << station);
535  if (Simulator::Now () < station->m_nextStatsUpdate)
536  {
537  return;
538  }
539 
540  if (!station->m_initialized)
541  {
542  return;
543  }
544  NS_LOG_FUNCTION (this);
546  NS_LOG_DEBUG ("Next update at " << station->m_nextStatsUpdate);
547  NS_LOG_DEBUG ("Currently using rate: " << station->m_txrate << " (" << GetSupported (station, station->m_txrate) << ")");
548 
549  Time txTime;
550  uint32_t tempProb;
551 
552  NS_LOG_DEBUG ("Index-Rate\t\tAttempt\tSuccess");
553  for (uint8_t i = 0; i < station->m_nModes; i++)
554  {
555 
556  //calculate the perfect TX time for this rate
557  txTime = station->m_minstrelTable[i].perfectTxTime;
558 
559  //just for initialization
560  if (txTime.GetMicroSeconds () == 0)
561  {
562  txTime = Seconds (1);
563  }
564 
565  NS_LOG_DEBUG (+i << " " << GetSupported (station, i) <<
566  "\t" << station->m_minstrelTable[i].numRateAttempt <<
567  "\t" << station->m_minstrelTable[i].numRateSuccess);
568 
569  //if we've attempted something
570  if (station->m_minstrelTable[i].numRateAttempt)
571  {
572  station->m_minstrelTable[i].numSamplesSkipped = 0;
577  tempProb = (station->m_minstrelTable[i].numRateSuccess * 18000) / station->m_minstrelTable[i].numRateAttempt;
578 
579  //bookkeeping
580  station->m_minstrelTable[i].prob = tempProb;
581 
582  if (station->m_minstrelTable[i].successHist == 0)
583  {
584  station->m_minstrelTable[i].ewmaProb = tempProb;
585  }
586  else
587  {
588  //EWMA probability (cast for gcc 3.4 compatibility)
589  tempProb = ((tempProb * (100 - m_ewmaLevel)) + (station->m_minstrelTable[i].ewmaProb * m_ewmaLevel) ) / 100;
590 
591  station->m_minstrelTable[i].ewmaProb = tempProb;
592  }
593 
594  //calculating throughput
595  station->m_minstrelTable[i].throughput = tempProb * static_cast<uint32_t> ((1000000 / txTime.GetMicroSeconds ()));
596  }
597  else
598  {
599  station->m_minstrelTable[i].numSamplesSkipped++;
600  }
601 
602  //bookkeeping
603  station->m_minstrelTable[i].successHist += station->m_minstrelTable[i].numRateSuccess;
604  station->m_minstrelTable[i].attemptHist += station->m_minstrelTable[i].numRateAttempt;
605  station->m_minstrelTable[i].prevNumRateSuccess = station->m_minstrelTable[i].numRateSuccess;
606  station->m_minstrelTable[i].prevNumRateAttempt = station->m_minstrelTable[i].numRateAttempt;
607  station->m_minstrelTable[i].numRateSuccess = 0;
608  station->m_minstrelTable[i].numRateAttempt = 0;
609 
610  //Sample less often below 10% and above 95% of success
611  if ((station->m_minstrelTable[i].ewmaProb > 17100) || (station->m_minstrelTable[i].ewmaProb < 1800))
612  {
620  if (station->m_minstrelTable[i].retryCount > 2)
621  {
622  station->m_minstrelTable[i].adjustedRetryCount = 2;
623  }
624  station->m_minstrelTable[i].sampleLimit = 4;
625  }
626  else
627  {
628  // no sampling limit.
629  station->m_minstrelTable[i].sampleLimit = -1;
630  station->m_minstrelTable[i].adjustedRetryCount = station->m_minstrelTable[i].retryCount;
631  }
632 
633  //if it's 0 allow two retries.
634  if (station->m_minstrelTable[i].adjustedRetryCount == 0)
635  {
636  station->m_minstrelTable[i].adjustedRetryCount = 2;
637  }
638  }
639 
640  NS_LOG_DEBUG ("Attempt/success reset to 0");
641 
642  uint32_t max_tp = 0;
643  uint8_t index_max_tp = 0, index_max_tp2 = 0;
644 
645  //go find max throughput, second maximum throughput, high probability of success
646  NS_LOG_DEBUG ("Finding the maximum throughput, second maximum throughput, and highest probability");
647  NS_LOG_DEBUG ("Index-Rate\t\tT-put\tEWMA");
648  for (uint8_t i = 0; i < station->m_nModes; i++)
649  {
650  NS_LOG_DEBUG (+i << " " << GetSupported (station, i) <<
651  "\t" << station->m_minstrelTable[i].throughput <<
652  "\t" << station->m_minstrelTable[i].ewmaProb);
653 
654  if (max_tp < station->m_minstrelTable[i].throughput)
655  {
656  index_max_tp = i;
657  max_tp = station->m_minstrelTable[i].throughput;
658  }
659  }
660 
661  max_tp = 0;
662  //find the second highest max
663  for (uint8_t i = 0; i < station->m_nModes; i++)
664  {
665  if ((i != index_max_tp) && (max_tp < station->m_minstrelTable[i].throughput))
666  {
667  index_max_tp2 = i;
668  max_tp = station->m_minstrelTable[i].throughput;
669  }
670  }
671 
672  uint32_t max_prob = 0;
673  uint8_t index_max_prob = 0;
674  for (uint8_t i = 0; i < station->m_nModes; i++)
675  {
676  if ((station->m_minstrelTable[i].ewmaProb >= 95 * 180) && (station->m_minstrelTable[i].throughput >= station->m_minstrelTable[index_max_prob].throughput))
677  {
678  index_max_prob = i;
679  max_prob = station->m_minstrelTable[i].ewmaProb;
680  }
681  else if (station->m_minstrelTable[i].ewmaProb >= max_prob)
682  {
683  index_max_prob = i;
684  max_prob = station->m_minstrelTable[i].ewmaProb;
685  }
686  }
687 
688  station->m_maxTpRate = index_max_tp;
689  station->m_maxTpRate2 = index_max_tp2;
690  station->m_maxProbRate = index_max_prob;
691 
692  if (index_max_tp > station->m_txrate)
693  {
694  station->m_txrate = index_max_tp;
695  }
696 
697  NS_LOG_DEBUG ("max throughput=" << +index_max_tp << "(" << GetSupported (station, index_max_tp) <<
698  ")\tsecond max throughput=" << +index_max_tp2 << "(" << GetSupported (station, index_max_tp2) <<
699  ")\tmax prob=" << +index_max_prob << "(" << GetSupported (station, index_max_prob) << ")");
700  if (m_printStats)
701  {
702  PrintTable (station);
703  }
704  if (m_printSamples)
705  {
706  PrintSampleTable (station);
707  }
708 }
709 
710 void
712 {
713  NS_LOG_FUNCTION (this << st << rxSnr << txMode);
714  NS_LOG_DEBUG ("DoReportRxOk m_txrate=" << static_cast<MinstrelWifiRemoteStation*> (st)->m_txrate);
715 }
716 
717 void
719 {
720  NS_LOG_FUNCTION (this << st);
721  MinstrelWifiRemoteStation *station = static_cast<MinstrelWifiRemoteStation*> (st);
722  NS_LOG_DEBUG ("DoReportRtsFailed m_txrate=" << station->m_txrate);
723  station->m_shortRetry++;
724 }
725 
726 void
727 MinstrelWifiManager::DoReportRtsOk (WifiRemoteStation *st, double ctsSnr, WifiMode ctsMode, double rtsSnr)
728 {
729  NS_LOG_FUNCTION (this << st << ctsSnr << ctsMode << rtsSnr);
730 }
731 
732 void
734 {
735  NS_LOG_FUNCTION (this << st);
736  MinstrelWifiRemoteStation *station = static_cast<MinstrelWifiRemoteStation*> (st);
737  UpdateRetry (station);
738 }
739 
740 void
742 {
743  NS_LOG_FUNCTION (this << st);
744  MinstrelWifiRemoteStation *station = static_cast<MinstrelWifiRemoteStation*> (st);
745  NS_LOG_DEBUG ("DoReportDataFailed " << station << "\t rate " << station->m_txrate << "\tlongRetry \t" << station->m_longRetry);
746  CheckInit (station);
747  if (!station->m_initialized)
748  {
749  return;
750  }
751 
752  UpdateRate (station);
753 }
754 
755 void
757  double dataSnr, uint16_t dataChannelWidth, uint8_t dataNss)
758 {
759  NS_LOG_FUNCTION (this << st << ackSnr << ackMode << dataSnr << dataChannelWidth << +dataNss);
760  MinstrelWifiRemoteStation *station = static_cast<MinstrelWifiRemoteStation*> (st);
761 
762  CheckInit (station);
763  if (!station->m_initialized)
764  {
765  return;
766  }
767 
768  NS_LOG_DEBUG ("DoReportDataOk m_txrate = " << station->m_txrate << ", attempt = " << station->m_minstrelTable[station->m_txrate].numRateAttempt << ", success = " << station->m_minstrelTable[station->m_txrate].numRateSuccess << " (before update).");
769 
770  station->m_minstrelTable[station->m_txrate].numRateSuccess++;
771  station->m_minstrelTable[station->m_txrate].numRateAttempt++;
772 
773  UpdatePacketCounters (station);
774 
775  NS_LOG_DEBUG ("DoReportDataOk m_txrate = " << station->m_txrate << ", attempt = " << station->m_minstrelTable[station->m_txrate].numRateAttempt << ", success = " << station->m_minstrelTable[station->m_txrate].numRateSuccess << " (after update).");
776 
777  UpdateRetry (station);
778  UpdateStats (station);
779 
780  if (station->m_nModes >= 1)
781  {
782  station->m_txrate = FindRate (station);
783  }
784  NS_LOG_DEBUG ("Next rate to use TxRate = " << station->m_txrate);
785 }
786 
787 void
789 {
790  NS_LOG_FUNCTION (this << st);
791  MinstrelWifiRemoteStation *station = static_cast<MinstrelWifiRemoteStation*> (st);
792 
793  CheckInit (station);
794  if (!station->m_initialized)
795  {
796  return;
797  }
798 
799  NS_LOG_DEBUG ("DoReportFinalDataFailed m_txrate = " << station->m_txrate << ", attempt = " << station->m_minstrelTable[station->m_txrate].numRateAttempt << ", success = " << station->m_minstrelTable[station->m_txrate].numRateSuccess << " (before update).");
800 
801  UpdatePacketCounters (station);
802 
803  UpdateRetry (station);
804  UpdateStats (station);
805 
806  NS_LOG_DEBUG ("DoReportFinalDataFailed m_txrate = " << station->m_txrate << ", attempt = " << station->m_minstrelTable[station->m_txrate].numRateAttempt << ", success = " << station->m_minstrelTable[station->m_txrate].numRateSuccess << " (after update).");
807 
808  if (station->m_nModes >= 1)
809  {
810  station->m_txrate = FindRate (station);
811  }
812  NS_LOG_DEBUG ("Next rate to use TxRate = " << station->m_txrate);
813 }
814 
815 void
817 {
818  NS_LOG_FUNCTION (this << station);
819 
820  station->m_totalPacketsCount++;
821  // If it is a sampling frame and the sampleRate was used, increase counter
822  if (station->m_isSampling && (!station->m_sampleDeferred || station->m_longRetry >= station->m_minstrelTable[station->m_maxTpRate].adjustedRetryCount))
823  {
824  station->m_samplePacketsCount++;
825  }
826 
827  if (station->m_numSamplesDeferred > 0)
828  {
829  station->m_numSamplesDeferred--;
830  }
831 
832  if (station->m_totalPacketsCount == ~0)
833  {
834  station->m_numSamplesDeferred = 0;
835  station->m_samplePacketsCount = 0;
836  station->m_totalPacketsCount = 0;
837  }
838  station->m_isSampling = false;
839  station->m_sampleDeferred = false;
840 }
841 
842 void
844 {
845  NS_LOG_FUNCTION (this << station);
846  station->m_retry = station->m_shortRetry + station->m_longRetry;
847  station->m_shortRetry = 0;
848  station->m_longRetry = 0;
849 }
850 
853 {
854  NS_LOG_FUNCTION (this << st);
855  MinstrelWifiRemoteStation *station = static_cast<MinstrelWifiRemoteStation*> (st);
856  return GetDataTxVector (station);
857 }
858 
861 {
862  NS_LOG_FUNCTION (this << st);
863  MinstrelWifiRemoteStation *station = static_cast<MinstrelWifiRemoteStation*> (st);
864  return GetRtsTxVector (station);
865 }
866 
867 bool
869 {
870  NS_LOG_FUNCTION (this << st << packet << normally);
871  MinstrelWifiRemoteStation *station = static_cast<MinstrelWifiRemoteStation*> (st);
872 
873  CheckInit (station);
874  if (!station->m_initialized)
875  {
876  return normally;
877  }
878  if (station->m_longRetry >= CountRetries (station))
879  {
880  NS_LOG_DEBUG ("No re-transmission allowed. Retries: " << station->m_longRetry << " Max retries: " << CountRetries (station));
881  return false;
882  }
883  else
884  {
885  NS_LOG_DEBUG ("Re-transmit. Retries: " << station->m_longRetry << " Max retries: " << CountRetries (station));
886  return true;
887  }
888 }
889 
890 uint16_t
892 {
893  NS_LOG_FUNCTION (this << station);
894  uint16_t bitrate;
895  bitrate = station->m_sampleTable[station->m_index][station->m_col];
896  station->m_index++;
897 
898  //bookkeeping for m_index and m_col variables
899  NS_ABORT_MSG_IF (station->m_nModes < 2, "Integer overflow detected");
900  if (station->m_index > station->m_nModes - 2)
901  {
902  station->m_index = 0;
903  station->m_col++;
904  if (station->m_col >= m_sampleCol)
905  {
906  station->m_col = 0;
907  }
908  }
909  return bitrate;
910 }
911 
912 void
914 {
915  NS_LOG_FUNCTION (this << station);
916  for (uint8_t i = 0; i < station->m_nModes; i++)
917  {
918  NS_LOG_DEBUG ("Initializing rate index " << +i << " " << GetSupported (station, i));
919  station->m_minstrelTable[i].numRateAttempt = 0;
920  station->m_minstrelTable[i].numRateSuccess = 0;
921  station->m_minstrelTable[i].prevNumRateSuccess = 0;
922  station->m_minstrelTable[i].prevNumRateAttempt = 0;
923  station->m_minstrelTable[i].successHist = 0;
924  station->m_minstrelTable[i].attemptHist = 0;
925  station->m_minstrelTable[i].numSamplesSkipped = 0;
926  station->m_minstrelTable[i].prob = 0;
927  station->m_minstrelTable[i].ewmaProb = 0;
928  station->m_minstrelTable[i].throughput = 0;
929  station->m_minstrelTable[i].perfectTxTime = GetCalcTxTime (GetSupported (station, i));
930  NS_LOG_DEBUG (" perfectTxTime = " << station->m_minstrelTable[i].perfectTxTime);
931  station->m_minstrelTable[i].retryCount = 1;
932  station->m_minstrelTable[i].adjustedRetryCount = 1;
933  //Emulating minstrel.c::ath_rate_ctl_reset
934  //We only check from 2 to 10 retries. This guarantee that
935  //at least one retry is permitted.
936  Time totalTxTimeWithGivenRetries = Seconds (0.0); //tx_time in minstrel.c
937  NS_LOG_DEBUG (" Calculating the number of retries");
938  for (uint32_t retries = 2; retries < 11; retries++)
939  {
940  NS_LOG_DEBUG (" Checking " << retries << " retries");
941  totalTxTimeWithGivenRetries = CalculateTimeUnicastPacket (station->m_minstrelTable[i].perfectTxTime, 0, retries);
942  NS_LOG_DEBUG (" totalTxTimeWithGivenRetries = " << totalTxTimeWithGivenRetries);
943  if (totalTxTimeWithGivenRetries > MilliSeconds (6))
944  {
945  break;
946  }
947  station->m_minstrelTable[i].sampleLimit = -1;
948  station->m_minstrelTable[i].retryCount = retries;
949  station->m_minstrelTable[i].adjustedRetryCount = retries;
950  }
951  }
952  UpdateStats (station);
953 }
954 
955 Time
956 MinstrelWifiManager::CalculateTimeUnicastPacket (Time dataTransmissionTime, uint32_t shortRetries, uint32_t longRetries)
957 {
958  NS_LOG_FUNCTION (this << dataTransmissionTime << shortRetries << longRetries);
959  //See rc80211_minstrel.c
960 
961  //First transmission (Data + Ack timeout)
962  Time tt = dataTransmissionTime + GetPhy ()->GetSifs () + GetPhy ()->GetAckTxTime ();
963 
964  uint32_t cwMax = 1023;
965  uint32_t cw = 31;
966  for (uint32_t retry = 0; retry < longRetries; retry++)
967  {
968  //Add one re-transmission (Data + Ack timeout)
969  tt += dataTransmissionTime + GetPhy ()->GetSifs () + GetPhy ()->GetAckTxTime ();
970 
971  //Add average back off (half the current contention window)
972  tt += (cw / 2.0) * GetPhy ()->GetSlot ();
973 
974  //Update contention window
975  cw = std::min (cwMax, (cw + 1) * 2);
976  }
977 
978  return tt;
979 }
980 
981 void
983 {
984  NS_LOG_FUNCTION (this << station);
985  station->m_col = station->m_index = 0;
986 
987  //for off-setting to make rates fall between 0 and nModes
988  uint8_t numSampleRates = station->m_nModes;
989 
990  uint16_t newIndex;
991  for (uint8_t col = 0; col < m_sampleCol; col++)
992  {
993  for (uint8_t i = 0; i < numSampleRates; i++ )
994  {
999  int uv = m_uniformRandomVariable->GetInteger (0, numSampleRates);
1000  NS_LOG_DEBUG ("InitSampleTable uv: " << uv);
1001  newIndex = (i + uv) % numSampleRates;
1002 
1003  //this loop is used for filling in other uninitialized places
1004  while (station->m_sampleTable[newIndex][col] != 0)
1005  {
1006  newIndex = (newIndex + 1) % station->m_nModes;
1007  }
1008  station->m_sampleTable[newIndex][col] = i;
1009  }
1010  }
1011 }
1012 
1013 void
1015 {
1016  uint8_t numSampleRates = station->m_nModes;
1017  std::stringstream table;
1018  for (uint8_t i = 0; i < numSampleRates; i++)
1019  {
1020  for (uint8_t j = 0; j < m_sampleCol; j++)
1021  {
1022  table << station->m_sampleTable[i][j] << "\t";
1023  }
1024  table << std::endl;
1025  }
1026  NS_LOG_DEBUG (table.str ());
1027 }
1028 
1029 void
1031 {
1032  if (!station->m_statsFile.is_open ())
1033  {
1034  std::ostringstream tmp;
1035  tmp << "minstrel-stats-" << station->m_state->m_address << ".txt";
1036  station->m_statsFile.open (tmp.str ().c_str (), std::ios::out);
1037  }
1038 
1039  station->m_statsFile << "best _______________rate________________ ________statistics________ ________last_______ ______sum-of________\n" <<
1040  "rate [ name idx airtime max_tp] [avg(tp) avg(prob) sd(prob)] [prob.|retry|suc|att] [#success | #attempts]\n";
1041 
1042  uint16_t maxTpRate = station->m_maxTpRate;
1043  uint16_t maxTpRate2 = station->m_maxTpRate2;
1044  uint16_t maxProbRate = station->m_maxProbRate;
1045 
1046  for (uint8_t i = 0; i < station->m_nModes; i++)
1047  {
1048  RateInfo rate = station->m_minstrelTable[i];
1049 
1050  if (i == maxTpRate)
1051  {
1052  station->m_statsFile << 'A';
1053  }
1054  else
1055  {
1056  station->m_statsFile << ' ';
1057  }
1058  if (i == maxTpRate2)
1059  {
1060  station->m_statsFile << 'B';
1061  }
1062  else
1063  {
1064  station->m_statsFile << ' ';
1065  }
1066  if (i == maxProbRate)
1067  {
1068  station->m_statsFile << 'P';
1069  }
1070  else
1071  {
1072  station->m_statsFile << ' ';
1073  }
1074 
1075  float tmpTh = rate.throughput / 100000.0f;
1076  station->m_statsFile << " " <<
1077  std::setw (17) << GetSupported (station, i) << " " <<
1078  std::setw (2) << i << " " <<
1079  std::setw (4) << rate.perfectTxTime.GetMicroSeconds () <<
1080  std::setw (8) << " ----- " <<
1081  std::setw (8) << tmpTh << " " <<
1082  std::setw (3) << rate.ewmaProb / 180 <<
1083  std::setw (3) << " --- " <<
1084  std::setw (3) << rate.prob / 180 << " " <<
1085  std::setw (1) << rate.adjustedRetryCount << " " <<
1086  std::setw (3) << rate.prevNumRateSuccess << " " <<
1087  std::setw (3) << rate.prevNumRateAttempt << " " <<
1088  std::setw (9) << rate.successHist << " " <<
1089  std::setw (9) << rate.attemptHist << "\n";
1090  }
1091  station->m_statsFile << "\nTotal packet count: ideal " << station->m_totalPacketsCount - station->m_samplePacketsCount
1092  << " lookaround " << station->m_samplePacketsCount << "\n\n";
1093 
1094  station->m_statsFile.flush ();
1095 }
1096 
1097 } //namespace ns3
ns3::MinstrelWifiManager::m_uniformRandomVariable
Ptr< UniformRandomVariable > m_uniformRandomVariable
Provides uniform random variables.
Definition: minstrel-wifi-manager.h:350
ns3::MinstrelWifiManager::m_currentRate
TracedValue< uint64_t > m_currentRate
Trace rate changes.
Definition: minstrel-wifi-manager.h:352
ns3::TypeId
a unique identifier for an interface.
Definition: type-id.h:59
ns3::WifiRemoteStationManager::GetDefaultTxPowerLevel
uint8_t GetDefaultTxPowerLevel(void) const
Definition: wifi-remote-station-manager.cc:1184
NS_LOG_COMPONENT_DEFINE
#define NS_LOG_COMPONENT_DEFINE(name)
Define a Log component with a specific name.
Definition: log.h:205
ns3::MinstrelWifiManager::DoCreateStation
WifiRemoteStation * DoCreateStation(void) const override
Definition: minstrel-wifi-manager.cc:176
ns3::RateInfo::prob
uint32_t prob
(# packets success)/(# total packets)
Definition: minstrel-wifi-manager.h:49
ns3::RateInfo::attemptHist
uint64_t attemptHist
Aggregate of all transmission attempts.
Definition: minstrel-wifi-manager.h:60
ns3::MinstrelWifiManager::m_pktLen
uint32_t m_pktLen
packet length used for calculate mode TxTime
Definition: minstrel-wifi-manager.h:345
NS_OBJECT_ENSURE_REGISTERED
#define NS_OBJECT_ENSURE_REGISTERED(type)
Register an Object subclass with the TypeId system.
Definition: object-base.h:45
NS_ASSERT
#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
ns3::MakeTimeChecker
Ptr< const AttributeChecker > MakeTimeChecker(const Time min, const Time max)
Helper to make a Time checker with bounded range.
Definition: time.cc:533
ns3::BooleanValue
AttributeValue implementation for Boolean.
Definition: boolean.h:37
ns3::MinstrelWifiRemoteStation::m_maxTpRate2
uint16_t m_maxTpRate2
second highest throughput rate in bps
Definition: minstrel-wifi-manager.h:96
ns3::WifiRemoteStationManager::GetUseNonErpProtection
bool GetUseNonErpProtection(void) const
Return whether the device supports protection of non-ERP stations.
Definition: wifi-remote-station-manager.cc:1029
minstrel-wifi-manager.h
min
#define min(a, b)
Definition: 80211b.c:42
ns3::MinstrelWifiManager::m_ewmaLevel
uint8_t m_ewmaLevel
exponential weighted moving average
Definition: minstrel-wifi-manager.h:343
ns3::RateInfo::perfectTxTime
Time perfectTxTime
Perfect transmission time calculation, or frame calculation Given a bit rate and a packet length n by...
Definition: minstrel-wifi-manager.h:43
ns3::MinstrelWifiManager::RateInit
void RateInit(MinstrelWifiRemoteStation *station)
Initialize Minstrel Table.
Definition: minstrel-wifi-manager.cc:913
ns3::WifiPhy::GetSlot
Time GetSlot(void) const
Return the slot duration for this PHY.
Definition: wifi-phy.cc:923
ns3::Simulator::Now
static Time Now(void)
Return the current simulation virtual time.
Definition: simulator.cc:195
ns3
Every class exported by the ns3 library is enclosed in the ns3 namespace.
ns3::MinstrelRate
std::vector< RateInfo > MinstrelRate
Data structure for a Minstrel Rate table A vector of a struct RateInfo.
Definition: minstrel-wifi-manager.h:70
ns3::SampleRate
std::vector< std::vector< uint8_t > > SampleRate
Data structure for a Sample Rate table A vector of a vector uint8_t.
Definition: minstrel-wifi-manager.h:75
ns3::MinstrelWifiManager::DoReportRtsOk
void DoReportRtsOk(WifiRemoteStation *station, double ctsSnr, WifiMode ctsMode, double rtsSnr) override
This method is a pure virtual method that must be implemented by the sub-class.
Definition: minstrel-wifi-manager.cc:727
ns3::MinstrelWifiManager::UpdateRetry
void UpdateRetry(MinstrelWifiRemoteStation *station)
Update the number of retries and reset accordingly.
Definition: minstrel-wifi-manager.cc:843
ns3::WifiRemoteStationManager::GetSupported
WifiMode GetSupported(const WifiRemoteStation *station, uint8_t i) const
Return whether mode associated with the specified station at the specified index.
Definition: wifi-remote-station-manager.cc:1610
ns3::MinstrelWifiManager::UpdatePacketCounters
void UpdatePacketCounters(MinstrelWifiRemoteStation *station)
Update packet counters.
Definition: minstrel-wifi-manager.cc:816
ns3::MinstrelWifiManager::AddCalcTxTime
void AddCalcTxTime(WifiMode mode, Time t)
Add transmission time for the given mode to an internal list.
Definition: minstrel-wifi-manager.cc:169
ns3::MinstrelWifiRemoteStation::m_retry
uint32_t m_retry
total retries short + long
Definition: minstrel-wifi-manager.h:107
ns3::MinstrelWifiManager::DoGetRtsTxVector
WifiTxVector DoGetRtsTxVector(WifiRemoteStation *station) override
Definition: minstrel-wifi-manager.cc:860
ns3::MinstrelWifiManager::m_printSamples
bool m_printSamples
whether samples table should be printed.
Definition: minstrel-wifi-manager.h:347
ns3::MinstrelWifiManager::GetCalcTxTime
Time GetCalcTxTime(WifiMode mode) const
Estimate the TxTime of a packet with a given mode.
Definition: minstrel-wifi-manager.cc:160
ns3::MinstrelWifiManager::FindRate
uint16_t FindRate(MinstrelWifiRemoteStation *station)
Find a rate to use from Minstrel Table.
Definition: minstrel-wifi-manager.cc:428
ns3::WifiMode::GetModulationClass
WifiModulationClass GetModulationClass() const
Definition: wifi-mode.cc:177
ns3::MinstrelWifiRemoteStation::m_initialized
bool m_initialized
for initializing tables
Definition: minstrel-wifi-manager.h:109
ns3::WifiRemoteStationManager
hold a list of per-remote-station state.
Definition: wifi-remote-station-manager.h:121
ns3::MinstrelWifiRemoteStation::m_txrate
uint16_t m_txrate
current transmit rate in bps
Definition: minstrel-wifi-manager.h:108
ns3::WifiRemoteStationManager::GetHtSupported
bool GetHtSupported(void) const
Return whether the device has HT capability support enabled.
Definition: wifi-remote-station-manager.cc:232
ns3::WifiRemoteStationManager::GetVhtSupported
bool GetVhtSupported(void) const
Return whether the device has VHT capability support enabled.
Definition: wifi-remote-station-manager.cc:238
ns3::WifiTxVector::SetMode
void SetMode(WifiMode mode)
Sets the selected payload transmission mode.
Definition: wifi-tx-vector.cc:226
ns3::WifiRemoteStationManager::GetNSupported
uint8_t GetNSupported(const WifiRemoteStation *station) const
Return the number of modes supported by the given station.
Definition: wifi-remote-station-manager.cc:1718
ns3::WifiTxVector
This class mimics the TXVECTOR which is to be passed to the PHY in order to define the parameters whi...
Definition: wifi-tx-vector.h:71
ns3::MinstrelWifiManager::DoReportFinalDataFailed
void DoReportFinalDataFailed(WifiRemoteStation *station) override
This method is a pure virtual method that must be implemented by the sub-class.
Definition: minstrel-wifi-manager.cc:788
third.mac
mac
Definition: third.py:99
ns3::MinstrelWifiRemoteStation::m_isSampling
bool m_isSampling
a flag to indicate we are currently sampling
Definition: minstrel-wifi-manager.h:102
ns3::MinstrelWifiManager::GetTypeId
static TypeId GetTypeId(void)
Get the type ID.
Definition: minstrel-wifi-manager.cc:50
ns3::MinstrelWifiRemoteStation
hold per-remote-station state for Minstrel Wifi manager.
Definition: minstrel-wifi-manager.h:84
ns3::MinstrelWifiManager::GetNextSample
uint16_t GetNextSample(MinstrelWifiRemoteStation *station)
Get the next sample from Sample Table.
Definition: minstrel-wifi-manager.cc:891
ns3::MakeBooleanAccessor
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
ns3::WifiPhy::GetAckTxTime
Time GetAckTxTime(void) const
Return the estimated Ack TX time for this PHY.
Definition: wifi-phy.cc:941
ns3::UniformRandomVariable::GetInteger
uint32_t GetInteger(uint32_t min, uint32_t max)
Get the next random value, as an unsigned integer in the specified range .
Definition: random-variable-stream.cc:193
ns3::TypeId::SetParent
TypeId SetParent(TypeId tid)
Set the parent TypeId.
Definition: type-id.cc:923
ns3::WifiRemoteStationManager::GetShortPreambleEnabled
bool GetShortPreambleEnabled(void) const
Return whether the device uses short PHY preambles.
Definition: wifi-remote-station-manager.cc:226
ns3::MinstrelWifiManager::m_updateStats
Time m_updateStats
how frequent do we calculate the stats
Definition: minstrel-wifi-manager.h:341
ns3::MinstrelWifiRemoteStation::m_minstrelTable
MinstrelRate m_minstrelTable
minstrel table
Definition: minstrel-wifi-manager.h:110
ns3::MinstrelWifiManager::GetRtsTxVector
WifiTxVector GetRtsTxVector(MinstrelWifiRemoteStation *station)
Get RTS transmit vector.
Definition: minstrel-wifi-manager.cc:387
ns3::MakeTraceSourceAccessor
Ptr< const TraceSourceAccessor > MakeTraceSourceAccessor(T a)
Create a TraceSourceAccessor which will control access to the underlying trace source.
Definition: trace-source-accessor.h:202
ns3::MinstrelWifiManager::DoReportFinalRtsFailed
void DoReportFinalRtsFailed(WifiRemoteStation *station) override
This method is a pure virtual method that must be implemented by the sub-class.
Definition: minstrel-wifi-manager.cc:733
ns3::RateInfo::throughput
uint32_t throughput
throughput of a rate in bps
Definition: minstrel-wifi-manager.h:55
ns3::MinstrelWifiRemoteStation::m_statsFile
std::ofstream m_statsFile
stats file
Definition: minstrel-wifi-manager.h:112
ns3::WifiRemoteStationManager::GetPhy
Ptr< WifiPhy > GetPhy(void) const
Return the WifiPhy.
Definition: wifi-remote-station-manager.cc:1706
ns3::MinstrelWifiRemoteStation::m_totalPacketsCount
int m_totalPacketsCount
total number of packets as of now
Definition: minstrel-wifi-manager.h:99
ns3::MinstrelWifiRemoteStation::m_sampleDeferred
bool m_sampleDeferred
a flag to indicate sample rate is on the second stage
Definition: minstrel-wifi-manager.h:104
ns3::MinstrelWifiManager::InitSampleTable
void InitSampleTable(MinstrelWifiRemoteStation *station)
Initialize Sample Table.
Definition: minstrel-wifi-manager.cc:982
ns3::Ptr< WifiPhy >
ns3::MinstrelWifiRemoteStation::m_nModes
uint8_t m_nModes
number of modes supported
Definition: minstrel-wifi-manager.h:98
NS_FATAL_ERROR
#define NS_FATAL_ERROR(msg)
Report a fatal error with a message and terminate.
Definition: fatal-error.h:165
ns3::RateInfo::adjustedRetryCount
uint32_t adjustedRetryCount
adjust the retry limit for this rate
Definition: minstrel-wifi-manager.h:46
ns3::MinstrelWifiRemoteStation::m_longRetry
uint32_t m_longRetry
long retries such as data packets
Definition: minstrel-wifi-manager.h:106
ns3::WifiMode
represent a single transmission mode
Definition: wifi-mode.h:48
ns3::MinstrelWifiManager::~MinstrelWifiManager
virtual ~MinstrelWifiManager()
Definition: minstrel-wifi-manager.cc:107
ns3::MinstrelWifiRemoteStation::m_maxTpRate
uint16_t m_maxTpRate
the current throughput rate in bps
Definition: minstrel-wifi-manager.h:95
ns3::MinstrelWifiManager
Implementation of Minstrel Rate Control Algorithm.
Definition: minstrel-wifi-manager.h:158
ns3::MinstrelWifiManager::DoGetDataTxVector
WifiTxVector DoGetDataTxVector(WifiRemoteStation *station) override
Definition: minstrel-wifi-manager.cc:852
ns3::MinstrelWifiManager::PrintTable
void PrintTable(MinstrelWifiRemoteStation *station)
Print Minstrel Table.
Definition: minstrel-wifi-manager.cc:1030
ns3::Time::GetMicroSeconds
int64_t GetMicroSeconds(void) const
Get an approximation of the time stored in this instance in the indicated unit.
Definition: nstime.h:388
ns3::MinstrelWifiManager::CountRetries
uint32_t CountRetries(MinstrelWifiRemoteStation *station)
Get the number of retries.
Definition: minstrel-wifi-manager.cc:409
ns3::MinstrelWifiRemoteStation::m_sampleTable
SampleRate m_sampleTable
sample table
Definition: minstrel-wifi-manager.h:111
ns3::RateInfo::ewmaProb
uint32_t ewmaProb
EWMA calculation ewma_prob =[prob *(100 - ewma_level) + (ewma_prob_old * ewma_level)]/100.
Definition: minstrel-wifi-manager.h:54
ns3::MilliSeconds
Time MilliSeconds(uint64_t value)
Construct a Time in the indicated unit.
Definition: nstime.h:1297
ns3::MinstrelWifiManager::m_printStats
bool m_printStats
whether statistics table should be printed.
Definition: minstrel-wifi-manager.h:346
ns3::MinstrelWifiManager::UpdateStats
void UpdateStats(MinstrelWifiRemoteStation *station)
Update the Minstrel Table.
Definition: minstrel-wifi-manager.cc:532
ns3::MakeBooleanChecker
Ptr< const AttributeChecker > MakeBooleanChecker(void)
Definition: boolean.cc:121
ns3::Time
Simulation virtual time values and global simulation resolution.
Definition: nstime.h:104
NS_ABORT_MSG_IF
#define NS_ABORT_MSG_IF(cond, msg)
Abnormal program termination if a condition is true, with a message.
Definition: abort.h:108
ns3::WifiRemoteStationManager::SetupPhy
virtual void SetupPhy(const Ptr< WifiPhy > phy)
Set up PHY associated with this device since it is the object that knows the full set of transmit rat...
Definition: wifi-remote-station-manager.cc:142
ns3::MinstrelWifiManager::SetupPhy
void SetupPhy(const Ptr< WifiPhy > phy) override
Set up PHY associated with this device since it is the object that knows the full set of transmit rat...
Definition: minstrel-wifi-manager.cc:113
ns3::MinstrelWifiRemoteStation::m_shortRetry
uint32_t m_shortRetry
short retries such as control packets
Definition: minstrel-wifi-manager.h:105
ns3::MinstrelWifiRemoteStation::m_samplePacketsCount
int m_samplePacketsCount
how many packets we have sample so far
Definition: minstrel-wifi-manager.h:100
ns3::GetPreambleForTransmission
WifiPreamble GetPreambleForTransmission(WifiModulationClass modulation, bool useShortPreamble)
Return the preamble to be used for the transmission.
Definition: wifi-phy-common.cc:87
ns3::MinstrelWifiRemoteStation::m_numSamplesDeferred
int m_numSamplesDeferred
number samples deferred
Definition: minstrel-wifi-manager.h:101
ns3::WIFI_PREAMBLE_LONG
@ WIFI_PREAMBLE_LONG
Definition: wifi-phy-common.h:69
ns3::WifiRemoteStation
hold per-remote-station state.
Definition: wifi-remote-station-manager.h:62
ns3::MinstrelWifiManager::DoInitialize
void DoInitialize(void) override
Initialize() implementation.
Definition: minstrel-wifi-manager.cc:134
ns3::WifiRemoteStationManager::GetAggregation
bool GetAggregation(const WifiRemoteStation *station) const
Return whether the given station supports A-MPDU.
Definition: wifi-remote-station-manager.cc:1682
ns3::MinstrelWifiManager::PrintSampleTable
void PrintSampleTable(MinstrelWifiRemoteStation *station)
Print Sample Table.
Definition: minstrel-wifi-manager.cc:1014
ns3::MinstrelWifiRemoteStation::m_sampleRate
uint16_t m_sampleRate
current sample rate in bps
Definition: minstrel-wifi-manager.h:103
ns3::MinstrelWifiManager::DoReportDataOk
void DoReportDataOk(WifiRemoteStation *station, double ackSnr, WifiMode ackMode, double dataSnr, uint16_t dataChannelWidth, uint8_t dataNss) override
This method is a pure virtual method that must be implemented by the sub-class.
Definition: minstrel-wifi-manager.cc:756
ns3::MinstrelWifiRemoteStation::m_col
uint8_t m_col
To keep track of the current position in the our random sample table going row by row from 1st column...
Definition: minstrel-wifi-manager.h:93
NS_LOG_DEBUG
#define NS_LOG_DEBUG(msg)
Use NS_LOG to output a message of level LOG_DEBUG.
Definition: log.h:273
ns3::MinstrelWifiRemoteStation::m_maxProbRate
uint16_t m_maxProbRate
rate with highest probability of success in bps
Definition: minstrel-wifi-manager.h:97
ns3::RateInfo::prevNumRateSuccess
uint32_t prevNumRateSuccess
Number of successful frames transmitted with previous rate.
Definition: minstrel-wifi-manager.h:58
ns3::MinstrelWifiManager::UpdateRate
void UpdateRate(MinstrelWifiRemoteStation *station)
Update the rate.
Definition: minstrel-wifi-manager.cc:236
ns3::MinstrelWifiManager::GetDataTxVector
WifiTxVector GetDataTxVector(MinstrelWifiRemoteStation *station)
Get data transmit vector.
Definition: minstrel-wifi-manager.cc:364
ns3::WifiRemoteStation::m_state
WifiRemoteStationState * m_state
Remote station state.
Definition: wifi-remote-station-manager.h:63
ns3::Seconds
Time Seconds(double value)
Construct a Time in the indicated unit.
Definition: nstime.h:1289
ns3::WifiRemoteStationManager::GetNonErpSupported
WifiMode GetNonErpSupported(const WifiRemoteStation *station, uint8_t i) const
Return whether non-ERP mode associated with the specified station at the specified index.
Definition: wifi-remote-station-manager.cc:1624
ns3::MinstrelWifiManager::MinstrelWifiManager
MinstrelWifiManager()
Definition: minstrel-wifi-manager.cc:99
ns3::RateInfo
A struct to contain all information related to a data rate.
Definition: minstrel-wifi-manager.h:38
ns3::MinstrelWifiManager::CheckInit
void CheckInit(MinstrelWifiRemoteStation *station)
Check for initializations.
Definition: minstrel-wifi-manager.cc:203
ns3::MinstrelWifiManager::m_sampleCol
uint8_t m_sampleCol
number of sample columns
Definition: minstrel-wifi-manager.h:344
ns3::MinstrelWifiManager::SetupMac
void SetupMac(const Ptr< WifiMac > mac) override
Set up MAC associated with this device since it is the object that knows the full set of timing param...
Definition: minstrel-wifi-manager.cc:127
ns3::MinstrelWifiManager::AssignStreams
int64_t AssignStreams(int64_t stream) override
Assign a fixed random variable stream number to the random variables used by this model.
Definition: minstrel-wifi-manager.cc:152
ns3::TimeValue
AttributeValue implementation for Time.
Definition: nstime.h:1353
NS_LOG_FUNCTION
#define NS_LOG_FUNCTION(parameters)
If log level LOG_FUNCTION is enabled, this macro will output all input parameters separated by ",...
Definition: log-macros-enabled.h:244
ns3::MinstrelWifiManager::CalculateTimeUnicastPacket
Time CalculateTimeUnicastPacket(Time dataTransmissionTime, uint32_t shortRetries, uint32_t longRetries)
Estimate the time to transmit the given packet with the given number of retries.
Definition: minstrel-wifi-manager.cc:956
ns3::MinstrelWifiManager::DoReportDataFailed
void DoReportDataFailed(WifiRemoteStation *station) override
This method is a pure virtual method that must be implemented by the sub-class.
Definition: minstrel-wifi-manager.cc:741
ns3::RandomVariableStream::SetStream
void SetStream(int64_t stream)
Specifies the stream number for the RngStream.
Definition: random-variable-stream.cc:100
ns3::MinstrelWifiManager::DoReportRxOk
void DoReportRxOk(WifiRemoteStation *station, double rxSnr, WifiMode txMode) override
This method is a pure virtual method that must be implemented by the sub-class.
Definition: minstrel-wifi-manager.cc:711
ns3::UintegerValue
Hold an unsigned integer type.
Definition: uinteger.h:44
ns3::WifiRemoteStationState::m_address
Mac48Address m_address
Mac48Address of the remote station.
Definition: wifi-remote-station-manager.h:95
ns3::WifiRemoteStationManager::GetChannelWidth
uint16_t GetChannelWidth(const WifiRemoteStation *station) const
Return the channel width supported by the station.
Definition: wifi-remote-station-manager.cc:1658
ns3::WifiMode::GetDataRate
uint64_t GetDataRate(uint16_t channelWidth, uint16_t guardInterval, uint8_t nss) const
Definition: wifi-mode.cc:114
ns3::MakeUintegerAccessor
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
ns3::MinstrelWifiManager::m_calcTxTime
TxTime m_calcTxTime
to hold all the calculated TxTime for all modes
Definition: minstrel-wifi-manager.h:340
ns3::MinstrelWifiManager::DoReportRtsFailed
void DoReportRtsFailed(WifiRemoteStation *station) override
This method is a pure virtual method that must be implemented by the sub-class.
Definition: minstrel-wifi-manager.cc:718
ns3::MinstrelWifiRemoteStation::m_nextStatsUpdate
Time m_nextStatsUpdate
10 times every second
Definition: minstrel-wifi-manager.h:85
ns3::MinstrelWifiManager::m_lookAroundRate
uint8_t m_lookAroundRate
the % to try other rates than our current rate
Definition: minstrel-wifi-manager.h:342
ns3::WifiPhy::GetSifs
Time GetSifs(void) const
Return the Short Interframe Space (SIFS) for this PHY.
Definition: wifi-phy.cc:911
ns3::WifiRemoteStationManager::SetupMac
virtual void SetupMac(const Ptr< WifiMac > mac)
Set up MAC associated with this device since it is the object that knows the full set of timing param...
Definition: wifi-remote-station-manager.cc:161
ns3::WifiTxVector::SetPreambleType
void SetPreambleType(WifiPreamble preamble)
Sets the preamble type.
Definition: wifi-tx-vector.cc:248
ns3::MinstrelWifiRemoteStation::m_index
uint8_t m_index
vector index
Definition: minstrel-wifi-manager.h:94
ns3::WifiRemoteStationManager::GetHeSupported
bool GetHeSupported(void) const
Return whether the device has HE capability support enabled.
Definition: wifi-remote-station-manager.cc:244
third.phy
phy
Definition: third.py:93
ns3::MakeTimeAccessor
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:1354
ns3::RateInfo::prevNumRateAttempt
uint32_t prevNumRateAttempt
Number of transmission attempts with previous rate.
Definition: minstrel-wifi-manager.h:57
ns3::RateInfo::successHist
uint64_t successHist
Aggregate of all transmission successes.
Definition: minstrel-wifi-manager.h:59
ns3::MinstrelWifiManager::DoNeedRetransmission
bool DoNeedRetransmission(WifiRemoteStation *st, Ptr< const Packet > packet, bool normally) override
Definition: minstrel-wifi-manager.cc:868