A Discrete-Event Network Simulator
API
nist-error-rate-model.cc
Go to the documentation of this file.
1 /* -*- Mode:C++; c-file-style:"gnu"; indent-tabs-mode:nil; -*- */
2 /*
3  * Copyright (c) 2010 The Boeing Company
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: Gary Pei <guangyu.pei@boeing.com>
19  * Sébastien Deronne <sebastien.deronne@gmail.com>
20  */
21 
22 #include "nist-error-rate-model.h"
23 #include "wifi-phy.h"
24 #include "ns3/log.h"
25 
26 namespace ns3 {
27 
28 NS_LOG_COMPONENT_DEFINE ("NistErrorRateModel");
29 
30 NS_OBJECT_ENSURE_REGISTERED (NistErrorRateModel);
31 
32 TypeId
34 {
35  static TypeId tid = TypeId ("ns3::NistErrorRateModel")
37  .SetGroupName ("Wifi")
38  .AddConstructor<NistErrorRateModel> ()
39  ;
40  return tid;
41 }
42 
44 {
45 }
46 
47 double
49 {
50  NS_LOG_FUNCTION (this << snr);
51  double z = std::sqrt (snr);
52  double ber = 0.5 * erfc (z);
53  NS_LOG_INFO ("bpsk snr=" << snr << " ber=" << ber);
54  return ber;
55 }
56 
57 double
59 {
60  NS_LOG_FUNCTION (this << snr);
61  double z = std::sqrt (snr / 2.0);
62  double ber = 0.5 * erfc (z);
63  NS_LOG_INFO ("qpsk snr=" << snr << " ber=" << ber);
64  return ber;
65 }
66 
67 double
69 {
70  NS_LOG_FUNCTION (this << snr);
71  double z = std::sqrt (snr / (5.0 * 2.0));
72  double ber = 0.75 * 0.5 * erfc (z);
73  NS_LOG_INFO ("16-Qam" << " snr=" << snr << " ber=" << ber);
74  return ber;
75 }
76 
77 double
79 {
80  NS_LOG_FUNCTION (this << snr);
81  double z = std::sqrt (snr / (21.0 * 2.0));
82  double ber = 7.0 / 12.0 * 0.5 * erfc (z);
83  NS_LOG_INFO ("64-Qam" << " snr=" << snr << " ber=" << ber);
84  return ber;
85 }
86 
87 double
89 {
90  NS_LOG_FUNCTION (this << snr);
91  double z = std::sqrt (snr / (85.0 * 2.0));
92  double ber = 15.0 / 32.0 * 0.5 * erfc (z);
93  NS_LOG_INFO ("256-Qam" << " snr=" << snr << " ber=" << ber);
94  return ber;
95 }
96 
97 double
99 {
100  NS_LOG_FUNCTION (this << snr);
101  double z = std::sqrt (snr / (341.0 * 2.0));
102  double ber = 31.0 / 160.0 * 0.5 * erfc (z);
103  NS_LOG_INFO ("1024-Qam" << " snr=" << snr << " ber=" << ber);
104  return ber;
105 }
106 
107 double
108 NistErrorRateModel::GetFecBpskBer (double snr, uint32_t nbits,
109  uint32_t bValue) const
110 {
111  NS_LOG_FUNCTION (this << snr << nbits << bValue);
112  double ber = GetBpskBer (snr);
113  if (ber == 0.0)
114  {
115  return 1.0;
116  }
117  double pe = CalculatePe (ber, bValue);
118  pe = std::min (pe, 1.0);
119  double pms = std::pow (1 - pe, (double)nbits);
120  return pms;
121 }
122 
123 double
124 NistErrorRateModel::GetFecQpskBer (double snr, uint32_t nbits,
125  uint32_t bValue) const
126 {
127  NS_LOG_FUNCTION (this << snr << nbits << bValue);
128  double ber = GetQpskBer (snr);
129  if (ber == 0.0)
130  {
131  return 1.0;
132  }
133  double pe = CalculatePe (ber, bValue);
134  pe = std::min (pe, 1.0);
135  double pms = std::pow (1 - pe, (double)nbits);
136  return pms;
137 }
138 
139 double
140 NistErrorRateModel::CalculatePe (double p, uint32_t bValue) const
141 {
142  NS_LOG_FUNCTION (this << p << bValue);
143  double D = std::sqrt (4.0 * p * (1.0 - p));
144  double pe = 1.0;
145  if (bValue == 1)
146  {
147  //code rate 1/2, use table 3.1.1
148  pe = 0.5 * (36.0 * std::pow (D, 10)
149  + 211.0 * std::pow (D, 12)
150  + 1404.0 * std::pow (D, 14)
151  + 11633.0 * std::pow (D, 16)
152  + 77433.0 * std::pow (D, 18)
153  + 502690.0 * std::pow (D, 20)
154  + 3322763.0 * std::pow (D, 22)
155  + 21292910.0 * std::pow (D, 24)
156  + 134365911.0 * std::pow (D, 26));
157  }
158  else if (bValue == 2)
159  {
160  //code rate 2/3, use table 3.1.2
161  pe = 1.0 / (2.0 * bValue) *
162  (3.0 * std::pow (D, 6)
163  + 70.0 * std::pow (D, 7)
164  + 285.0 * std::pow (D, 8)
165  + 1276.0 * std::pow (D, 9)
166  + 6160.0 * std::pow (D, 10)
167  + 27128.0 * std::pow (D, 11)
168  + 117019.0 * std::pow (D, 12)
169  + 498860.0 * std::pow (D, 13)
170  + 2103891.0 * std::pow (D, 14)
171  + 8784123.0 * std::pow (D, 15));
172  }
173  else if (bValue == 3)
174  {
175  //code rate 3/4, use table 3.1.2
176  pe = 1.0 / (2.0 * bValue) *
177  (42.0 * std::pow (D, 5)
178  + 201.0 * std::pow (D, 6)
179  + 1492.0 * std::pow (D, 7)
180  + 10469.0 * std::pow (D, 8)
181  + 62935.0 * std::pow (D, 9)
182  + 379644.0 * std::pow (D, 10)
183  + 2253373.0 * std::pow (D, 11)
184  + 13073811.0 * std::pow (D, 12)
185  + 75152755.0 * std::pow (D, 13)
186  + 428005675.0 * std::pow (D, 14));
187  }
188  else if (bValue == 5)
189  {
190  //code rate 5/6, use table V from D. Haccoun and G. Begin, "High-Rate Punctured Convolutional Codes
191  //for Viterbi Sequential Decoding", IEEE Transactions on Communications, Vol. 32, Issue 3, pp.315-319.
192  pe = 1.0 / (2.0 * bValue) *
193  (92.0 * std::pow (D, 4.0)
194  + 528.0 * std::pow (D, 5.0)
195  + 8694.0 * std::pow (D, 6.0)
196  + 79453.0 * std::pow (D, 7.0)
197  + 792114.0 * std::pow (D, 8.0)
198  + 7375573.0 * std::pow (D, 9.0)
199  + 67884974.0 * std::pow (D, 10.0)
200  + 610875423.0 * std::pow (D, 11.0)
201  + 5427275376.0 * std::pow (D, 12.0)
202  + 47664215639.0 * std::pow (D, 13.0));
203  }
204  else
205  {
206  NS_ASSERT (false);
207  }
208  return pe;
209 }
210 
211 double
212 NistErrorRateModel::GetFec16QamBer (double snr, uint32_t nbits,
213  uint32_t bValue) const
214 {
215  NS_LOG_FUNCTION (this << snr << nbits << bValue);
216  double ber = Get16QamBer (snr);
217  if (ber == 0.0)
218  {
219  return 1.0;
220  }
221  double pe = CalculatePe (ber, bValue);
222  pe = std::min (pe, 1.0);
223  double pms = std::pow (1 - pe, static_cast<double> (nbits));
224  return pms;
225 }
226 
227 double
228 NistErrorRateModel::GetFec64QamBer (double snr, uint32_t nbits,
229  uint32_t bValue) const
230 {
231  NS_LOG_FUNCTION (this << snr << nbits << bValue);
232  double ber = Get64QamBer (snr);
233  if (ber == 0.0)
234  {
235  return 1.0;
236  }
237  double pe = CalculatePe (ber, bValue);
238  pe = std::min (pe, 1.0);
239  double pms = std::pow (1 - pe, static_cast<double> (nbits));
240  return pms;
241 }
242 
243 double
244 NistErrorRateModel::GetFec256QamBer (double snr, uint32_t nbits,
245  uint32_t bValue) const
246 {
247  NS_LOG_FUNCTION (this << snr << nbits << bValue);
248  double ber = Get256QamBer (snr);
249  if (ber == 0.0)
250  {
251  return 1.0;
252  }
253  double pe = CalculatePe (ber, bValue);
254  pe = std::min (pe, 1.0);
255  double pms = std::pow (1 - pe, static_cast<double> (nbits));
256  return pms;
257 }
258 
259 double
260 NistErrorRateModel::GetFec1024QamBer (double snr, uint32_t nbits,
261  uint32_t bValue) const
262 {
263  NS_LOG_FUNCTION (this << snr << nbits << bValue);
264  double ber = Get1024QamBer (snr);
265  if (ber == 0.0)
266  {
267  return 1.0;
268  }
269  double pe = CalculatePe (ber, bValue);
270  pe = std::min (pe, 1.0);
271  double pms = std::pow (1 - pe, static_cast<double> (nbits));
272  return pms;
273 }
274 
275 double
276 NistErrorRateModel::GetChunkSuccessRate (WifiMode mode, WifiTxVector txVector, double snr, uint32_t nbits) const
277 {
278  NS_LOG_FUNCTION (this << mode << txVector.GetMode () << snr << nbits);
284  {
285  if (mode.GetConstellationSize () == 2)
286  {
287  if (mode.GetCodeRate () == WIFI_CODE_RATE_1_2)
288  {
289  return GetFecBpskBer (snr,
290  nbits,
291  1); //b value
292  }
293  else
294  {
295  return GetFecBpskBer (snr,
296  nbits,
297  3); //b value
298  }
299  }
300  else if (mode.GetConstellationSize () == 4)
301  {
302  if (mode.GetCodeRate () == WIFI_CODE_RATE_1_2)
303  {
304  return GetFecQpskBer (snr,
305  nbits,
306  1); //b value
307  }
308  else
309  {
310  return GetFecQpskBer (snr,
311  nbits,
312  3); //b value
313  }
314  }
315  else if (mode.GetConstellationSize () == 16)
316  {
317  if (mode.GetCodeRate () == WIFI_CODE_RATE_1_2)
318  {
319  return GetFec16QamBer (snr,
320  nbits,
321  1); //b value
322  }
323  else
324  {
325  return GetFec16QamBer (snr,
326  nbits,
327  3); //b value
328  }
329  }
330  else if (mode.GetConstellationSize () == 64)
331  {
332  if (mode.GetCodeRate () == WIFI_CODE_RATE_2_3)
333  {
334  return GetFec64QamBer (snr,
335  nbits,
336  2); //b value
337  }
338  else if (mode.GetCodeRate () == WIFI_CODE_RATE_5_6)
339  {
340  return GetFec64QamBer (snr,
341  nbits,
342  5); //b value
343  }
344  else
345  {
346  return GetFec64QamBer (snr,
347  nbits,
348  3); //b value
349  }
350  }
351  else if (mode.GetConstellationSize () == 256)
352  {
353  if (mode.GetCodeRate () == WIFI_CODE_RATE_5_6)
354  {
355  return GetFec256QamBer (snr,
356  nbits,
357  5 // b value
358  );
359  }
360  else
361  {
362  return GetFec256QamBer (snr,
363  nbits,
364  3 // b value
365  );
366  }
367  }
368  else if (mode.GetConstellationSize () == 1024)
369  {
370  if (mode.GetCodeRate () == WIFI_CODE_RATE_5_6)
371  {
372  return GetFec1024QamBer (snr,
373  nbits,
374  5 // b value
375  );
376  }
377  else
378  {
379  return GetFec1024QamBer (snr,
380  nbits,
381  3 // b value
382  );
383  }
384  }
385  }
387  {
388  switch (mode.GetDataRate (20))
389  {
390  case 1000000:
392  case 2000000:
394  case 5500000:
396  case 11000000:
398  default:
399  NS_ASSERT ("undefined DSSS/HR-DSSS datarate");
400  }
401  }
402  return 0;
403 }
404 
405 } //namespace ns3
double GetQpskBer(double snr) const
Return BER of QPSK at the given SNR.
static double GetDsssDqpskCck11SuccessRate(double sinr, uint32_t nbits)
Return the chunk success rate of the differential encoded QPSK for 11Mbps data rate.
static TypeId GetTypeId(void)
Get the type ID.
#define NS_LOG_FUNCTION(parameters)
If log level LOG_FUNCTION is enabled, this macro will output all input parameters separated by "...
ERP-OFDM PHY (19.5)
Definition: wifi-mode.h:54
This class mimics the TXVECTOR which is to be passed to the PHY in order to define the parameters whi...
#define NS_OBJECT_ENSURE_REGISTERED(type)
Register an Object subclass with the TypeId system.
Definition: object-base.h:45
#define min(a, b)
Definition: 80211b.c:44
#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
#define NS_LOG_COMPONENT_DEFINE(name)
Define a Log component with a specific name.
Definition: log.h:201
static double GetDsssDqpskSuccessRate(double sinr, uint32_t nbits)
Return the chunk success rate of the differential encoded QPSK.
#define NS_LOG_INFO(msg)
Use NS_LOG to output a message of level LOG_INFO.
Definition: log.h:277
VHT PHY (Clause 22)
Definition: wifi-mode.h:60
HR/DSSS PHY (Clause 18)
Definition: wifi-mode.h:48
double GetFec64QamBer(double snr, uint32_t nbits, uint32_t bValue) const
Return BER of QAM64 at the given SNR after applying FEC.
double Get1024QamBer(double snr) const
Return BER of QAM1024 at the given SNR.
double GetFec16QamBer(double snr, uint32_t nbits, uint32_t bValue) const
Return BER of QAM16 at the given SNR after applying FEC.
represent a single transmission modeA WifiMode is implemented by a single integer which is used to lo...
Definition: wifi-mode.h:97
double GetFec256QamBer(double snr, uint32_t nbits, uint32_t bValue) const
Return BER of QAM256 at the given SNR after applying FEC.
the interface for Wifi's error models
double GetFec1024QamBer(double snr, uint32_t nbits, uint32_t bValue) const
Return BER of QAM1024 at the given SNR after applying FEC.
double CalculatePe(double p, uint32_t bValue) const
Return the coded BER for the given p and b.
uint16_t GetConstellationSize(void) const
Definition: wifi-mode.cc:393
double GetChunkSuccessRate(WifiMode mode, WifiTxVector txVector, double snr, uint32_t nbits) const
A pure virtual method that must be implemented in the subclass.
uint64_t GetDataRate(uint8_t channelWidth, uint16_t guardInterval, uint8_t nss) const
Definition: wifi-mode.cc:143
double Get16QamBer(double snr) const
Return BER of QAM16 at the given SNR.
HT PHY (Clause 20)
Definition: wifi-mode.h:58
A model for the error rate for different modulations.
Every class exported by the ns3 library is enclosed in the ns3 namespace.
double GetFecQpskBer(double snr, uint32_t nbits, uint32_t bValue) const
Return BER of QPSK at the given SNR after applying FEC.
double Get64QamBer(double snr) const
Return BER of QAM64 at the given SNR.
double Get256QamBer(double snr) const
Return BER of QAM256 at the given SNR.
static double GetDsssDqpskCck5_5SuccessRate(double sinr, uint32_t nbits)
Return the chunk success rate of the differential encoded QPSK for 5.5Mbps data rate.
OFDM PHY (Clause 17)
Definition: wifi-mode.h:56
double GetFecBpskBer(double snr, uint32_t nbits, uint32_t bValue) const
Return BER of BPSK at the given SNR after applying FEC.
static double GetDsssDbpskSuccessRate(double sinr, uint32_t nbits)
Return the chunk success rate of the differential BPSK.
WifiModulationClass GetModulationClass() const
Definition: wifi-mode.cc:487
WifiMode GetMode(void) const
a unique identifier for an interface.
Definition: type-id.h:58
WifiCodeRate GetCodeRate(void) const
Definition: wifi-mode.cc:317
TypeId SetParent(TypeId tid)
Set the parent TypeId.
Definition: type-id.cc:914
HE PHY (Clause 26)
Definition: wifi-mode.h:62
DSSS PHY (Clause 15)
Definition: wifi-mode.h:46
double GetBpskBer(double snr) const
Return BER of BPSK at the given SNR.