fun_ofdm  1.0
802.11a Physical Layer for USRP
 All Classes Namespaces Files Functions Variables Enumerations Enumerator Macros Pages
phase_tracker.cpp
Go to the documentation of this file.
1 
11 #include <cstring>
12 #include <iostream>
13 
14 #include "phase_tracker.h"
15 
16 namespace fun
17 {
18 
23  const double POLARITY[127] = {
24  1, 1, 1, 1,-1,-1,-1, 1,-1,-1,-1,-1, 1, 1,-1, 1,
25  -1,-1, 1, 1,-1, 1, 1,-1, 1, 1, 1, 1, 1, 1,-1, 1,
26  1, 1,-1, 1, 1,-1,-1, 1, 1, 1,-1, 1,-1,-1,-1, 1,
27  -1, 1,-1,-1, 1,-1,-1, 1, 1, 1, 1, 1,-1,-1, 1, 1,
28  -1,-1, 1,-1, 1,-1, 1, 1,-1,-1,-1, 1, 1,-1,-1,-1,
29  -1, 1,-1,-1, 1,-1, 1, 1, 1, 1,-1, 1,-1, 1,-1, 1,
30  -1,-1,-1,-1,-1, 1,-1, 1, 1,-1, 1,-1, 1, 1, 1,-1,
31  -1, 1,-1,-1,-1, 1, 1, 1,-1,-1,-1,-1,-1,-1,-1
32  };
33 
37  static int PILOTS[4][2] =
38  {
39  { 11, 1 },
40  { 25, 1 },
41  { 39, 1 },
42  { 53, -1 },
43  };
44 
46  static int DATA_SUBCARRIERS[48] =
47  {
48  6, 7, 8, 9, 10, /*11,*/ 12, 13, 14, 15, 16, 17, 18, 19, 20, 21, 22, 23, 24, /*25,*/ 26, 27, 28, 29, 30, 31,
49  /*32,*/ 33, 34, 35, 36, 37, 38, /*39,*/ 40, 41, 42, 43, 44, 45, 46, 47, 48, 49, 50, 51, 52, /*53*/ 54, 55, 56, 57, 58
50  };
51 
52 
58  block("phase_tracker"),
59  m_symbol_count(0)
60 
61  {
62  }
63 
71  {
72  if(input_buffer.size() == 0) return;
73  output_buffer.resize(input_buffer.size());
74 
75  for(int i = 0; i < input_buffer.size(); i++)
76  {
77  if(input_buffer[i].tag == START_OF_FRAME)
78  {
79  m_symbol_count = 0; // Reset the symbol count
80  }
81 
82  // Calculate the phase error of this symbol based on the pilots
83  std::complex<double> phase_error = std::complex<double>(0,0);
84  for(int p = 0; p < 4; p++)
85  {
86  int pilot = PILOTS[p][1] * POLARITY[m_symbol_count % 127];
87  std::complex<double> ref_pilot_sample = std::complex<double>(pilot, 0);
88  std::complex<double> rec_pilot_sample = input_buffer[i].samples[PILOTS[p][0]];
89  phase_error += rec_pilot_sample * std::conj(ref_pilot_sample) / 4.0;
90  }
91 
92  double angle = std::arg(phase_error);
93 
94  // Apply the phase correction to the data samples
95  for(int s = 0; s < 48; s++)
96  {
97  int index = DATA_SUBCARRIERS[s];
98  output_buffer[i].samples[s] = input_buffer[i].samples[index] * std::complex<double>(std::cos(-angle), std::sin(-angle));
99  }
100 
101  output_buffer[i].tag = input_buffer[i].tag;
102  m_symbol_count++; //Keep track of the current symbol number in the frame
103  }
104 
105  }
106 
107 }
108 
109 
110 
111