A Discrete-Event Network Simulator
API
80211b.c
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  * Author: Gary Pei <guangyu.pei@boeing.com>
19  */
20 
21 /*
22  * This program is used to generate plots found in the paper
23  * G. Pei and Tom Henderson, "Validation of ns-3 802.11b PHY model",
24  * available online at http://www.nsnam.org/~pei/80211b.pdf
25  *
26  * It can be compiled as a C program and relies on a library installation of
27  * the GNU Scientific Library (gsl). To compile:
28  * gcc 80211b.c -o 80211b -lm -lgsl -lgslcblas
29  *
30  * The executable output should be redirected into a text file 80211b.txt
31  * ./80211b > 80211b.txt
32  *
33  * Then gnuplot can load the associated plot file which references 80211b.txt:
34  * gnuplot 80211b.plt
35  */
36 
37 #include "math.h"
38 #include "stdlib.h"
39 #include "stdio.h"
40 #include <gsl/gsl_math.h>
41 #include <gsl/gsl_integration.h>
42 #include <gsl/gsl_cdf.h>
43 #include <gsl/gsl_sf_bessel.h>
44 #define min(a,b) ((a) < (b) ? (a) : (b))
45 #define max(a,b) ((a) > (b) ? (a) : (b))
46 #define WLAN_SIR_perfect 10.0 // if SIR > 10dB, perfect reception
47 #define WLAN_SIR_impossible 0.1 // if SIR < -10dB, impossible to receive
48 
61 typedef struct fn_parameter_t
62 {
63  double beta;
64  double n;
66 
67 double QFunction (double x)
68 {
69  return 0.5 * erfc (x / sqrt (2.0));
70 }
71 
72 double f (double x, void * params)
73 {
74  double beta = ((fn_parameters *) params)->beta;
75  double n = ((fn_parameters *) params)->n;
76  double f = pow ( 2 * gsl_cdf_ugaussian_P (x + beta) - 1, n - 1) * exp (-x * x / 2.0) / sqrt (2.0 * M_PI);
77  return f;
78 }
79 
80 double p_e2 (double e2)
81 {
82  double sep;
83  double error;
84  fn_parameters params;
85  params.beta = sqrt (2.0 * e2);
86  params.n = 8.0;
87  gsl_integration_workspace* w = gsl_integration_workspace_alloc (1000);
88  gsl_function F;
89  F.function = &f;
90  F.params = &params;
91  gsl_integration_qagiu (&F, -params.beta, 0, 1e-7, 1000, w, &sep, &error);
92  gsl_integration_workspace_free (w);
93  if (error == 0.0)
94  {
95  sep = 1.0;
96  }
97  return 1.0 - sep;
98 }
99 
100 double p_e1 (double e1)
101 {
102  return 1.0 - pow ( 1.0 - p_e2 (e1 / 2.0), 2.0);
103 }
104 
105 double DbToNoneDb (double x)
106 {
107  return pow (10.0, x / 10.0);
108 }
109 
110 double NoneDbToDb (double x)
111 {
112  return 10.0 * log10 (x);
113 }
114 
115 double DQPSKFunction (double x)
116 {
117  double pi = acos (-1.0);
118  return ( (sqrt (2.0) + 1.0) / sqrt (8.0 * pi * sqrt (2.0))) * (1.0 / sqrt (x)) * exp ( -(2.0 - sqrt (2.0)) * x);
119 }
120 
121 double Get80211bDsssDbpskBerIeee (double EcNc)
122 {
123  double ber;
124  if (EcNc > WLAN_SIR_perfect)
125  {
126  ber = 0;
127  }
128  else if (EcNc < WLAN_SIR_impossible)
129  {
130  ber = 0.5;
131  }
132  else
133  {
134  ber = min (QFunction (sqrt (11.0 * EcNc)),0.5);
135  }
136  return ber;
137 }
138 
139 double Get80211bDsssDbpskBer (double sinr)
140 {
141  double EbN0 = sinr * 22000000.0 / 1000000.0;
142  double ber = 0.5 * exp (-EbN0);
143  return ber;
144 }
145 
146 double Get80211bDsssDqpskBerIeee (double EcNc)
147 {
148  double ber;
149  if (EcNc > WLAN_SIR_perfect)
150  {
151  ber = 0;
152  }
153  else if (EcNc < WLAN_SIR_impossible)
154  {
155  ber = 0.5;
156  }
157  else
158  {
159  ber = min (QFunction (sqrt (5.5 * EcNc)),0.5);
160  }
161  return ber;
162 }
163 
164 double Get80211bDsssDqpskBer (double sinr)
165 {
166 // 2 bits per symbol, 1 MSPS
167  double EbN0 = sinr * 22000000.0 / 1000000.0 / 2.0;
168  double ber = DQPSKFunction (EbN0);
169  return ber;
170 }
171 
173 {
174  double ber;
175  if (EcNc > WLAN_SIR_perfect)
176  {
177  ber = 0.0;
178  }
179  else if (EcNc < WLAN_SIR_impossible)
180  {
181  ber = 0.5;
182  }
183  else
184  {
185  double pew = 14.0 * QFunction (sqrt (EcNc * 8.0)) + QFunction (sqrt (EcNc * 16.0));
186  pew = min (pew, 0.99999);
187  ber = 8.0 / 15.0 * pew;
188  }
189  return ber;
190 }
191 
192 double Get80211bDsssDqpskCCK11BerIeee (double EcNc)
193 {
194  double ber;
195  if (EcNc > WLAN_SIR_perfect)
196  {
197  ber = 0.0;
198  }
199  else if (EcNc < WLAN_SIR_impossible)
200  {
201  ber = 0.5;
202  }
203  else
204  {
205  double pew = 24.0 * QFunction (sqrt (EcNc * 4.0)) + 16.0 * QFunction (sqrt (EcNc * 6.0)) + 174.0 * QFunction (sqrt (EcNc * 8.0)) + 16.0 * QFunction (sqrt (EcNc * 10.0)) + 24.0 * QFunction (sqrt (EcNc * 12.0)) + QFunction (sqrt (EcNc * 16.0));
206  pew = min (pew, 0.99999);
207  ber = 128.0 / 255.0 * pew;
208  }
209  return ber;
210 }
211 
212 int main (int argc, char * argv[])
213 {
214  double rss, sinr;
215  double totalPkt = 200.0;
216 //double noise = 1.552058; // (dB) this noise figure value corresponds to
217  // -99 dBm noise floor reported in CMU paper
218  double noise = 7; // (dB) this noise figure value corresponds to the
219  // default in YansWifiPhy, and matches CMU testbed results
220  double EcNc, EbN01, EbN02, EbN05, EbN011;
221  double ieee1,ieee2,ieee5,ieee11;
222  double numBits = (1024. + 40. + 14.) * 8.;
223  double dbpsk,dqpsk,cck16,cck256,sepcck16,sepcck256;
224  noise = DbToNoneDb (noise) * 1.3803e-23 * 290.0 * 22000000;
225  for (rss = -102.0; rss <= -80.0; rss += 0.1)
226  {
227  sinr = DbToNoneDb (rss) / 1000.0 / noise;
228  EcNc = sinr * 22000000.0 / 11000000.0; // IEEE sir
229  EbN01 = sinr * 22000000.0 / 1000000.0;
230  // 2 bits per symbol, 1 MSPS
231  EbN02 = sinr * 22000000.0 / 1000000.0 / 2.0;
232  EbN05 = sinr * 22000000.0 / 1375000.0 / 4.0;
233  EbN011 = sinr * 22000000.0 / 1375000.0 / 8.0;
234  // 1=rss, 2=EcNc, 3=EbN01, 4=EbN02, 5=EBN05, 6=EbN011
235  printf ("%g %g %g %g %g %g ", rss, NoneDbToDb (EcNc),
236  NoneDbToDb (EbN01),NoneDbToDb (EbN02),
237  NoneDbToDb (EbN05),NoneDbToDb (EbN011));
238  ieee1 = Get80211bDsssDbpskBerIeee (EcNc);
239  ieee2 = Get80211bDsssDqpskBerIeee (EcNc);
240  ieee5 = Get80211bDsssDqpskCCK5_5BerIeee (EcNc);
241  ieee11 = Get80211bDsssDqpskCCK11BerIeee (EcNc);
242  // 7=ber_ieee1, 8=ber_ieee2, 9=ber_ieee5, 10=ber_ieee11
243  printf (" %g %g %g %g ", ieee1, ieee2,ieee5,ieee11);
244  ieee1 = totalPkt * pow (1 - ieee1, numBits);
245  ieee2 = totalPkt * pow (1 - ieee2, numBits);
246  ieee5 = totalPkt * pow (1 - ieee5, numBits);
247  ieee11 = totalPkt * pow (1 - ieee11, numBits);
248  // 11=pkt_ieee1, 12=pkt_ieee2, 13=pkt_ieee5, 14=pkt_ieee11
249  printf (" %g %g %g %g ", ieee1, ieee2,ieee5,ieee11);
250  dbpsk = Get80211bDsssDbpskBer (sinr);
251  dqpsk = Get80211bDsssDqpskBer (sinr);
252  cck16 = max (0, 8.0 / 15.0 * p_e2 (4.0 * EbN05 / 2.0));
253  cck256 = max (0, 128.0 / 255.0 * p_e1 (8.0 * EbN011 / 2.0));
254  // 15=ber_dbpsk, 16=ber_dqpsk, 17=ber_cck16, 18=ber_cck256
255  printf (" %g %g %g %g ", dbpsk, dqpsk,cck16,cck256);
256  dbpsk = totalPkt * pow (1 - dbpsk,numBits);
257  dqpsk = totalPkt * pow (1 - dqpsk,numBits);
258  sepcck16 = p_e2 (4.0 * EbN05 / 2.0);
259  sepcck256 = p_e1 (8.0 * EbN011 / 2.0);
260  cck16 = totalPkt * pow (1.0 - sepcck16,numBits / 4.0);
261  cck256 = totalPkt * pow (1.0 - sepcck256,numBits / 8.0);
262  // 19=pkt_dbpsk, 20=pkt_dqpsk, 21=pkt_cck16, 22=pkt_cck256
263  printf (" %g %g %g %g ", dbpsk, dqpsk,cck16,cck256);
264  // 23=sinr
265  printf (" %g \n",NoneDbToDb (sinr));
266  }
267  return 0;
268 }
log2() macro definition; to deal with Bug 1467.
fn_parameter_t structure
Definition: 80211b.c:61
double p_e2(double e2)
Definition: 80211b.c:80
double Get80211bDsssDbpskBer(double sinr)
Definition: 80211b.c:139
#define min(a, b)
Definition: 80211b.c:44
double beta
beta
Definition: 80211b.c:63
double Get80211bDsssDqpskCCK11BerIeee(double EcNc)
Definition: 80211b.c:192
double n
n
Definition: 80211b.c:64
double QFunction(double x)
Definition: 80211b.c:67
double Get80211bDsssDqpskBer(double sinr)
Definition: 80211b.c:164
#define max(a, b)
Definition: 80211b.c:45
double NoneDbToDb(double x)
Definition: 80211b.c:110
double Get80211bDsssDqpskBerIeee(double EcNc)
Definition: 80211b.c:146
double f(double x, void *params)
Definition: 80211b.c:72
double p_e1(double e1)
Definition: 80211b.c:100
double Get80211bDsssDqpskCCK5_5BerIeee(double EcNc)
Definition: 80211b.c:172
double DbToNoneDb(double x)
Definition: 80211b.c:105
#define WLAN_SIR_perfect
Definition: 80211b.c:46
double Get80211bDsssDbpskBerIeee(double EcNc)
Definition: 80211b.c:121
double DQPSKFunction(double x)
Definition: 80211b.c:115
#define WLAN_SIR_impossible
Definition: 80211b.c:47