dlsch_demodulation.c 178 KB
Newer Older
1
/*******************************************************************************
2
    OpenAirInterface
ghaddab's avatar
ghaddab committed
3
    Copyright(c) 1999 - 2014 Eurecom
4

ghaddab's avatar
ghaddab committed
5
6
7
8
    OpenAirInterface is free software: you can redistribute it and/or modify
    it under the terms of the GNU General Public License as published by
    the Free Software Foundation, either version 3 of the License, or
    (at your option) any later version.
9
10


ghaddab's avatar
ghaddab committed
11
12
13
14
    OpenAirInterface is distributed in the hope that it will be useful,
    but WITHOUT ANY WARRANTY; without even the implied warranty of
    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
    GNU General Public License for more details.
15

ghaddab's avatar
ghaddab committed
16
    You should have received a copy of the GNU General Public License
17
18
    along with OpenAirInterface.The full GNU General Public License is
   included in this distribution in the file called "COPYING". If not,
ghaddab's avatar
ghaddab committed
19
   see <http://www.gnu.org/licenses/>.
20
21

  Contact Information
ghaddab's avatar
ghaddab committed
22
23
  OpenAirInterface Admin: openair_admin@eurecom.fr
  OpenAirInterface Tech : openair_tech@eurecom.fr
24
  OpenAirInterface Dev  : openair4g-devel@lists.eurecom.fr
25

ghaddab's avatar
ghaddab committed
26
  Address      : Eurecom, Campus SophiaTech, 450 Route des Chappes, CS 50193 - 06904 Biot Sophia Antipolis cedex, FRANCE
27

28
*******************************************************************************/
29
30
31
32
33

/*! \file PHY/LTE_TRANSPORT/dlsch_demodulation.c
 * \brief Top-level routines for demodulating the PDSCH physical channel from 36-211, V8.6 2009-03
 * \author R. Knopp, F. Kaltenberger,A. Bhamri, S. Aubert
 * \date 2011
34
 * \version 0.1
35
36
37
38
39
40
41
42
43
44
 * \company Eurecom
 * \email: knopp@eurecom.fr,florian.kaltenberger@eurecom.fr,ankit.bhamri@eurecom.fr,sebastien.aubert@eurecom.fr
 * \note
 * \warning
 */

#include "PHY/defs.h"
#include "PHY/extern.h"
#include "defs.h"
#include "extern.h"
45
#include "PHY/sse_intrin.h"
46
47
48
49
50


#ifndef USER_MODE
#define NOCYGWIN_STATIC static
#else
51
#define NOCYGWIN_STATIC
52
53
#endif

Elena Lukashova's avatar
Elena Lukashova committed
54
55
56
//#undef LOG_D
//#define LOG_D LOG_I

57
//#define DEBUG_PHY 1
58
//#define DEBUG_DLSCH_DEMOD 1
59

knopp's avatar
knopp committed
60
int avg[4]; 
61
62

// [MCS][i_mod (0,1,2) = (2,4,6)]
63
unsigned char offset_mumimo_llr_drange_fix=0;
64
uint8_t intefr_unaw_shift;
65
66
67
/*
//original values from sebastion + same hand tuning
unsigned char offset_mumimo_llr_drange[29][3]={{8,8,8},{7,7,7},{7,7,7},{7,7,7},{6,6,6},{6,6,6},{6,6,6},{5,5,5},{4,4,4},{1,2,4}, // QPSK
68
69
{5,5,4},{5,5,5},{5,5,5},{3,3,3},{2,2,2},{2,2,2},{2,2,2}, // 16-QAM
{2,2,1},{3,3,3},{3,3,3},{3,3,1},{2,2,2},{2,2,2},{0,0,0},{0,0,0},{0,0,0},{0,0,0},{0,0,0},{0,0,0}}; //64-QAM
70
*/
71
72
73
74
75
76
77
78
 /*
 //first optimization try
 unsigned char offset_mumimo_llr_drange[29][3]={{7, 8, 7},{6, 6, 7},{6, 6, 7},{6, 6, 6},{5, 6, 6},{5, 5, 6},{5, 5, 6},{4, 5, 4},{4, 3, 4},{3, 2, 2},{6, 5, 5},{5, 4, 4},{5, 5, 4},{3, 3, 2},{2, 2, 1},{2, 1, 1},{2, 2, 2},{3, 3, 3},{3, 3, 2},{3, 3, 2},{3, 2, 1},{2, 2, 2},{2, 2, 2},{0, 0, 0},{0, 0, 0},{0, 0, 0},{0, 0, 0},{0, 0, 0}};
 */
 //second optimization try
 /*
   unsigned char offset_mumimo_llr_drange[29][3]={{5, 8, 7},{4, 6, 8},{3, 6, 7},{7, 7, 6},{4, 7, 8},{4, 7, 4},{6, 6, 6},{3, 6, 6},{3, 6, 6},{1, 3, 4},{1, 1, 0},{3, 3, 2},{3, 4, 1},{4, 0, 1},{4, 2, 2},{3, 1, 2},{2, 1, 0},{2, 1, 1},{1, 0, 1},{1, 0, 1},{0, 0, 0},{1, 0, 0},{0, 0, 0},{0, 1, 0},{1, 0, 0},{0, 0, 0},{0, 0, 0},{0, 0, 0},{0, 0, 0}};  w
 */
79
unsigned char offset_mumimo_llr_drange[29][3]= {{0, 6, 5},{0, 4, 5},{0, 4, 5},{0, 5, 4},{0, 5, 6},{0, 5, 3},{0, 4, 4},{0, 4, 4},{0, 3, 3},{0, 1, 2},{1, 1, 0},{1, 3, 2},{3, 4, 1},{2, 0, 0},{2, 2, 2},{1, 1, 1},{2, 1, 0},{2, 1, 1},{1, 0, 1},{1, 0, 1},{0, 0, 0},{1, 0, 0},{0, 0, 0},{0, 1, 0},{1, 0, 0},{0, 0, 0},{0, 0, 0},{0, 0, 0},{0, 0, 0}};
80
81


82
extern void print_shorts(char *s,int16_t *x);
83

84

85
86
87
88
int rx_pdsch(PHY_VARS_UE *phy_vars_ue,
             PDSCH_t type,
             unsigned char eNB_id,
             unsigned char eNB_id_i, //if this == phy_vars_ue->n_connected_eNB, we assume MU interference
gauthier's avatar
gauthier committed
89
             uint8_t subframe,
90
91
             unsigned char symbol,
             unsigned char first_symbol_flag,
92
             RX_type_t rx_type,
93
             unsigned char i_mod,
94
95
96
             unsigned char harq_pid)
{

97
98
99
100
101
102
  LTE_UE_COMMON *lte_ue_common_vars  = &phy_vars_ue->lte_ue_common_vars;
  LTE_UE_PDSCH **lte_ue_pdsch_vars;
  LTE_DL_FRAME_PARMS *frame_parms    = &phy_vars_ue->lte_frame_parms;
  PHY_MEASUREMENTS *phy_measurements = &phy_vars_ue->PHY_measurements;
  LTE_UE_DLSCH_t   **dlsch_ue;

Elena Lukashova's avatar
Elena Lukashova committed
103

104
  unsigned char aatx,aarx;    
105
  unsigned short nb_rb, round;
106
  int avgs, rb;  
Elena Lukashova's avatar
Elena Lukashova committed
107
108

 LTE_DL_UE_HARQ_t *dlsch0_harq,*dlsch1_harq = 0;
109
  uint32_t *rballoc;
110

111
112
113
  int32_t **rxdataF_comp_ptr;
  int32_t **dl_ch_mag_ptr;

Elena Lukashova's avatar
Elena Lukashova committed
114
115
  
  
116
117
118
119
  switch (type) {
  case SI_PDSCH:
    lte_ue_pdsch_vars = &phy_vars_ue->lte_ue_pdsch_vars_SI[eNB_id];
    dlsch_ue          = &phy_vars_ue->dlsch_ue_SI[eNB_id];
120
    dlsch0_harq       = dlsch_ue[0]->harq_processes[harq_pid];
121
    break;
122

123
124
125
  case RA_PDSCH:
    lte_ue_pdsch_vars = &phy_vars_ue->lte_ue_pdsch_vars_ra[eNB_id];
    dlsch_ue          = &phy_vars_ue->dlsch_ue_ra[eNB_id];
126
    dlsch0_harq       = dlsch_ue[0]->harq_processes[harq_pid];
127
    break;
128

129
130
131
  case PDSCH:
    lte_ue_pdsch_vars = &phy_vars_ue->lte_ue_pdsch_vars[eNB_id];
    dlsch_ue          = phy_vars_ue->dlsch_ue[eNB_id];
132
133
    dlsch0_harq       = dlsch_ue[0]->harq_processes[harq_pid];
    dlsch1_harq       = dlsch_ue[1]->harq_processes[harq_pid];
134
135
136
    break;

  default:
137
    LOG_E(PHY,"[UE %d][FATAL] Frame %d subframe %d: Unknown PDSCH format %d\n",phy_vars_ue->frame_rx,subframe,type);
138
139
140
    return(-1);
    break;
  }
141

142
143
  DevAssert(dlsch0_harq);
  round = dlsch0_harq->round;
144

145
  if (eNB_id > 2) {
jiangx's avatar
jiangx committed
146
    LOG_W(PHY,"dlsch_demodulation.c: Illegal eNB_id %d\n",eNB_id);
147
148
    return(-1);
  }
149

150
  if (!lte_ue_common_vars) {
jiangx's avatar
jiangx committed
151
    LOG_W(PHY,"dlsch_demodulation.c: Null lte_ue_common_vars\n");
152
153
154
155
    return(-1);
  }

  if (!dlsch_ue[0]) {
jiangx's avatar
jiangx committed
156
    LOG_W(PHY,"dlsch_demodulation.c: Null dlsch_ue pointer\n");
157
158
159
160
    return(-1);
  }

  if (!lte_ue_pdsch_vars) {
jiangx's avatar
jiangx committed
161
    LOG_W(PHY,"dlsch_demodulation.c: Null lte_ue_pdsch_vars pointer\n");
162
163
    return(-1);
  }
164

165
  if (!frame_parms) {
jiangx's avatar
jiangx committed
166
    LOG_W(PHY,"dlsch_demodulation.c: Null lte_frame_parms\n");
167
168
    return(-1);
  }
169
170
171
172
173
174
  
  if (((frame_parms->Ncp == NORMAL) && (symbol>=7)) ||
      ((frame_parms->Ncp == EXTENDED) && (symbol>=6)))
    rballoc = dlsch0_harq->rb_alloc_odd;
  else
    rballoc = dlsch0_harq->rb_alloc_even;
175

Elena Lukashova's avatar
Elena Lukashova committed
176
  if (dlsch0_harq->mimo_mode>DUALSTREAM_PUSCH_PRECODING) {
177
178
179
    LOG_E(PHY,"This transmission mode is not yet supported!\n");
    return(-1);
  }
Elena Lukashova's avatar
Elena Lukashova committed
180
181
182
  
  
  
183
184
185
186
187
188
189
190
191
192
  if ((dlsch0_harq->mimo_mode==LARGE_CDD) || ((dlsch0_harq->mimo_mode>=DUALSTREAM_UNIFORM_PRECODING1) && (dlsch0_harq->mimo_mode<=DUALSTREAM_PUSCH_PRECODING)))  {
    DevAssert(dlsch1_harq);
    if (eNB_id!=eNB_id_i) {
      LOG_E(PHY,"TM3/TM4 requires to set eNB_id==eNB_id_i!\n");
      return(-1);
    }
  }

  //printf("rx_pdsch: harq_pid=%d, round=%d\n",harq_pid,round);

193
194
  if (frame_parms->nb_antennas_tx_eNB>1) {
    nb_rb = dlsch_extract_rbs_dual(lte_ue_common_vars->rxdataF,
195
196
197
198
199
                                   lte_ue_common_vars->dl_ch_estimates[eNB_id],
                                   lte_ue_pdsch_vars[eNB_id]->rxdataF_ext,
                                   lte_ue_pdsch_vars[eNB_id]->dl_ch_estimates_ext,
                                   dlsch0_harq->pmi_alloc,
                                   lte_ue_pdsch_vars[eNB_id]->pmi_ext,
200
                                   rballoc,
201
202
203
                                   symbol,
                                   subframe,
                                   phy_vars_ue->high_speed_flag,
Elena Lukashova's avatar
Elena Lukashova committed
204
205
                                   frame_parms,
				   dlsch0_harq->mimo_mode);
206
//#ifdef DEBUG_DLSCH_MOD
207
208
209
210
    /*   printf("dlsch: using pmi %lx, rb_alloc %x, pmi_ext ",pmi2hex_2Ar1(dlsch0_harq->pmi_alloc),*rballoc);
       for (rb=0;rb<nb_rb;rb++)
	  printf("%d",lte_ue_pdsch_vars[eNB_id]->pmi_ext[rb]);
       printf("\n");*/
211
//#endif
212

Elena Lukashova's avatar
Elena Lukashova committed
213
   if (rx_type==rx_IC_single_stream) {
214
      if (eNB_id_i<phy_vars_ue->n_connected_eNB) // we are in TM5
Elena Lukashova's avatar
Elena Lukashova committed
215
       nb_rb = dlsch_extract_rbs_dual(lte_ue_common_vars->rxdataF,
216
217
218
219
220
                                       lte_ue_common_vars->dl_ch_estimates[eNB_id_i],
                                       lte_ue_pdsch_vars[eNB_id_i]->rxdataF_ext,
                                       lte_ue_pdsch_vars[eNB_id_i]->dl_ch_estimates_ext,
                                       dlsch0_harq->pmi_alloc,
                                       lte_ue_pdsch_vars[eNB_id_i]->pmi_ext,
221
                                       rballoc,
222
223
224
                                       symbol,
                                       subframe,
                                       phy_vars_ue->high_speed_flag,
Elena Lukashova's avatar
Elena Lukashova committed
225
226
                                       frame_parms,
				       dlsch0_harq->mimo_mode);
Elena Lukashova's avatar
Elena Lukashova committed
227
228
     else 
       nb_rb = dlsch_extract_rbs_dual(lte_ue_common_vars->rxdataF,
229
230
231
232
233
                                       lte_ue_common_vars->dl_ch_estimates[eNB_id],
                                       lte_ue_pdsch_vars[eNB_id_i]->rxdataF_ext,
                                       lte_ue_pdsch_vars[eNB_id_i]->dl_ch_estimates_ext,
                                       dlsch0_harq->pmi_alloc,
                                       lte_ue_pdsch_vars[eNB_id_i]->pmi_ext,
234
                                       rballoc,
235
236
237
                                       symbol,
                                       subframe,
                                       phy_vars_ue->high_speed_flag,
Elena Lukashova's avatar
Elena Lukashova committed
238
239
                                       frame_parms,
				       dlsch0_harq->mimo_mode);
240
241
    }
  } // if n_tx>1
242
  else {
243
    nb_rb = dlsch_extract_rbs_single(lte_ue_common_vars->rxdataF,
244
245
246
247
248
                                     lte_ue_common_vars->dl_ch_estimates[eNB_id],
                                     lte_ue_pdsch_vars[eNB_id]->rxdataF_ext,
                                     lte_ue_pdsch_vars[eNB_id]->dl_ch_estimates_ext,
                                     dlsch0_harq->pmi_alloc,
                                     lte_ue_pdsch_vars[eNB_id]->pmi_ext,
249
                                     rballoc,
250
251
252
253
                                     symbol,
                                     subframe,
                                     phy_vars_ue->high_speed_flag,
                                     frame_parms);
Elena Lukashova's avatar
Elena Lukashova committed
254
255
   if (rx_type==rx_IC_single_stream) {
     if (eNB_id_i<phy_vars_ue->n_connected_eNB)
256
257
258
259
260
261
        nb_rb = dlsch_extract_rbs_single(lte_ue_common_vars->rxdataF,
                                         lte_ue_common_vars->dl_ch_estimates[eNB_id_i],
                                         lte_ue_pdsch_vars[eNB_id_i]->rxdataF_ext,
                                         lte_ue_pdsch_vars[eNB_id_i]->dl_ch_estimates_ext,    
                                         dlsch0_harq->pmi_alloc,
                                         lte_ue_pdsch_vars[eNB_id_i]->pmi_ext,
262
                                         rballoc,
263
264
265
266
                                         symbol,
                                         subframe,
                                         phy_vars_ue->high_speed_flag,
                                         frame_parms);
Elena Lukashova's avatar
Elena Lukashova committed
267

268
      else 
269
270
271
272
273
274
        nb_rb = dlsch_extract_rbs_single(lte_ue_common_vars->rxdataF,
                                         lte_ue_common_vars->dl_ch_estimates[eNB_id],
                                         lte_ue_pdsch_vars[eNB_id_i]->rxdataF_ext,
                                         lte_ue_pdsch_vars[eNB_id_i]->dl_ch_estimates_ext,    
                                         dlsch0_harq->pmi_alloc,
                                         lte_ue_pdsch_vars[eNB_id_i]->pmi_ext,
275
                                         rballoc,
276
277
278
279
                                         symbol,
                                         subframe,
                                         phy_vars_ue->high_speed_flag,
                                         frame_parms);
280
281
    }
  } //else n_tx>1
282
283

  //  printf("nb_rb = %d, eNB_id %d\n",nb_rb,eNB_id);
284
  if (nb_rb==0) {
285
    LOG_D(PHY,"dlsch_demodulation.c: nb_rb=0\n");
286
287
    return(-1);
  }
288

knopp's avatar
   
knopp committed
289
  /*
290
291
  // DL power control: Scaling of Channel estimates for PDSCH
  dlsch_scale_channel(lte_ue_pdsch_vars[eNB_id]->dl_ch_estimates_ext,
292
293
294
295
  frame_parms,
  dlsch_ue,
  symbol,
  nb_rb);
knopp's avatar
   
knopp committed
296
  */
297
298
  if (first_symbol_flag==1) {
    dlsch_channel_level(lte_ue_pdsch_vars[eNB_id]->dl_ch_estimates_ext,
299
300
301
302
                        frame_parms,
                        avg,
                        symbol,
                        nb_rb);
303
#ifdef DEBUG_PHY
jiangx's avatar
jiangx committed
304
    LOG_D(PHY,"[DLSCH] avg[0] %d\n",avg[0]);
305
#endif
306

307
308
309
310
    // the channel gain should be the effective gain of precoding + channel
    // however lets be more conservative and set maxh = nb_tx*nb_rx*max(h_i)
    // in case of precoding we add an additional factor of two for the precoding gain
    avgs = 0;
311

312
313
    for (aatx=0;aatx<frame_parms->nb_antennas_tx_eNB;aatx++)
      for (aarx=0;aarx<frame_parms->nb_antennas_rx;aarx++)
314
315
        avgs = cmax(avgs,avg[(aatx<<1)+aarx]);
    //  avgs = cmax(avgs,avg[(aarx<<1)+aatx]);
316

Elena Lukashova's avatar
Elena Lukashova committed
317
   lte_ue_pdsch_vars[eNB_id]->log2_maxh = (log2_approx(avgs)/2);
318
319
    // + log2_approx(frame_parms->nb_antennas_tx_eNB-1) //-1 because log2_approx counts the number of bits
    //      + log2_approx(frame_parms->nb_antennas_rx-1);
320

321
    if ((dlsch0_harq->mimo_mode>=UNIFORM_PRECODING11) &&
322
323
        (dlsch0_harq->mimo_mode< DUALSTREAM_UNIFORM_PRECODING1) &&
        (dlsch0_harq->dl_power_off==1)) // we are in TM 6
324
325
      lte_ue_pdsch_vars[eNB_id]->log2_maxh++;

326
327
    //printf("log2_maxh =%d\n",lte_ue_pdsch_vars[eNB_id]->log2_maxh);
    
328
    // this version here applies the factor .5 also to the extra terms. however, it does not work so well as the one above
329
    /* K = Nb_rx         in TM1
330
331
332
333
       Nb_tx*Nb_rx   in TM2,4,5
       Nb_tx^2*Nb_rx in TM6 */
    /*
      K = frame_parms->nb_antennas_rx*frame_parms->nb_antennas_tx_eNB; //that also covers TM1 since Nb_tx=1
334
335
336
      if ((dlsch0_harq->mimo_mode>=UNIFORM_PRECODING11) &&
      (dlsch0_harq->mimo_mode< DUALSTREAM_UNIFORM_PRECODING1) &&
      (dlsch0_harq->dl_power_off==1)) // we are in TM 6
337
338
339
340
341
342
      K *= frame_parms->nb_antennas_tx_eNB;

      lte_ue_pdsch_vars[eNB_id]->log2_maxh = (log2_approx(K*avgs)/2);
    */

#ifdef DEBUG_PHY
jiangx's avatar
jiangx committed
343
344
    LOG_D(PHY,"[DLSCH] log2_maxh = %d (%d,%d)\n",lte_ue_pdsch_vars[eNB_id]->log2_maxh,avg[0],avgs);
    LOG_D(PHY,"[DLSCH] mimo_mode = %d\n", dlsch0_harq->mimo_mode);
345
346
#endif
  }
347

348
349
350
  aatx = frame_parms->nb_antennas_tx_eNB;
  aarx = frame_parms->nb_antennas_rx;

351
  if (dlsch0_harq->mimo_mode<LARGE_CDD) {// SISO or ALAMOUTI
352
    
Elena Lukashova's avatar
Elena Lukashova committed
353
    	dlsch_channel_compensation(lte_ue_pdsch_vars[eNB_id]->rxdataF_ext,
354
355
356
357
358
359
360
361
                               lte_ue_pdsch_vars[eNB_id]->dl_ch_estimates_ext,
                               lte_ue_pdsch_vars[eNB_id]->dl_ch_mag0,
                               lte_ue_pdsch_vars[eNB_id]->dl_ch_magb0,
                               lte_ue_pdsch_vars[eNB_id]->rxdataF_comp0,
                               (aatx>1) ? lte_ue_pdsch_vars[eNB_id]->rho : NULL,
                               frame_parms,
                               symbol,
                               first_symbol_flag,
Elena Lukashova's avatar
Elena Lukashova committed
362
                               dlsch0_harq->Qm,
363
364
365
366
367
368
369
370
371
                               nb_rb,
                               lte_ue_pdsch_vars[eNB_id]->log2_maxh,
                               phy_measurements); // log2_maxh+I0_shift
 /*
 if (symbol == 5) {
     write_output("rxF_comp_d.m","rxF_c_d",&lte_ue_pdsch_vars[eNB_id]->rxdataF_comp0[0][symbol*frame_parms->N_RB_DL*12],frame_parms->N_RB_DL*12,1,1);
 } */
    if ((rx_type==rx_IC_single_stream) && 
        (eNB_id_i<phy_vars_ue->n_connected_eNB)) {
Elena Lukashova's avatar
Elena Lukashova committed
372
373
         
	 dlsch_channel_compensation(lte_ue_pdsch_vars[eNB_id_i]->rxdataF_ext,
374
375
376
377
378
379
380
381
382
383
384
385
                                 lte_ue_pdsch_vars[eNB_id_i]->dl_ch_estimates_ext,
                                 lte_ue_pdsch_vars[eNB_id_i]->dl_ch_mag0,
                                 lte_ue_pdsch_vars[eNB_id_i]->dl_ch_magb0,
                                 lte_ue_pdsch_vars[eNB_id_i]->rxdataF_comp0,
                                 (aatx>1) ? lte_ue_pdsch_vars[eNB_id_i]->rho : NULL,
                                 frame_parms,
                                 symbol,
                                 first_symbol_flag,
                                 i_mod,
                                 nb_rb,
                                 lte_ue_pdsch_vars[eNB_id]->log2_maxh,
                                 phy_measurements); // log2_maxh+I0_shift
386
#ifdef DEBUG_PHY
387

388
      if (symbol == 5) {
389
        write_output("rxF_comp_d.m","rxF_c_d",&lte_ue_pdsch_vars[eNB_id]->rxdataF_comp0[0][symbol*frame_parms->N_RB_DL*12],frame_parms->N_RB_DL*12,1,1);
390

391
        write_output("rxF_comp_i.m","rxF_c_i",&lte_ue_pdsch_vars[eNB_id_i]->rxdataF_comp0[0][symbol*frame_parms->N_RB_DL*12],frame_parms->N_RB_DL*12,1,1);     
392
393
      }
#endif 
Elena Lukashova's avatar
Elena Lukashova committed
394
     // compute correlation between signal and interference channels
395
      dlsch_dual_stream_correlation(frame_parms,
396
397
398
399
400
401
                                    symbol,
                                    nb_rb,
                                    lte_ue_pdsch_vars[eNB_id]->dl_ch_estimates_ext,
                                    lte_ue_pdsch_vars[eNB_id_i]->dl_ch_estimates_ext,
                                    lte_ue_pdsch_vars[eNB_id]->dl_ch_rho_ext[harq_pid][round],
                                    lte_ue_pdsch_vars[eNB_id]->log2_maxh);
402
    }
403
    
404
  }
405
406
407
  else if ((dlsch0_harq->mimo_mode == LARGE_CDD) || 
           ((dlsch0_harq->mimo_mode >=DUALSTREAM_UNIFORM_PRECODING1) && 
            (dlsch0_harq->mimo_mode <=DUALSTREAM_PUSCH_PRECODING))){  // TM3 or TM4
408
    //   LOG_I(PHY,"Running PDSCH RX for TM3\n");
409
	      
410
    if (frame_parms->nb_antennas_tx_eNB == 2) {
411
412
413
414
415
416
417
418
419
420
       
	 
	 // scaling interfering channel (following for TM56)
	dlsch_scale_channel(lte_ue_pdsch_vars[eNB_id]->dl_ch_estimates_ext,
			    frame_parms,
			    dlsch_ue,
			    symbol,
			    nb_rb);
	
	        
421
      if (first_symbol_flag==1) {
422
423
        // effective channel of desired user is always stronger than interfering eff. channel
        dlsch_channel_level_TM34(lte_ue_pdsch_vars[eNB_id]->dl_ch_estimates_ext, 
Elena Lukashova's avatar
Elena Lukashova committed
424
425
                                 frame_parms,
				 lte_ue_pdsch_vars[eNB_id]->pmi_ext,
Elena Lukashova's avatar
Elena Lukashova committed
426
427
428
                                 avg,
				 symbol,
				 nb_rb,
429
430
                                 dlsch0_harq->mimo_mode);
	    
Elena Lukashova's avatar
Elena Lukashova committed
431
	
432
	if (rx_type>rx_standard) {
433
434
435
	  //	LOG_D(PHY,"llr_offset = %d\n",offset_mumimo_llr_drange[dlsch0_harq->mcs][(dlsch1_harq->mcs>>1)-1]);
	  lte_ue_pdsch_vars[eNB_id]->log2_maxh = log2_approx(avg[0]) - 13 + offset_mumimo_llr_drange[dlsch0_harq->mcs][(get_Qm(dlsch1_harq->mcs)>>1)-1];
	}
436
	else
437
	lte_ue_pdsch_vars[eNB_id]->log2_maxh = (log2_approx(avg[0])/2)+intefr_unaw_shift;
438
439
440
441
442
443
444
      }
    
      dlsch_channel_compensation_TM34(frame_parms, 
                                     lte_ue_pdsch_vars[eNB_id],
                                     phy_measurements, 
                                     eNB_id, 
                                     symbol, 
Elena Lukashova's avatar
Elena Lukashova committed
445
446
                                     dlsch0_harq->Qm, 
                                     dlsch1_harq->Qm,
447
448
449
450
451
                                     harq_pid,
                                     dlsch0_harq->round,
                                     dlsch0_harq->mimo_mode,
                                     nb_rb, 
                                     lte_ue_pdsch_vars[eNB_id]->log2_maxh); 
Elena Lukashova's avatar
Elena Lukashova committed
452
   	/*   
453
454
455
456
457
458
459
460
       if (symbol == 5) {
   
     write_output("rxF_comp_d00.m","rxF_c_d00",&lte_ue_pdsch_vars[eNB_id]->rxdataF_comp0[0][symbol*frame_parms->N_RB_DL*12],frame_parms->N_RB_DL*12,1,1);// should be QAM
     write_output("rxF_comp_d01.m","rxF_c_d01",&lte_ue_pdsch_vars[eNB_id]->rxdataF_comp0[1][symbol*frame_parms->N_RB_DL*12],frame_parms->N_RB_DL*12,1,1);//should be almost 0
     write_output("rxF_comp_d10.m","rxF_c_d10",&lte_ue_pdsch_vars[eNB_id]->rxdataF_comp1[harq_pid][round][0][symbol*frame_parms->N_RB_DL*12],frame_parms->N_RB_DL*12,1,1);//should be almost 0
     write_output("rxF_comp_d11.m","rxF_c_d11",&lte_ue_pdsch_vars[eNB_id]->rxdataF_comp1[harq_pid][round][1][symbol*frame_parms->N_RB_DL*12],frame_parms->N_RB_DL*12,1,1);//should be QAM

   
Elena Lukashova's avatar
Elena Lukashova committed
461
	}*/
462
      // compute correlation between signal and interference channels (rho12 and rho21)
Elena Lukashova's avatar
Elena Lukashova committed
463
464
      
	dlsch_dual_stream_correlation(frame_parms,
465
466
467
468
469
                                    symbol,
                                    nb_rb,
                                    lte_ue_pdsch_vars[eNB_id]->dl_ch_estimates_ext,
                                    &(lte_ue_pdsch_vars[eNB_id]->dl_ch_estimates_ext[2]),
                                    lte_ue_pdsch_vars[eNB_id]->dl_ch_rho_ext[harq_pid][round],
Elena Lukashova's avatar
Elena Lukashova committed
470
			   	    lte_ue_pdsch_vars[eNB_id]->log2_maxh);
471
472

      //to be optimized (just take complex conjugate)
Elena Lukashova's avatar
Elena Lukashova committed
473

474
      dlsch_dual_stream_correlation(frame_parms,
475
476
477
478
                                    symbol,
                                    nb_rb,
                                    &(lte_ue_pdsch_vars[eNB_id]->dl_ch_estimates_ext[2]),
                                    lte_ue_pdsch_vars[eNB_id]->dl_ch_estimates_ext,
479
                                    lte_ue_pdsch_vars[eNB_id]->dl_ch_rho2_ext,
Elena Lukashova's avatar
Elena Lukashova committed
480
				    lte_ue_pdsch_vars[eNB_id]->log2_maxh);
481
482
      //printf("TM3 log2_maxh : %d\n",lte_ue_pdsch_vars[eNB_id]->log2_maxh);

Elena Lukashova's avatar
Elena Lukashova committed
483
   }
484
      else {
Elena Lukashova's avatar
Elena Lukashova committed
485
     LOG_E(PHY, "only 2 tx antennas supported for TM3\n");
486
      return(-1);
487
488
    }
  }
489
  else if (dlsch0_harq->mimo_mode<DUALSTREAM_UNIFORM_PRECODING1) {// single-layer precoding (TM5, TM6)
Elena Lukashova's avatar
Elena Lukashova committed
490
   //    printf("Channel compensation for precoding\n");
491
    if ((rx_type==rx_IC_single_stream) && (eNB_id_i==phy_vars_ue->n_connected_eNB)) {  // TM5 two-user
492
493
494

      // Scale the channel estimates for interfering stream

495
      dlsch_scale_channel(lte_ue_pdsch_vars[eNB_id_i]->dl_ch_estimates_ext,
496
497
498
499
                          frame_parms,
                          dlsch_ue,
                          symbol,
                          nb_rb);     
500
501
502

      /* compute new log2_maxh for effective channel */
      if (first_symbol_flag==1) {
Elena Lukashova's avatar
Elena Lukashova committed
503

504
        // effective channel of desired user is always stronger than interfering eff. channel
Elena Lukashova's avatar
Elena Lukashova committed
505
506
507
508
509
510
       dlsch_channel_level_TM56(lte_ue_pdsch_vars[eNB_id]->dl_ch_estimates_ext,
				frame_parms,
				lte_ue_pdsch_vars[eNB_id]->pmi_ext,
				avg,
				symbol,
				nb_rb);
511

512
513
        //    LOG_D(PHY,"llr_offset = %d\n",offset_mumimo_llr_drange[dlsch0_harq->mcs][(i_mod>>1)-1]);
        avg[0] = log2_approx(avg[0]) - 13 + offset_mumimo_llr_drange[dlsch0_harq->mcs][(i_mod>>1)-1];
514

515
516
        lte_ue_pdsch_vars[eNB_id]->log2_maxh = cmax(avg[0],0);
        //printf("log1_maxh =%d\n",lte_ue_pdsch_vars[eNB_id]->log2_maxh);
517
518
519
520
521
522
523
524
525
526
527
528
      }

      dlsch_channel_compensation_TM56(lte_ue_pdsch_vars[eNB_id]->rxdataF_ext,
                                      lte_ue_pdsch_vars[eNB_id]->dl_ch_estimates_ext,
                                      lte_ue_pdsch_vars[eNB_id]->dl_ch_mag0,
                                      lte_ue_pdsch_vars[eNB_id]->dl_ch_magb0,
                                      lte_ue_pdsch_vars[eNB_id]->rxdataF_comp0,
                                      lte_ue_pdsch_vars[eNB_id]->pmi_ext,
                                      frame_parms,
                                      phy_measurements,
                                      eNB_id,
                                      symbol,
529
                                      dlsch0_harq->Qm,
530
531
                                      nb_rb,
                                      lte_ue_pdsch_vars[eNB_id]->log2_maxh,
532
                                      dlsch0_harq->dl_power_off);
533
534
535
536

      // if interference source is MU interference, assume opposite precoder was used at eNB

      // calculate opposite PMI
537
      for (rb=0; rb<nb_rb; rb++) {
Elena Lukashova's avatar
Elena Lukashova committed
538

539
540
541
542
        switch(lte_ue_pdsch_vars[eNB_id]->pmi_ext[rb]) {
        case 0:
          lte_ue_pdsch_vars[eNB_id_i]->pmi_ext[rb]=1;
          break;
Elena Lukashova's avatar
Elena Lukashova committed
543
       case 1:
544
545
          lte_ue_pdsch_vars[eNB_id_i]->pmi_ext[rb]=0;
          break;
Elena Lukashova's avatar
Elena Lukashova committed
546
       case 2:
547
548
549
550
551
552
          lte_ue_pdsch_vars[eNB_id_i]->pmi_ext[rb]=3;
          break;
        case 3:
          lte_ue_pdsch_vars[eNB_id_i]->pmi_ext[rb]=2;
          break;
        }
553

Elena Lukashova's avatar
Elena Lukashova committed
554
       //  if (rb==0)
555
556
        //    printf("pmi %d, pmi_i %d\n",lte_ue_pdsch_vars[eNB_id]->pmi_ext[rb],lte_ue_pdsch_vars[eNB_id_i]->pmi_ext[rb]);

557
558
      }

559
560
561
562
563
564
565
566
567
568
569
570
571
      dlsch_channel_compensation_TM56(lte_ue_pdsch_vars[eNB_id_i]->rxdataF_ext,
                                      lte_ue_pdsch_vars[eNB_id_i]->dl_ch_estimates_ext,
                                      lte_ue_pdsch_vars[eNB_id_i]->dl_ch_mag0,
                                      lte_ue_pdsch_vars[eNB_id_i]->dl_ch_magb0,
                                      lte_ue_pdsch_vars[eNB_id_i]->rxdataF_comp0,
                                      lte_ue_pdsch_vars[eNB_id_i]->pmi_ext,
                                      frame_parms,
                                      phy_measurements,
                                      eNB_id_i,
                                      symbol,
                                      i_mod,
                                      nb_rb,
                                      lte_ue_pdsch_vars[eNB_id]->log2_maxh,
572
                                      dlsch0_harq->dl_power_off);
573

Elena Lukashova's avatar
Elena Lukashova committed
574

575
#ifdef DEBUG_PHY
576

577
      if (symbol==5) {
578
        write_output("rxF_comp_d.m","rxF_c_d",&lte_ue_pdsch_vars[eNB_id]->rxdataF_comp0[0][symbol*frame_parms->N_RB_DL*12],frame_parms->N_RB_DL*12,1,1);
Elena Lukashova's avatar
Elena Lukashova committed
579
       write_output("rxF_comp_i.m","rxF_c_i",&lte_ue_pdsch_vars[eNB_id_i]->rxdataF_comp0[0][symbol*frame_parms->N_RB_DL*12],frame_parms->N_RB_DL*12,1,1);
580
      }
581
#endif
582
      dlsch_dual_stream_correlation(frame_parms, 
583
584
585
586
587
588
                                    symbol, 
                                    nb_rb, 
                                    lte_ue_pdsch_vars[eNB_id]->dl_ch_estimates_ext, 
                                    lte_ue_pdsch_vars[eNB_id_i]->dl_ch_estimates_ext, 
                                    lte_ue_pdsch_vars[eNB_id]->dl_ch_rho_ext[harq_pid][round], 
                                    lte_ue_pdsch_vars[eNB_id]->log2_maxh);
589

590
    } else {
591
      dlsch_channel_compensation_TM56(lte_ue_pdsch_vars[eNB_id]->rxdataF_ext,
592
593
594
595
596
597
598
599
600
                                      lte_ue_pdsch_vars[eNB_id]->dl_ch_estimates_ext,
                                      lte_ue_pdsch_vars[eNB_id]->dl_ch_mag0,
                                      lte_ue_pdsch_vars[eNB_id]->dl_ch_magb0,
                                      lte_ue_pdsch_vars[eNB_id]->rxdataF_comp0,
                                      lte_ue_pdsch_vars[eNB_id]->pmi_ext,
                                      frame_parms,
                                      phy_measurements,
                                      eNB_id,
                                      symbol,
601
                                      dlsch0_harq->Qm,
602
603
604
                                      nb_rb,
                                      lte_ue_pdsch_vars[eNB_id]->log2_maxh,
                                      1);
Elena Lukashova's avatar
Elena Lukashova committed
605

606
607
608
609
    }
  }

  //  printf("MRC\n");
610
  if (frame_parms->nb_antennas_rx > 1) {
611
612
613
    if ((dlsch0_harq->mimo_mode == LARGE_CDD) ||
        ((dlsch0_harq->mimo_mode >=DUALSTREAM_UNIFORM_PRECODING1) && 
         (dlsch0_harq->mimo_mode <=DUALSTREAM_PUSCH_PRECODING))){  // TM3 or TM4
614
      if (frame_parms->nb_antennas_tx_eNB == 2) {
Elena Lukashova's avatar
Elena Lukashova committed
615

616
617
618
619
620
621
622
	dlsch_detection_mrc_TM34(frame_parms, 
                                 lte_ue_pdsch_vars[eNB_id],
				 harq_pid,
                                 dlsch0_harq->round,
				 symbol,
				 nb_rb,
				 1);
623
      }
624
625
    } else {

626
      dlsch_detection_mrc(frame_parms,
627
628
629
630
631
632
633
634
635
636
637
                          lte_ue_pdsch_vars[eNB_id]->rxdataF_comp0,
                          lte_ue_pdsch_vars[eNB_id_i]->rxdataF_comp0,
                          lte_ue_pdsch_vars[eNB_id]->rho,
                          lte_ue_pdsch_vars[eNB_id]->dl_ch_rho_ext[harq_pid][round],
                          lte_ue_pdsch_vars[eNB_id]->dl_ch_mag0,
                          lte_ue_pdsch_vars[eNB_id]->dl_ch_magb0,
                          lte_ue_pdsch_vars[eNB_id_i]->dl_ch_mag0,
                          lte_ue_pdsch_vars[eNB_id_i]->dl_ch_magb0,
                          symbol,
                          nb_rb,
                          rx_type==rx_IC_single_stream); 
638
639
    }
  }
640

641
642
643
644
645
646
647
648
649
650
651
652
653
654
655
  //  printf("Combining");
  if ((dlsch0_harq->mimo_mode == SISO) ||
      ((dlsch0_harq->mimo_mode >= UNIFORM_PRECODING11) &&
       (dlsch0_harq->mimo_mode <= PUSCH_PRECODING0))) {

    /*
      dlsch_siso(frame_parms,
      lte_ue_pdsch_vars[eNB_id]->rxdataF_comp,
      lte_ue_pdsch_vars[eNB_id_i]->rxdataF_comp,
      symbol,
      nb_rb);
    */
  } else if (dlsch0_harq->mimo_mode == ALAMOUTI) {

    dlsch_alamouti(frame_parms,
656
657
658
659
660
                   lte_ue_pdsch_vars[eNB_id]->rxdataF_comp0,
                   lte_ue_pdsch_vars[eNB_id]->dl_ch_mag0,
                   lte_ue_pdsch_vars[eNB_id]->dl_ch_magb0,
                   symbol,
                   nb_rb);
Elena Lukashova's avatar
Elena Lukashova committed
661
        
662
  } 
663
          
664
665
666
667
668
669
  //    printf("LLR");
  if ((dlsch0_harq->mimo_mode == LARGE_CDD) || 
      ((dlsch0_harq->mimo_mode >=DUALSTREAM_UNIFORM_PRECODING1) && 
       (dlsch0_harq->mimo_mode <=DUALSTREAM_PUSCH_PRECODING)))  {
    rxdataF_comp_ptr = lte_ue_pdsch_vars[eNB_id]->rxdataF_comp1[harq_pid][round];
    dl_ch_mag_ptr = lte_ue_pdsch_vars[eNB_id]->dl_ch_mag1;
670
671
  }
  else {
672
673
674
    rxdataF_comp_ptr = lte_ue_pdsch_vars[eNB_id_i]->rxdataF_comp0;
    dl_ch_mag_ptr = lte_ue_pdsch_vars[eNB_id_i]->dl_ch_mag0;
    //i_mod should have been passed as a parameter
675
  }
676

677
  switch (dlsch0_harq->Qm) {
678
  case 2 : 
679
680
681
682
683
    if (rx_type==rx_standard) {
        dlsch_qpsk_llr(frame_parms,
                       lte_ue_pdsch_vars[eNB_id]->rxdataF_comp0,
                       lte_ue_pdsch_vars[eNB_id]->llr[0],
                       symbol,first_symbol_flag,nb_rb,
684
                       adjust_G2(frame_parms,dlsch0_harq->rb_alloc_even,2,subframe,symbol),
685
686
687
                       lte_ue_pdsch_vars[eNB_id]->llr128);
    }
      else if ((rx_type==rx_IC_single_stream) || (rx_type==rx_IC_dual_stream)) {
Elena Lukashova's avatar
Elena Lukashova committed
688
        if (dlsch1_harq->Qm == 2) {
689
690
691
692
693
694
          dlsch_qpsk_qpsk_llr(frame_parms,
                              lte_ue_pdsch_vars[eNB_id]->rxdataF_comp0,
                              rxdataF_comp_ptr,
                              lte_ue_pdsch_vars[eNB_id]->dl_ch_rho_ext[harq_pid][round],
                              lte_ue_pdsch_vars[eNB_id]->llr[0],
                              symbol,first_symbol_flag,nb_rb,
Elena Lukashova's avatar
Elena Lukashova committed
695
                              adjust_G2(frame_parms,dlsch0_harq->rb_alloc_even,2,subframe,symbol),
696
697
698
699
700
701
702
703
                              lte_ue_pdsch_vars[eNB_id]->llr128);
          if (rx_type==rx_IC_dual_stream) {
            dlsch_qpsk_qpsk_llr(frame_parms,
                                rxdataF_comp_ptr,
                                lte_ue_pdsch_vars[eNB_id]->rxdataF_comp0,
                                lte_ue_pdsch_vars[eNB_id]->dl_ch_rho2_ext,
                                lte_ue_pdsch_vars[eNB_id]->llr[1],
                                symbol,first_symbol_flag,nb_rb,
Elena Lukashova's avatar
Elena Lukashova committed
704
                               adjust_G2(frame_parms,dlsch1_harq->rb_alloc_even,2,subframe,symbol),
705
706
707
                                lte_ue_pdsch_vars[eNB_id]->llr128_2ndstream);
          }
        }
Elena Lukashova's avatar
Elena Lukashova committed
708
        else if (dlsch1_harq->Qm == 4) { 
709
710
711
712
713
714
715
          dlsch_qpsk_16qam_llr(frame_parms,
                               lte_ue_pdsch_vars[eNB_id]->rxdataF_comp0,
                               rxdataF_comp_ptr,//i
                               dl_ch_mag_ptr,//i
                               lte_ue_pdsch_vars[eNB_id]->dl_ch_rho_ext[harq_pid][round],
                               lte_ue_pdsch_vars[eNB_id]->llr[0],
                               symbol,first_symbol_flag,nb_rb,
Elena Lukashova's avatar
Elena Lukashova committed
716
                               adjust_G2(frame_parms,dlsch0_harq->rb_alloc_even,2,subframe,symbol),
717
718
719
720
721
722
723
724
725
                               lte_ue_pdsch_vars[eNB_id]->llr128);
          if (rx_type==rx_IC_dual_stream) {
            dlsch_16qam_qpsk_llr(frame_parms,
                                 rxdataF_comp_ptr,
                                 lte_ue_pdsch_vars[eNB_id]->rxdataF_comp0,//i
                                 dl_ch_mag_ptr,
                                 lte_ue_pdsch_vars[eNB_id]->dl_ch_rho2_ext,
                                 lte_ue_pdsch_vars[eNB_id]->llr[1],
                                 symbol,first_symbol_flag,nb_rb,
Elena Lukashova's avatar
Elena Lukashova committed
726
                                 adjust_G2(frame_parms,dlsch1_harq->rb_alloc_even,4,subframe,symbol),
727
728
729
730
731
732
733
734
735
736
737
                                 lte_ue_pdsch_vars[eNB_id]->llr128_2ndstream);
          }
        }
        else {
          dlsch_qpsk_64qam_llr(frame_parms,
                               lte_ue_pdsch_vars[eNB_id]->rxdataF_comp0,
                               rxdataF_comp_ptr,//i
                               dl_ch_mag_ptr,//i
                               lte_ue_pdsch_vars[eNB_id]->dl_ch_rho_ext[harq_pid][round],
                               lte_ue_pdsch_vars[eNB_id]->llr[0],
                               symbol,first_symbol_flag,nb_rb,
Elena Lukashova's avatar
Elena Lukashova committed
738
                               adjust_G2(frame_parms,dlsch0_harq->rb_alloc_even,2,subframe,symbol),
739
740
741
742
743
744
745
746
747
                               lte_ue_pdsch_vars[eNB_id]->llr128);
          if (rx_type==rx_IC_dual_stream) {
            dlsch_64qam_qpsk_llr(frame_parms,
                                 rxdataF_comp_ptr,
                                 lte_ue_pdsch_vars[eNB_id]->rxdataF_comp0,//i
                                 dl_ch_mag_ptr,
                                 lte_ue_pdsch_vars[eNB_id]->dl_ch_rho2_ext,
                                 lte_ue_pdsch_vars[eNB_id]->llr[1],
                                 symbol,first_symbol_flag,nb_rb,
Elena Lukashova's avatar
Elena Lukashova committed
748
                                 adjust_G2(frame_parms,dlsch1_harq->rb_alloc_even,6,subframe,symbol),
749
750
751
                                 lte_ue_pdsch_vars[eNB_id]->llr128_2ndstream);
          }
        }          
752
      }
753
754
755
756
757
758
759
760
    break;
  case 4 :
    if (rx_type==rx_standard) {
      dlsch_16qam_llr(frame_parms,
                      lte_ue_pdsch_vars[eNB_id]->rxdataF_comp0,
                      lte_ue_pdsch_vars[eNB_id]->llr[0],
                      lte_ue_pdsch_vars[eNB_id]->dl_ch_mag0,
                      symbol,first_symbol_flag,nb_rb,
761
                      adjust_G2(frame_parms,dlsch0_harq->rb_alloc_even,4,subframe,symbol),
762
                      lte_ue_pdsch_vars[eNB_id]->llr128);
763
    }
764
    else if ((rx_type==rx_IC_single_stream) || (rx_type==rx_IC_dual_stream)) {
Elena Lukashova's avatar
Elena Lukashova committed
765
      if (dlsch1_harq->Qm == 2) {
766
767
768
769
770
771
772
        dlsch_16qam_qpsk_llr(frame_parms,
                             lte_ue_pdsch_vars[eNB_id]->rxdataF_comp0,
                             rxdataF_comp_ptr,//i
                             lte_ue_pdsch_vars[eNB_id]->dl_ch_mag0,
                             lte_ue_pdsch_vars[eNB_id]->dl_ch_rho_ext[harq_pid][round],
                             lte_ue_pdsch_vars[eNB_id]->llr[0],
                             symbol,first_symbol_flag,nb_rb,
Elena Lukashova's avatar
Elena Lukashova committed
773
                             adjust_G2(frame_parms,dlsch0_harq->rb_alloc_even,4,subframe,symbol),
774
775
776
777
778
779
780
781
782
                             lte_ue_pdsch_vars[eNB_id]->llr128);
        if (rx_type==rx_IC_dual_stream) {
          dlsch_qpsk_16qam_llr(frame_parms,
                               rxdataF_comp_ptr,
                               lte_ue_pdsch_vars[eNB_id]->rxdataF_comp0,//i
                               lte_ue_pdsch_vars[eNB_id]->dl_ch_mag0,//i
                               lte_ue_pdsch_vars[eNB_id]->dl_ch_rho2_ext,
                               lte_ue_pdsch_vars[eNB_id]->llr[1],
                               symbol,first_symbol_flag,nb_rb,
Elena Lukashova's avatar
Elena Lukashova committed
783
                               adjust_G2(frame_parms,dlsch1_harq->rb_alloc_even,2,subframe,symbol),
784
785
                               lte_ue_pdsch_vars[eNB_id]->llr128_2ndstream);
        }
786
      }
Elena Lukashova's avatar
Elena Lukashova committed
787
      else if (dlsch1_harq->Qm == 4) {
788
789
790
791
792
793
794
795
	dlsch_16qam_16qam_llr(frame_parms,
			      lte_ue_pdsch_vars[eNB_id]->rxdataF_comp0,
			      rxdataF_comp_ptr,//i
			      lte_ue_pdsch_vars[eNB_id]->dl_ch_mag0,
			      dl_ch_mag_ptr,//i
			      lte_ue_pdsch_vars[eNB_id]->dl_ch_rho_ext[harq_pid][round],
			      lte_ue_pdsch_vars[eNB_id]->llr[0],
			      symbol,first_symbol_flag,nb_rb,
Elena Lukashova's avatar
Elena Lukashova committed
796
			      adjust_G2(frame_parms,dlsch0_harq->rb_alloc_even,4,subframe,symbol),
797
798
799
800
801
802
803
804
805
806
			      lte_ue_pdsch_vars[eNB_id]->llr128);
	if (rx_type==rx_IC_dual_stream) {
	  dlsch_16qam_16qam_llr(frame_parms,
				rxdataF_comp_ptr,
				lte_ue_pdsch_vars[eNB_id]->rxdataF_comp0,//i
				dl_ch_mag_ptr,
				lte_ue_pdsch_vars[eNB_id]->dl_ch_mag0,//i
				lte_ue_pdsch_vars[eNB_id]->dl_ch_rho2_ext,
				lte_ue_pdsch_vars[eNB_id]->llr[1],
				symbol,first_symbol_flag,nb_rb,
Elena Lukashova's avatar
Elena Lukashova committed
807
				adjust_G2(frame_parms,dlsch1_harq->rb_alloc_even,4,subframe,symbol),
808
809
				lte_ue_pdsch_vars[eNB_id]->llr128_2ndstream);
	}
810
811
      }
      else {
812
813
814
815
816
817
818
819
	dlsch_16qam_64qam_llr(frame_parms,
			      lte_ue_pdsch_vars[eNB_id]->rxdataF_comp0,
			      rxdataF_comp_ptr,//i
			      lte_ue_pdsch_vars[eNB_id]->dl_ch_mag0,
			      dl_ch_mag_ptr,//i
			      lte_ue_pdsch_vars[eNB_id]->dl_ch_rho_ext[harq_pid][round],
			      lte_ue_pdsch_vars[eNB_id]->llr[0],
			      symbol,first_symbol_flag,nb_rb,
Elena Lukashova's avatar
Elena Lukashova committed
820
			      adjust_G2(frame_parms,dlsch0_harq->rb_alloc_even,4,subframe,symbol),
821
822
823
824
825
826
827
828
829
830
			      lte_ue_pdsch_vars[eNB_id]->llr128);
	if (rx_type==rx_IC_dual_stream) {
	  dlsch_64qam_16qam_llr(frame_parms,
				rxdataF_comp_ptr,
				lte_ue_pdsch_vars[eNB_id]->rxdataF_comp0,
				dl_ch_mag_ptr,
				lte_ue_pdsch_vars[eNB_id]->dl_ch_mag0,
				lte_ue_pdsch_vars[eNB_id]->dl_ch_rho2_ext,
				lte_ue_pdsch_vars[eNB_id]->llr[1],
				symbol,first_symbol_flag,nb_rb,
Elena Lukashova's avatar
Elena Lukashova committed
831
				adjust_G2(frame_parms,dlsch1_harq->rb_alloc_even,6,subframe,symbol),
832
833
834
835
836
837
838
839
840
841
842
843
844
				lte_ue_pdsch_vars[eNB_id]->llr128_2ndstream);
	}
      }
    }
    break;
  case 6 :
    if (rx_type==rx_standard) {
      dlsch_64qam_llr(frame_parms,
                      lte_ue_pdsch_vars[eNB_id]->rxdataF_comp0,
                      lte_ue_pdsch_vars[eNB_id]->llr[0],
                      lte_ue_pdsch_vars[eNB_id]->dl_ch_mag0,
                      lte_ue_pdsch_vars[eNB_id]->dl_ch_magb0,
                      symbol,first_symbol_flag,nb_rb,
845
                      adjust_G2(frame_parms,dlsch0_harq->rb_alloc_even,6,subframe,symbol),
846
847
848
                      lte_ue_pdsch_vars[eNB_id]->llr128);
    }
    else if ((rx_type==rx_IC_single_stream) || (rx_type==rx_IC_dual_stream)) {
Elena Lukashova's avatar
Elena Lukashova committed
849
      if (dlsch1_harq->Qm == 2) {              
850
	dlsch_64qam_qpsk_llr(frame_parms,
851
			     lte_ue_pdsch_vars[eNB_id]->rxdataF_comp0,
852
853
854
			     rxdataF_comp_ptr,//i
			     lte_ue_pdsch_vars[eNB_id]->dl_ch_mag0,
			     lte_ue_pdsch_vars[eNB_id]->dl_ch_rho_ext[harq_pid][round],
855
856
			     lte_ue_pdsch_vars[eNB_id]->llr[0],
			     symbol,first_symbol_flag,nb_rb,
Elena Lukashova's avatar
Elena Lukashova committed
857
			     adjust_G2(frame_parms,dlsch0_harq->rb_alloc_even,6,subframe,symbol),
858
			     lte_ue_pdsch_vars[eNB_id]->llr128);
859
860
861
862
863
864
865
866
	if (rx_type==rx_IC_dual_stream) {
	  dlsch_qpsk_64qam_llr(frame_parms,
			       rxdataF_comp_ptr,
			       lte_ue_pdsch_vars[eNB_id]->rxdataF_comp0,//i
			       lte_ue_pdsch_vars[eNB_id]->dl_ch_mag0,
			       lte_ue_pdsch_vars[eNB_id]->dl_ch_rho2_ext,
			       lte_ue_pdsch_vars[eNB_id]->llr[1],
			       symbol,first_symbol_flag,nb_rb,
Elena Lukashova's avatar
Elena Lukashova committed
867
			       adjust_G2(frame_parms,dlsch1_harq->rb_alloc_even,2,subframe,symbol),
868
869
870
			       lte_ue_pdsch_vars[eNB_id]->llr128_2ndstream);
	}
      }
Elena Lukashova's avatar
Elena Lukashova committed
871
      else if (dlsch1_harq->Qm == 4) {
872
873
874
875
876
877
878
879
	dlsch_64qam_16qam_llr(frame_parms,
			      lte_ue_pdsch_vars[eNB_id]->rxdataF_comp0,
			      rxdataF_comp_ptr,//i
			      lte_ue_pdsch_vars[eNB_id]->dl_ch_mag0,
			      dl_ch_mag_ptr,//i
			      lte_ue_pdsch_vars[eNB_id]->dl_ch_rho_ext[harq_pid][round],
			      lte_ue_pdsch_vars[eNB_id]->llr[0],
			      symbol,first_symbol_flag,nb_rb,
Elena Lukashova's avatar
Elena Lukashova committed
880
			      adjust_G2(frame_parms,dlsch0_harq->rb_alloc_even,6,subframe,symbol),
881
882
883
884
885
886
887
888
889
890
			      lte_ue_pdsch_vars[eNB_id]->llr128);
	if (rx_type==rx_IC_dual_stream) {
	  dlsch_16qam_64qam_llr(frame_parms,
				rxdataF_comp_ptr,
				lte_ue_pdsch_vars[eNB_id]->rxdataF_comp0,//i
				dl_ch_mag_ptr,
				lte_ue_pdsch_vars[eNB_id]->dl_ch_mag0,//i
				lte_ue_pdsch_vars[eNB_id]->dl_ch_rho2_ext,
				lte_ue_pdsch_vars[eNB_id]->llr[1],
				symbol,first_symbol_flag,nb_rb,
Elena Lukashova's avatar
Elena Lukashova committed
891
				adjust_G2(frame_parms,dlsch1_harq->rb_alloc_even,4,subframe,symbol),
892
893
894
895
896
897
898
899
900
901
902
903
				lte_ue_pdsch_vars[eNB_id]->llr128_2ndstream);
	}
      }
      else {	  
	dlsch_64qam_64qam_llr(frame_parms,
			      lte_ue_pdsch_vars[eNB_id]->rxdataF_comp0,
			      rxdataF_comp_ptr,//i
			      lte_ue_pdsch_vars[eNB_id]->dl_ch_mag0,
			      dl_ch_mag_ptr,//i
			      lte_ue_pdsch_vars[eNB_id]->dl_ch_rho_ext[harq_pid][round],
			      lte_ue_pdsch_vars[eNB_id]->llr[0],
			      symbol,first_symbol_flag,nb_rb,
Elena Lukashova's avatar
Elena Lukashova committed
904
			      adjust_G2(frame_parms,dlsch0_harq->rb_alloc_even,6,subframe,symbol),
905
906
907
908
909
910
911
912
913
914
			      lte_ue_pdsch_vars[eNB_id]->llr128);
	if (rx_type==rx_IC_dual_stream) {
	  dlsch_64qam_64qam_llr(frame_parms,
				rxdataF_comp_ptr,
				lte_ue_pdsch_vars[eNB_id]->rxdataF_comp0,//i
				dl_ch_mag_ptr,
				lte_ue_pdsch_vars[eNB_id]->dl_ch_mag0,//i
				lte_ue_pdsch_vars[eNB_id]->dl_ch_rho2_ext,
				lte_ue_pdsch_vars[eNB_id]->llr[1],
				symbol,first_symbol_flag,nb_rb,
Elena Lukashova's avatar
Elena Lukashova committed
915
				adjust_G2(frame_parms,dlsch1_harq->rb_alloc_even,6,subframe,symbol),
916
917
918
				lte_ue_pdsch_vars[eNB_id]->llr128_2ndstream);
	}
      }
919

920
    }
Elena Lukashova's avatar
Elena Lukashova committed
921

922
    break;
923
924
925
926
927
928
929
930
931
932
933
934
935
  default:
    LOG_W(PHY,"rx_dlsch.c : Unknown mod_order!!!!\n");
    return(-1);
    break;
  }

  switch (get_Qm(dlsch1_harq->mcs)) {
  case 2 : 
    if (rx_type==rx_standard) {
        dlsch_qpsk_llr(frame_parms,
                       rxdataF_comp_ptr,
                       lte_ue_pdsch_vars[eNB_id]->llr[1],
                       symbol,first_symbol_flag,nb_rb,
Elena Lukashova's avatar
Elena Lukashova committed
936
                       adjust_G2(frame_parms,dlsch1_harq->rb_alloc_even,2,subframe,symbol),
937
                       lte_ue_pdsch_vars[eNB_id]->llr128_2ndstream);
938
    }
939
940
941
942
943
944
945
946
    break;
  case 4:
    if (rx_type==rx_standard) {
      dlsch_16qam_llr(frame_parms,
                      rxdataF_comp_ptr,
                      lte_ue_pdsch_vars[eNB_id]->llr[1],
                      lte_ue_pdsch_vars[eNB_id]->dl_ch_mag1,
                      symbol,first_symbol_flag,nb_rb,
Elena Lukashova's avatar
Elena Lukashova committed
947
                      adjust_G2(frame_parms,dlsch1_harq->rb_alloc_even,4,subframe,symbol),
948
                      lte_ue_pdsch_vars[eNB_id]->llr128_2ndstream);
949
    }
950

951
    break;
952

953
  case 6 :
954
    if (rx_type==rx_standard) {
955
      dlsch_64qam_llr(frame_parms,
956
957
958
959
960
                      rxdataF_comp_ptr,
                      lte_ue_pdsch_vars[eNB_id]->llr[1],
                      lte_ue_pdsch_vars[eNB_id]->dl_ch_mag1,
                      lte_ue_pdsch_vars[eNB_id]->dl_ch_magb1,
                      symbol,first_symbol_flag,nb_rb,
Elena Lukashova's avatar
Elena Lukashova committed
961
                      adjust_G2(frame_parms,dlsch1_harq->rb_alloc_even,6,subframe,symbol),
962
                      lte_ue_pdsch_vars[eNB_id]->llr128_2ndstream);
Elena Lukashova's avatar
Elena Lukashova committed
963
964
  }

965
    break;
Elena Lukashova's avatar
Elena Lukashova committed
966

967
  default:
jiangx's avatar
jiangx committed
968
    LOG_W(PHY,"rx_dlsch.c : Unknown mod_order!!!!\n");
969
    return(-1);
970
    break;
Elena Lukashova's avatar
Elena Lukashova committed
971
  } 
972
  return(0);    
973

974
975
976
977
978
979
980
981
982
983
984
985
986
987
}

//==============================================================================================
// Pre-processing for LLR computation
//==============================================================================================

void dlsch_channel_compensation(int **rxdataF_ext,
                                int **dl_ch_estimates_ext,
                                int **dl_ch_mag,
                                int **dl_ch_magb,
                                int **rxdataF_comp,
                                int **rho,
                                LTE_DL_FRAME_PARMS *frame_parms,
                                unsigned char symbol,
gauthier's avatar
gauthier committed
988
                                uint8_t first_symbol_flag,
989
990
991
992
993
994
995
996
                                unsigned char mod_order,
                                unsigned short nb_rb,
                                unsigned char output_shift,
                                PHY_MEASUREMENTS *phy_measurements) {

  unsigned short rb;
  unsigned char aatx,aarx,symbol_mod,pilots=0;
  __m128i *dl_ch128,*dl_ch128_2,*dl_ch_mag128,*dl_ch_mag128b,*rxdataF128,*rxdataF_comp128,*rho128;
997
  __m128i mmtmpD0,mmtmpD1,mmtmpD2,mmtmpD3,QAM_amp128,QAM_amp128b;
998
999
1000

  symbol_mod = (symbol>=(7-frame_parms->Ncp)) ? symbol-(7-frame_parms->Ncp) : symbol;

For faster browsing, not all history is shown. View entire blame