lte-softmodem.c 40.8 KB
Newer Older
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21
/*
 * Licensed to the OpenAirInterface (OAI) Software Alliance under one or more
 * contributor license agreements.  See the NOTICE file distributed with
 * this work for additional information regarding copyright ownership.
 * The OpenAirInterface Software Alliance licenses this file to You under
 * the OAI Public License, Version 1.0  (the "License"); you may not use this file
 * except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *      http://www.openairinterface.org/?page_id=698
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 *-------------------------------------------------------------------------------
 * For more information about the OpenAirInterface (OAI) Software Alliance:
 *      contact@openairinterface.org
 */

22 23
/*! \file lte-enb.c
 * \brief Top-level threads for eNodeB
24
 * \author R. Knopp, F. Kaltenberger, Navid Nikaein
knopp's avatar
knopp committed
25 26 27
 * \date 2012
 * \version 0.1
 * \company Eurecom
28
 * \email: knopp@eurecom.fr,florian.kaltenberger@eurecom.fr, navid.nikaein@eurecom.fr
knopp's avatar
knopp committed
29 30 31
 * \note
 * \warning
 */
32

33

Cedric Roux's avatar
Cedric Roux committed
34 35 36
#define _GNU_SOURCE             /* See feature_test_macros(7) */
#include <sched.h>

37

38 39
#include "T.h"

40
#include "rt_wrapper.h"
41

42

43 44
#undef MALLOC //there are two conflicting definitions, so we better make sure we don't use it at all

45
#include "assertions.h"
46
#include "msc.h"
47 48

#include "PHY/types.h"
49

50
#include "PHY/defs.h"
51
#include "common/ran_context.h"
52
#include "common/config/config_userapi.h"
53

54
#undef MALLOC //there are two conflicting definitions, so we better make sure we don't use it at all
knopp's avatar
knopp committed
55
//#undef FRAME_LENGTH_COMPLEX_SAMPLES //there are two conflicting definitions, so we better make sure we don't use it at all
56

knopp's avatar
knopp committed
57
#include "../../ARCH/COMMON/common_lib.h"
58
#include "../../ARCH/ETHERNET/USERSPACE/LIB/if_defs.h"
knopp's avatar
knopp committed
59

knopp's avatar
knopp committed
60
//#undef FRAME_LENGTH_COMPLEX_SAMPLES //there are two conflicting definitions, so we better make sure we don't use it at all
61 62 63 64 65 66 67 68 69

#include "PHY/vars.h"
#include "SCHED/vars.h"
#include "LAYER2/MAC/vars.h"

#include "../../SIMU/USER/init_lte.h"

#include "LAYER2/MAC/defs.h"
#include "LAYER2/MAC/vars.h"
70
#include "LAYER2/MAC/proto.h"
71 72 73 74 75 76 77 78
#include "RRC/LITE/vars.h"
#include "PHY_INTERFACE/vars.h"

#ifdef SMBV
#include "PHY/TOOLS/smbv.h"
unsigned short config_frames[4] = {2,9,11,13};
#endif
#include "UTIL/LOG/log_extern.h"
nikaeinn's avatar
nikaeinn committed
79
#include "UTIL/OTG/otg_tx.h"
80
#include "UTIL/OTG/otg_externs.h"
81 82
#include "UTIL/MATH/oml.h"
#include "UTIL/LOG/vcd_signal_dumper.h"
83
#include "UTIL/OPT/opt.h"
84
#include "enb_config.h"
nikaeinn's avatar
nikaeinn committed
85
//#include "PHY/TOOLS/time_meas.h"
86

Florian Kaltenberger's avatar
Florian Kaltenberger committed
87 88 89 90
#ifndef OPENAIR2
#include "UTIL/OTG/otg_vars.h"
#endif

91
#if defined(ENABLE_ITTI)
92 93
#include "intertask_interface_init.h"
#include "create_tasks.h"
94 95
#endif

96 97
#include "system.h"

98 99 100
#ifdef XFORMS
#include "PHY/TOOLS/lte_phy_scope.h"
#include "stats.h"
101
#endif
102
#include "lte-softmodem.h"
103

104

105
#ifdef XFORMS
106
// current status is that every UE has a DL scope for a SINGLE eNB (eNB_id=0)
107
// at eNB 0, an UL scope for every UE
108
FD_lte_phy_scope_ue  *form_ue[NUMBER_OF_UE_MAX];
109
FD_lte_phy_scope_enb *form_enb[MAX_NUM_CCs][NUMBER_OF_UE_MAX];
110
FD_stats_form                  *form_stats=NULL,*form_stats_l2=NULL;
111
char title[255];
112
unsigned char                   scope_enb_num_ue = 2;
113
static pthread_t                forms_thread; //xforms
114 115
#endif //XFORMS

knopp's avatar
knopp committed
116 117
pthread_cond_t sync_cond;
pthread_mutex_t sync_mutex;
118
int sync_var=-1; //!< protected by mutex \ref sync_mutex.
119

120 121
uint16_t runtime_phy_rx[29][6]; // SISO [MCS 0-28][RBs 0-5 : 6, 15, 25, 50, 75, 100]
uint16_t runtime_phy_tx[29][6]; // SISO [MCS 0-28][RBs 0-5 : 6, 15, 25, 50, 75, 100]
knopp's avatar
knopp committed
122

123
#if defined(ENABLE_ITTI)
124 125
volatile int             start_eNB = 0;
volatile int             start_UE = 0;
126
#endif
knopp's avatar
knopp committed
127
volatile int             oai_exit = 0;
128

129
static clock_source_t clock_source = internal;
130
static int wait_for_sync = 0;
knopp's avatar
knopp committed
131

knopp's avatar
knopp committed
132
static char              UE_flag=0;
133
unsigned int                    mmapped_dma=0;
134
int                             single_thread_flag=1;
135

136
static char                     threequarter_fs=0;
137

138
uint32_t                 downlink_frequency[MAX_NUM_CCs][4];
139
int32_t                  uplink_frequency_offset[MAX_NUM_CCs][4];
gauthier's avatar
gauthier committed
140

141

142

143
#if defined(ENABLE_ITTI)
144
static char                    *itti_dump_file = NULL;
knopp's avatar
knopp committed
145 146
#endif

147
int UE_scan = 1;
148
int UE_scan_carrier = 0;
149 150
runmode_t mode = normal_txrx;

151 152
FILE *input_fd=NULL;

153

154 155
#if MAX_NUM_CCs == 1
rx_gain_t                rx_gain_mode[MAX_NUM_CCs][4] = {{max_gain,max_gain,max_gain,max_gain}};
156 157
double tx_gain[MAX_NUM_CCs][4] = {{20,0,0,0}};
double rx_gain[MAX_NUM_CCs][4] = {{110,0,0,0}};
158 159 160 161
#else
rx_gain_t                rx_gain_mode[MAX_NUM_CCs][4] = {{max_gain,max_gain,max_gain,max_gain},{max_gain,max_gain,max_gain,max_gain}};
double tx_gain[MAX_NUM_CCs][4] = {{20,0,0,0},{20,0,0,0}};
double rx_gain[MAX_NUM_CCs][4] = {{110,0,0,0},{20,0,0,0}};
gauthier's avatar
gauthier committed
162
#endif
knopp's avatar
knopp committed
163

164
double rx_gain_off = 0.0;
165

knopp's avatar
knopp committed
166
double sample_rate=30.72e6;
167
double bw = 10.0e6;
168

169
static int                      tx_max_power[MAX_NUM_CCs]; /* =  {0,0}*/;
170

171 172
char   rf_config_file[1024];

Florian Kaltenberger's avatar
Florian Kaltenberger committed
173
int chain_offset=0;
174
int phy_test = 0;
175
uint8_t usim_test = 0;
Florian Kaltenberger's avatar
Florian Kaltenberger committed
176

177 178 179
uint8_t dci_Format = 0;
uint8_t agregation_Level =0xFF;

180 181
uint8_t nb_antenna_tx = 1;
uint8_t nb_antenna_rx = 1;
182

knopp's avatar
knopp committed
183 184 185
char ref[128] = "internal";
char channels[128] = "0";

186
int                      rx_input_level_dBm;
187
static int                      online_log_messages=0;
188
#ifdef XFORMS
189
extern int                      otg_enabled;
190
static char                     do_forms=0;
191
#else
192
int                             otg_enabled;
193
#endif
knopp's avatar
knopp committed
194
//int                             number_of_cards =   1;
195

196 197

static LTE_DL_FRAME_PARMS      *frame_parms[MAX_NUM_CCs];
Florian Kaltenberger's avatar
Florian Kaltenberger committed
198
uint32_t target_dl_mcs = 28; //maximum allowed mcs
199
uint32_t target_ul_mcs = 20;
200
uint32_t timing_advance = 0;
201 202
uint8_t exit_missed_slots=1;
uint64_t num_missed_slots=0; // counter for the number of missed slots
203

204

205 206
extern void reset_opp_meas(void);
extern void print_opp_meas(void);
207

208
int transmission_mode=1;
knopp's avatar
knopp committed
209

210
int16_t           glog_level         = LOG_INFO;
gauthier's avatar
gauthier committed
211
int16_t           glog_verbosity     = LOG_MED;
212
int16_t           hw_log_level       = LOG_INFO;
gauthier's avatar
gauthier committed
213
int16_t           hw_log_verbosity   = LOG_MED;
214
int16_t           phy_log_level      = LOG_DEBUG;
gauthier's avatar
gauthier committed
215
int16_t           phy_log_verbosity  = LOG_MED;
216
int16_t           mac_log_level      = LOG_DEBUG;
gauthier's avatar
gauthier committed
217
int16_t           mac_log_verbosity  = LOG_MED;
218
int16_t           rlc_log_level      = LOG_INFO;
gauthier's avatar
gauthier committed
219
int16_t           rlc_log_verbosity  = LOG_MED;
220
int16_t           pdcp_log_level     = LOG_INFO;
gauthier's avatar
gauthier committed
221
int16_t           pdcp_log_verbosity = LOG_MED;
222
int16_t           rrc_log_level      = LOG_INFO;
gauthier's avatar
gauthier committed
223
int16_t           rrc_log_verbosity  = LOG_MED;
224 225 226
int16_t           opt_log_level      = LOG_INFO;
int16_t           opt_log_verbosity  = LOG_MED;

gauthier's avatar
gauthier committed
227 228 229 230 231 232
# if defined(ENABLE_USE_MME)
int16_t           gtpu_log_level     = LOG_DEBUG;
int16_t           gtpu_log_verbosity = LOG_MED;
int16_t           udp_log_level      = LOG_DEBUG;
int16_t           udp_log_verbosity  = LOG_MED;
#endif
233 234 235
#if defined (ENABLE_SECURITY)
int16_t           osa_log_level      = LOG_INFO;
int16_t           osa_log_verbosity  = LOG_MED;
236
#endif
237

238 239 240
/* struct for ethernet specific parameters given in eNB conf file */
eth_params_t *eth_params;

241 242 243 244
openair0_config_t openair0_cfg[MAX_CARDS];

double cpuf;

245 246
extern char uecap_xer[1024];
char uecap_xer_in=0;
247

248
int oaisim_flag=0;
249
threads_t threads= {-1,-1,-1,-1,-1,-1,-1};
knopp's avatar
knopp committed
250

Cedric Roux's avatar
Cedric Roux committed
251 252 253 254
/* see file openair2/LAYER2/MAC/main.c for why abstraction_flag is needed
 * this is very hackish - find a proper solution
 */
uint8_t abstraction_flag=0;
knopp's avatar
knopp committed
255

256 257 258 259 260
/*---------------------BMC: timespec helpers -----------------------------*/

struct timespec min_diff_time = { .tv_sec = 0, .tv_nsec = 0 };
struct timespec max_diff_time = { .tv_sec = 0, .tv_nsec = 0 };

261
struct timespec clock_difftime(struct timespec start, struct timespec end) {
262 263 264 265 266 267 268 269 270
  struct timespec temp;
  if ((end.tv_nsec-start.tv_nsec)<0) {
    temp.tv_sec = end.tv_sec-start.tv_sec-1;
    temp.tv_nsec = 1000000000+end.tv_nsec-start.tv_nsec;
  } else {
    temp.tv_sec = end.tv_sec-start.tv_sec;
    temp.tv_nsec = end.tv_nsec-start.tv_nsec;
  }
  return temp;
271 272
}

273
void print_difftimes(void) {
274
#ifdef DEBUG
275
  printf("difftimes min = %lu ns ; max = %lu ns\n", min_diff_time.tv_nsec, max_diff_time.tv_nsec);
276
#else
277
  LOG_I(HW,"difftimes min = %lu ns ; max = %lu ns\n", min_diff_time.tv_nsec, max_diff_time.tv_nsec);
278 279 280
#endif
}

281
void update_difftimes(struct timespec start, struct timespec end) {
282 283 284
  struct timespec diff_time = { .tv_sec = 0, .tv_nsec = 0 };
  int             changed = 0;
  diff_time = clock_difftime(start, end);
285 286 287 288 289 290 291 292
  if ((min_diff_time.tv_nsec == 0) || (diff_time.tv_nsec < min_diff_time.tv_nsec)) {
    min_diff_time.tv_nsec = diff_time.tv_nsec;
    changed = 1;
  }
  if ((max_diff_time.tv_nsec == 0) || (diff_time.tv_nsec > max_diff_time.tv_nsec)) {
    max_diff_time.tv_nsec = diff_time.tv_nsec;
    changed = 1;
  }
293
#if 1
294
  if (changed) print_difftimes();
295 296 297 298 299
#endif
}

/*------------------------------------------------------------------------*/

300
unsigned int build_rflocal(int txi, int txq, int rxi, int rxq) {
knopp's avatar
knopp committed
301
  return (txi + (txq<<6) + (rxi<<12) + (rxq<<18));
302
}
303
unsigned int build_rfdc(int dcoff_i_rxfe, int dcoff_q_rxfe) {
knopp's avatar
knopp committed
304
  return (dcoff_i_rxfe + (dcoff_q_rxfe<<8));
305 306
}

307
#if !defined(ENABLE_ITTI)
308
void signal_handler(int sig) {
309 310 311 312 313 314
  void *array[10];
  size_t size;

  if (sig==SIGSEGV) {
    // get void*'s for all entries on the stack
    size = backtrace(array, 10);
315

316 317 318 319
    // print out all the frames to stderr
    fprintf(stderr, "Error: signal %d:\n", sig);
    backtrace_symbols_fd(array, size, 2);
    exit(-1);
320 321
  } else {
    printf("trying to exit gracefully...\n");
322
    oai_exit = 1;
323 324
  }
}
325
#endif
326 327 328 329 330 331
#define KNRM  "\x1B[0m"
#define KRED  "\x1B[31m"
#define KGRN  "\x1B[32m"
#define KBLU  "\x1B[34m"
#define RESET "\033[0m"

332

Raymond Knopp's avatar
Raymond Knopp committed
333

334 335
void exit_fun(const char* s)
{
Raymond Knopp's avatar
Raymond Knopp committed
336
  int CC_id;
337
  int ru_id;
Raymond Knopp's avatar
Raymond Knopp committed
338

339
  if (s != NULL) {
340
    printf("%s %s() Exiting OAI softmodem: %s\n",__FILE__, __FUNCTION__, s);
341 342 343
  }

  oai_exit = 1;
344 345 346 347 348 349 350 351 352 353

  if (UE_flag==0) {
    for (ru_id=0; ru_id<RC.nb_RU;ru_id++) {
      if (RC.ru[ru_id]->rfdevice.trx_end_func)
	RC.ru[ru_id]->rfdevice.trx_end_func(&RC.ru[ru_id]->rfdevice);
      if (RC.ru[ru_id]->ifdevice.trx_end_func)
	RC.ru[ru_id]->ifdevice.trx_end_func(&RC.ru[ru_id]->ifdevice);  
    }
  }

Raymond Knopp's avatar
Raymond Knopp committed
354
  for(CC_id=0; CC_id<MAX_NUM_CCs; CC_id++) {
355 356 357 358

    oai_exit = 1;

    for(CC_id=0; CC_id<MAX_NUM_CCs; CC_id++) {
359 360 361 362 363
      if (UE_flag == 0) {
      } else {
	if (PHY_vars_UE_g[0][CC_id]->rfdevice.trx_end_func)
	  PHY_vars_UE_g[0][CC_id]->rfdevice.trx_end_func(&PHY_vars_UE_g[0][CC_id]->rfdevice);
      }
knopp's avatar
knopp committed
364
    }
365 366

#if defined(ENABLE_ITTI)
367 368
    sleep(1); //allow lte-softmodem threads to exit first
    itti_terminate_tasks (TASK_UNKNOWN);
369
#endif
370

371
  }
372

373
}
374

375
#ifdef XFORMS
376

377

378 379
void reset_stats(FL_OBJECT *button, long arg)
{
380
  int i,j,k;
381
  PHY_VARS_eNB *phy_vars_eNB = RC.eNB[0][0];
382 383 384

  for (i=0; i<NUMBER_OF_UE_MAX; i++) {
    for (k=0; k<8; k++) { //harq_processes
385
      for (j=0; j<phy_vars_eNB->dlsch[i][0]->Mlimit; j++) {
386 387 388
	phy_vars_eNB->UE_stats[i].dlsch_NAK[k][j]=0;
	phy_vars_eNB->UE_stats[i].dlsch_ACK[k][j]=0;
	phy_vars_eNB->UE_stats[i].dlsch_trials[k][j]=0;
389
      }
390

391 392 393
      phy_vars_eNB->UE_stats[i].dlsch_l2_errors[k]=0;
      phy_vars_eNB->UE_stats[i].ulsch_errors[k]=0;
      phy_vars_eNB->UE_stats[i].ulsch_consecutive_errors=0;
394 395


396 397 398
      phy_vars_eNB->UE_stats[i].dlsch_sliding_cnt=0;
      phy_vars_eNB->UE_stats[i].dlsch_NAK_round0=0;
      phy_vars_eNB->UE_stats[i].dlsch_mcs_offset=0;
399 400 401 402
    }
  }
}

403
static void *scope_thread(void *arg) {
knopp's avatar
knopp committed
404
  char stats_buffer[16384];
405
# ifdef ENABLE_XFORMS_WRITE_STATS
knopp's avatar
knopp committed
406
  FILE *UE_stats, *eNB_stats;
407
# endif
knopp's avatar
knopp committed
408
  struct sched_param sched_param;
409
  int UE_id, CC_id;
410
  int ue_cnt=0;
411

412
  sched_param.sched_priority = sched_get_priority_min(SCHED_FIFO)+1;
knopp's avatar
knopp committed
413
  sched_setscheduler(0, SCHED_FIFO,&sched_param);
414

knopp's avatar
knopp committed
415
  printf("Scope thread has priority %d\n",sched_param.sched_priority);
416

417
# ifdef ENABLE_XFORMS_WRITE_STATS
418 419

  if (UE_flag==1)
knopp's avatar
knopp committed
420
    UE_stats  = fopen("UE_stats.txt", "w");
421
  else
knopp's avatar
knopp committed
422
    eNB_stats = fopen("eNB_stats.txt", "w");
423

424
#endif
425

knopp's avatar
knopp committed
426 427
  while (!oai_exit) {
    if (UE_flag==1) {
428
      dump_ue_stats (PHY_vars_UE_g[0][0], &PHY_vars_UE_g[0][0]->proc.proc_rxtx[0],stats_buffer, 0, mode,rx_input_level_dBm);
knopp's avatar
knopp committed
429 430 431
      //fl_set_object_label(form_stats->stats_text, stats_buffer);
      fl_clear_browser(form_stats->stats_text);
      fl_add_browser_line(form_stats->stats_text, stats_buffer);
432

433
      phy_scope_UE(form_ue[0],
434 435 436 437
		   PHY_vars_UE_g[0][0],
		   0,
		   0,7);

438

knopp's avatar
knopp committed
439
    } else {
440
      /*
441
	if (RC.eNB[0][0]->mac_enabled==1) {
442 443 444 445
	len = dump_eNB_l2_stats (stats_buffer, 0);
	//fl_set_object_label(form_stats_l2->stats_text, stats_buffer);
	fl_clear_browser(form_stats_l2->stats_text);
	fl_add_browser_line(form_stats_l2->stats_text, stats_buffer);
446 447
	}
	len = dump_eNB_stats (RC.eNB[0][0], stats_buffer, 0);
448

449 450
	if (MAX_NUM_CCs>1)
	len += dump_eNB_stats (RC.eNB[0][1], &stats_buffer[len], 0);
451

452 453 454
	//fl_set_object_label(form_stats->stats_text, stats_buffer);
	fl_clear_browser(form_stats->stats_text);
	fl_add_browser_line(form_stats->stats_text, stats_buffer);
455
      */
456 457
      ue_cnt=0;
      for(UE_id=0; UE_id<NUMBER_OF_UE_MAX; UE_id++) {
458
	for(CC_id=0; CC_id<MAX_NUM_CCs; CC_id++) {
459
	  //	  if ((RC.eNB[0][CC_id]->dlsch[UE_id][0]->rnti>0) && (ue_cnt<scope_enb_num_ue)) {
460
	  if ((ue_cnt<scope_enb_num_ue)) {
gauthier's avatar
gauthier committed
461
	    phy_scope_eNB(form_enb[CC_id][ue_cnt],
462
			  RC.eNB[0][CC_id],
463 464 465
			  UE_id);
	    ue_cnt++;
	  }
466
	}
knopp's avatar
knopp committed
467
      }
468

469
    }
470
	
knopp's avatar
knopp committed
471
    //printf("doing forms\n");
Florian Kaltenberger's avatar
Florian Kaltenberger committed
472 473
    //usleep(100000); // 100 ms
    sleep(1);
knopp's avatar
knopp committed
474
  }
475

476
  //  printf("%s",stats_buffer);
477

478
# ifdef ENABLE_XFORMS_WRITE_STATS
479

480 481 482 483 484 485
  if (UE_flag==1) {
    if (UE_stats) {
      rewind (UE_stats);
      fwrite (stats_buffer, 1, len, UE_stats);
      fclose (UE_stats);
    }
486
  } else {
487 488 489 490 491 492
    if (eNB_stats) {
      rewind (eNB_stats);
      fwrite (stats_buffer, 1, len, eNB_stats);
      fclose (eNB_stats);
    }
  }
493

494
# endif
495

knopp's avatar
knopp committed
496
  pthread_exit((void*)arg);
497 498 499
}
#endif

500

501

502

knopp's avatar
knopp committed
503
#if defined(ENABLE_ITTI)
504
void *l2l1_task(void *arg) {
knopp's avatar
knopp committed
505 506 507 508 509
  MessageDef *message_p = NULL;
  int         result;

  itti_set_task_real_time(TASK_L2L1);
  itti_mark_task_ready(TASK_L2L1);
510

knopp's avatar
knopp committed
511 512
  if (UE_flag == 0) {
    /* Wait for the initialize message */
513
    printf("Wait for the ITTI initialize message\n");
514
    do {
knopp's avatar
knopp committed
515
      if (message_p != NULL) {
516 517
	result = itti_free (ITTI_MSG_ORIGIN_ID(message_p), message_p);
	AssertFatal (result == EXIT_SUCCESS, "Failed to free memory (%d)!\n", result);
knopp's avatar
knopp committed
518
      }
519

520 521 522
      itti_receive_msg (TASK_L2L1, &message_p);

      switch (ITTI_MSG_ID(message_p)) {
knopp's avatar
knopp committed
523
      case INITIALIZE_MESSAGE:
524 525 526 527
	/* Start eNB thread */
	LOG_D(EMU, "L2L1 TASK received %s\n", ITTI_MSG_NAME(message_p));
	start_eNB = 1;
	break;
knopp's avatar
knopp committed
528 529

      case TERMINATE_MESSAGE:
530 531 532 533
	printf("received terminate message\n");
	oai_exit=1;
	itti_exit_task ();
	break;
knopp's avatar
knopp committed
534 535

      default:
536 537
	LOG_E(EMU, "Received unexpected message %s\n", ITTI_MSG_NAME(message_p));
	break;
538
      }
knopp's avatar
knopp committed
539
    } while (ITTI_MSG_ID(message_p) != INITIALIZE_MESSAGE);
540

knopp's avatar
knopp committed
541 542 543 544 545 546 547 548 549 550 551 552 553 554 555 556 557 558 559 560 561
    result = itti_free (ITTI_MSG_ORIGIN_ID(message_p), message_p);
    AssertFatal (result == EXIT_SUCCESS, "Failed to free memory (%d)!\n", result);
  }

  do {
    // Wait for a message
    itti_receive_msg (TASK_L2L1, &message_p);

    switch (ITTI_MSG_ID(message_p)) {
    case TERMINATE_MESSAGE:
      oai_exit=1;
      itti_exit_task ();
      break;

    case ACTIVATE_MESSAGE:
      start_UE = 1;
      break;

    case DEACTIVATE_MESSAGE:
      start_UE = 0;
      break;
562

knopp's avatar
knopp committed
563 564 565 566 567 568 569 570 571 572 573
    case MESSAGE_TEST:
      LOG_I(EMU, "Received %s\n", ITTI_MSG_NAME(message_p));
      break;

    default:
      LOG_E(EMU, "Received unexpected message %s\n", ITTI_MSG_NAME(message_p));
      break;
    }

    result = itti_free (ITTI_MSG_ORIGIN_ID(message_p), message_p);
    AssertFatal (result == EXIT_SUCCESS, "Failed to free memory (%d)!\n", result);
574
  } while(!oai_exit);
575

knopp's avatar
knopp committed
576
  return NULL;
577 578 579
}
#endif

580

581 582 583 584 585 586 587 588 589 590 591 592 593 594 595 596 597 598 599 600 601 602
static void get_options(void) {
  int CC_id;
  int tddflag;
  char *loopfile=NULL;
  int dumpframe;
  paramdef_t cmdline_params[] =CMDLINE_PARAMS_DESC ;

  config_process_cmdline( cmdline_params,sizeof(cmdline_params)/sizeof(paramdef_t),NULL); 

  if (strlen(in_path) > 0) {
      opt_type = OPT_PCAP;
      opt_enabled=1;
      printf("Enabling OPT for PCAP  with the following file %s \n",in_path);
  }
  if (strlen(in_ip) > 0) {
      opt_enabled=1;
      opt_type = OPT_WIRESHARK;
      printf("Enabling OPT for wireshark for local interface");
  }
  if (UE_flag > 0) {
     paramdef_t cmdline_uemodeparams[] =CMDLINE_UEMODEPARAMS_DESC;
     paramdef_t cmdline_ueparams[] =CMDLINE_UEPARAMS_DESC;
oai's avatar
oai committed
603 604 605



606 607 608 609 610 611 612 613 614 615 616 617 618 619 620 621 622 623 624 625 626 627 628 629 630 631
     config_process_cmdline( cmdline_uemodeparams,sizeof(cmdline_uemodeparams)/sizeof(paramdef_t),NULL);
     config_process_cmdline( cmdline_ueparams,sizeof(cmdline_ueparams)/sizeof(paramdef_t),NULL);
      if (loopfile != NULL) {
  	  printf("Input file for hardware emulation: %s",loopfile);
  	  mode=loop_through_memory;
  	  input_fd = fopen(loopfile,"r");
  	  AssertFatal(input_fd != NULL,"Please provide a valid input file\n");
      }
      if ( (cmdline_uemodeparams[CMDLINE_CALIBUERX_IDX].paramflags &  PARAMFLAG_PARAMSET) != 0) mode = rx_calib_ue;
      if ( (cmdline_uemodeparams[CMDLINE_CALIBUERXMED_IDX].paramflags &  PARAMFLAG_PARAMSET) != 0) mode = rx_calib_ue_med;
      if ( (cmdline_uemodeparams[CMDLINE_CALIBUERXBYP_IDX].paramflags &  PARAMFLAG_PARAMSET) != 0) mode = rx_calib_ue_byp;
      if ( *(cmdline_uemodeparams[CMDLINE_DEBUGUEPRACH_IDX].uptr) > 0) mode = debug_prach;
      if ( *(cmdline_uemodeparams[CMDLINE_NOL2CONNECT_IDX].uptr) > 0)  mode = no_L2_connect;
      if ( *(cmdline_uemodeparams[CMDLINE_CALIBPRACHTX_IDX].uptr) > 0) mode = calib_prach_tx; 
      if (dumpframe  > 0)  mode = rx_dump_frame;
      
      if ( downlink_frequency[0][0] > 0) {
  	  for (CC_id=1; CC_id<MAX_NUM_CCs; CC_id++) {
  	    downlink_frequency[CC_id][1] = downlink_frequency[0][0];
  	    downlink_frequency[CC_id][2] = downlink_frequency[0][0];
  	    downlink_frequency[CC_id][3] = downlink_frequency[0][0];
  	    printf("Downlink for CC_id %d frequency set to %u\n", CC_id, downlink_frequency[CC_id][0]);
  	  }
      UE_scan=0;
      } 

oai's avatar
oai committed
632 633 634 635
      if (tddflag > 0) {
         for (CC_id=0; CC_id<MAX_NUM_CCs; CC_id++) 
	     frame_parms[CC_id]->frame_type = TDD;
      }
636 637 638 639 640 641 642 643 644 645 646 647 648 649 650 651 652 653 654 655 656 657 658 659 660 661 662 663 664 665 666 667 668 669 670 671 672 673

      if (frame_parms[0]->N_RB_DL !=0) {
  	  if ( frame_parms[0]->N_RB_DL < 6 ) {
  	     frame_parms[0]->N_RB_DL = 6;
  	     printf ( "%i: Invalid number of ressource blocks, adjusted to 6\n",frame_parms[0]->N_RB_DL);
  	  }
  	  if ( frame_parms[0]->N_RB_DL > 100 ) {
  	     frame_parms[0]->N_RB_DL = 100;
  	     printf ( "%i: Invalid number of ressource blocks, adjusted to 100\n",frame_parms[0]->N_RB_DL);
  	  }
  	  if ( frame_parms[0]->N_RB_DL > 50 && frame_parms[0]->N_RB_DL < 100 ) {
  	     frame_parms[0]->N_RB_DL = 50;
  	     printf ( "%i: Invalid number of ressource blocks, adjusted to 50\n",frame_parms[0]->N_RB_DL);
  	  }
  	  if ( frame_parms[0]->N_RB_DL > 25 && frame_parms[0]->N_RB_DL < 50 ) {
  	     frame_parms[0]->N_RB_DL = 25;
  	     printf ( "%i: Invalid number of ressource blocks, adjusted to 25\n",frame_parms[0]->N_RB_DL);
  	  }
  	  UE_scan = 0;
  	  frame_parms[0]->N_RB_UL=frame_parms[0]->N_RB_DL;
  	  for (CC_id=1; CC_id<MAX_NUM_CCs; CC_id++) {
  	      frame_parms[CC_id]->N_RB_DL=frame_parms[0]->N_RB_DL;
  	      frame_parms[CC_id]->N_RB_UL=frame_parms[0]->N_RB_UL;
  	  }
      }


      for (CC_id=1;CC_id<MAX_NUM_CCs;CC_id++) {
  	    tx_max_power[CC_id]=tx_max_power[0];
	    rx_gain[0][CC_id] = rx_gain[0][0];
	    tx_gain[0][CC_id] = tx_gain[0][0];
      }
  } /* UE_flag > 0 */
#if T_TRACER
  paramdef_t cmdline_ttraceparams[] =CMDLINE_TTRACEPARAMS_DESC ;
  config_process_cmdline( cmdline_ttraceparams,sizeof(cmdline_ttraceparams)/sizeof(paramdef_t),NULL);   
#endif

674 675 676 677
  if ( !(CONFIG_ISFLAGSET(CONFIG_ABORT)) ) {
    if (UE_flag == 0) {
      memset((void*)&RC,0,sizeof(RC));
      /* Read RC configuration file */
678
      RCConfig();
679 680 681
      NB_eNB_INST = RC.nb_inst;
      NB_RU	  = RC.nb_RU;
      printf("Configuration: nb_inst %d, nb_ru %d\n",NB_eNB_INST,NB_RU);
682
    }
683 684 685 686 687 688
  } else if (UE_flag == 1 && (CONFIG_GETCONFFILE != NULL)) {
    // Here the configuration file is the XER encoded UE capabilities
    // Read it in and store in asn1c data structures
    strcpy(uecap_xer,CONFIG_GETCONFFILE);
    uecap_xer_in=1;
  } /* UE with config file  */
689 690 691
}


692
  
693 694 695
#if T_TRACER
int T_wait = 1;       /* by default we wait for the tracer */
int T_port = 2021;    /* default port to listen to to wait for the tracer */
696
int T_dont_fork = 0;  /* default is to fork, see 'T_init' to understand */
697 698
#endif

699

knopp's avatar
knopp committed
700 701
void set_default_frame_parms(LTE_DL_FRAME_PARMS *frame_parms[MAX_NUM_CCs]);
void set_default_frame_parms(LTE_DL_FRAME_PARMS *frame_parms[MAX_NUM_CCs]) {
knopp's avatar
knopp committed
702 703 704 705 706 707 708 709 710 711 712 713 714 715 716

  int CC_id;

  for (CC_id=0; CC_id<MAX_NUM_CCs; CC_id++) {
    frame_parms[CC_id] = (LTE_DL_FRAME_PARMS*) malloc(sizeof(LTE_DL_FRAME_PARMS));
    /* Set some default values that may be overwritten while reading options */
    frame_parms[CC_id]->frame_type          = FDD;
    frame_parms[CC_id]->tdd_config          = 3;
    frame_parms[CC_id]->tdd_config_S        = 0;
    frame_parms[CC_id]->N_RB_DL             = 100;
    frame_parms[CC_id]->N_RB_UL             = 100;
    frame_parms[CC_id]->Ncp                 = NORMAL;
    frame_parms[CC_id]->Ncp_UL              = NORMAL;
    frame_parms[CC_id]->Nid_cell            = 0;
    frame_parms[CC_id]->num_MBSFN_config    = 0;
717
    frame_parms[CC_id]->nb_antenna_ports_eNB  = 1;
knopp's avatar
knopp committed
718 719 720 721 722 723 724 725 726 727 728 729 730 731 732 733 734 735 736 737 738 739 740 741 742 743 744 745 746
    frame_parms[CC_id]->nb_antennas_tx      = 1;
    frame_parms[CC_id]->nb_antennas_rx      = 1;

    frame_parms[CC_id]->nushift             = 0;

    frame_parms[CC_id]->phich_config_common.phich_resource = oneSixth;
    frame_parms[CC_id]->phich_config_common.phich_duration = normal;
    // UL RS Config
    frame_parms[CC_id]->pusch_config_common.ul_ReferenceSignalsPUSCH.cyclicShift = 0;//n_DMRS1 set to 0
    frame_parms[CC_id]->pusch_config_common.ul_ReferenceSignalsPUSCH.groupHoppingEnabled = 0;
    frame_parms[CC_id]->pusch_config_common.ul_ReferenceSignalsPUSCH.sequenceHoppingEnabled = 0;
    frame_parms[CC_id]->pusch_config_common.ul_ReferenceSignalsPUSCH.groupAssignmentPUSCH = 0;

    frame_parms[CC_id]->prach_config_common.rootSequenceIndex=22;
    frame_parms[CC_id]->prach_config_common.prach_ConfigInfo.zeroCorrelationZoneConfig=1;
    frame_parms[CC_id]->prach_config_common.prach_ConfigInfo.prach_ConfigIndex=0;
    frame_parms[CC_id]->prach_config_common.prach_ConfigInfo.highSpeedFlag=0;
    frame_parms[CC_id]->prach_config_common.prach_ConfigInfo.prach_FreqOffset=0;

    downlink_frequency[CC_id][0] = 2680000000; // Use float to avoid issue with frequency over 2^31.
    downlink_frequency[CC_id][1] = downlink_frequency[CC_id][0];
    downlink_frequency[CC_id][2] = downlink_frequency[CC_id][0];
    downlink_frequency[CC_id][3] = downlink_frequency[CC_id][0];
    //printf("Downlink for CC_id %d frequency set to %u\n", CC_id, downlink_frequency[CC_id][0]);

  }

}

knopp's avatar
knopp committed
747 748
void init_openair0(void);

knopp's avatar
knopp committed
749 750 751 752 753 754 755 756 757 758 759 760 761
void init_openair0() {

  int card;
  int i;

  for (card=0; card<MAX_CARDS; card++) {

    openair0_cfg[card].mmapped_dma=mmapped_dma;
    openair0_cfg[card].configFilename = NULL;

    if(frame_parms[0]->N_RB_DL == 100) {
      if (frame_parms[0]->threequarter_fs) {
	openair0_cfg[card].sample_rate=23.04e6;
762
	openair0_cfg[card].samples_per_frame = 230400;
knopp's avatar
knopp committed
763 764
	openair0_cfg[card].tx_bw = 10e6;
	openair0_cfg[card].rx_bw = 10e6;
765
      } else {
knopp's avatar
knopp committed
766
	openair0_cfg[card].sample_rate=30.72e6;
767
	openair0_cfg[card].samples_per_frame = 307200;
knopp's avatar
knopp committed
768 769 770 771 772 773 774 775 776 777 778 779 780 781 782 783 784 785 786 787 788 789 790 791 792 793 794 795 796
	openair0_cfg[card].tx_bw = 10e6;
	openair0_cfg[card].rx_bw = 10e6;
      }
    } else if(frame_parms[0]->N_RB_DL == 50) {
      openair0_cfg[card].sample_rate=15.36e6;
      openair0_cfg[card].samples_per_frame = 153600;
      openair0_cfg[card].tx_bw = 5e6;
      openair0_cfg[card].rx_bw = 5e6;
    } else if (frame_parms[0]->N_RB_DL == 25) {
      openair0_cfg[card].sample_rate=7.68e6;
      openair0_cfg[card].samples_per_frame = 76800;
      openair0_cfg[card].tx_bw = 2.5e6;
      openair0_cfg[card].rx_bw = 2.5e6;
    } else if (frame_parms[0]->N_RB_DL == 6) {
      openair0_cfg[card].sample_rate=1.92e6;
      openair0_cfg[card].samples_per_frame = 19200;
      openair0_cfg[card].tx_bw = 1.5e6;
      openair0_cfg[card].rx_bw = 1.5e6;
    }




    if (frame_parms[0]->frame_type==TDD)
      openair0_cfg[card].duplex_mode = duplex_mode_TDD;
    else //FDD
      openair0_cfg[card].duplex_mode = duplex_mode_FDD;

    printf("HW: Configuring card %d, nb_antennas_tx/rx %d/%d\n",card,
797 798
	   ((UE_flag==0) ? RC.eNB[0][0]->frame_parms.nb_antennas_tx : PHY_vars_UE_g[0][0]->frame_parms.nb_antennas_tx),
	   ((UE_flag==0) ? RC.eNB[0][0]->frame_parms.nb_antennas_rx : PHY_vars_UE_g[0][0]->frame_parms.nb_antennas_rx));
knopp's avatar
knopp committed
799 800 801
    openair0_cfg[card].Mod_id = 0;

    openair0_cfg[card].num_rb_dl=frame_parms[0]->N_RB_DL;
802

803
    openair0_cfg[card].clock_source = clock_source;
804

805

806 807
    openair0_cfg[card].tx_num_channels=min(2,((UE_flag==0) ? RC.eNB[0][0]->frame_parms.nb_antennas_tx : PHY_vars_UE_g[0][0]->frame_parms.nb_antennas_tx));
    openair0_cfg[card].rx_num_channels=min(2,((UE_flag==0) ? RC.eNB[0][0]->frame_parms.nb_antennas_rx : PHY_vars_UE_g[0][0]->frame_parms.nb_antennas_rx));
808

knopp's avatar
knopp committed
809
    for (i=0; i<4; i++) {
810

knopp's avatar
knopp committed
811 812 813 814
      if (i<openair0_cfg[card].tx_num_channels)
	openair0_cfg[card].tx_freq[i] = (UE_flag==0) ? downlink_frequency[0][i] : downlink_frequency[0][i]+uplink_frequency_offset[0][i];
      else
	openair0_cfg[card].tx_freq[i]=0.0;
815

knopp's avatar
knopp committed
816 817 818 819 820 821 822 823
      if (i<openair0_cfg[card].rx_num_channels)
	openair0_cfg[card].rx_freq[i] = (UE_flag==0) ? downlink_frequency[0][i] + uplink_frequency_offset[0][i] : downlink_frequency[0][i];
      else
	openair0_cfg[card].rx_freq[i]=0.0;

      openair0_cfg[card].autocal[i] = 1;
      openair0_cfg[card].tx_gain[i] = tx_gain[0][i];
      if (UE_flag == 0) {
824
	openair0_cfg[card].rx_gain[i] = RC.eNB[0][0]->rx_total_gain_dB;
knopp's avatar
knopp committed
825 826
      }
      else {
827
	openair0_cfg[card].rx_gain[i] = PHY_vars_UE_g[0][0]->rx_total_gain_dB - rx_gain_off;
knopp's avatar
knopp committed
828 829
      }

830
      openair0_cfg[card].configFilename = rf_config_file;
831
      printf("Card %d, channel %d, Setting tx_gain %f, rx_gain %f, tx_freq %f, rx_freq %f\n",
832 833 834 835
	     card,i, openair0_cfg[card].tx_gain[i],
	     openair0_cfg[card].rx_gain[i],
	     openair0_cfg[card].tx_freq[i],
	     openair0_cfg[card].rx_freq[i]);
836
    }
knopp's avatar
knopp committed
837
  }
knopp's avatar
knopp committed
838
}
839

840

841
void wait_RUs(void) {
842 843 844 845 846 847 848 849 850 851 852 853 854 855 856

  LOG_I(PHY,"Waiting for RUs to be configured ...\n");

  // wait for all RUs to be configured over fronthaul
  pthread_mutex_lock(&RC.ru_mutex);



  while (RC.ru_mask>0) {
    pthread_cond_wait(&RC.ru_cond,&RC.ru_mutex);
  }

  LOG_I(PHY,"RUs configured\n");
}

857
void wait_eNBs(void) {
858 859 860 861 862 863 864 865 866 867 868 869 870 871 872 873 874 875

  int i,j;
  int waiting=1;


  while (waiting==1) {
    printf("Waiting for eNB L1 instances to all get configured ... sleeping 500ms (nb_L1_inst %d)\n",RC.nb_L1_inst);
    usleep(500000);
    waiting=0;
    for (i=0;i<RC.nb_L1_inst;i++)
      for (j=0;j<RC.nb_L1_CC[i];j++)
	if (RC.eNB[i][j]->configured==0) {
	  waiting=1;
	  break;
	}
  }
  printf("eNB L1 are configured\n");
}
876

877 878
int main( int argc, char **argv )
{
879
  int i;
880
#if defined (XFORMS)
knopp's avatar
knopp committed
881
  void *status;
882
#endif
883

knopp's avatar
knopp committed
884
  int CC_id;
885
  int ru_id;
knopp's avatar
knopp committed
886
  uint8_t  abstraction_flag=0;
knopp's avatar
knopp committed
887
  uint8_t beta_ACK=0,beta_RI=0,beta_CQI=2;
888

knopp's avatar
knopp committed
889
#if defined (XFORMS)
890 891
  int ret;
#endif
892

893
  start_background_system();
894 895 896
  if ( load_configmodule(argc,argv) == NULL) {
    exit_fun("[SOFTMODEM] Error, configuration module init failed\n");
  } 
897

898
      
899 900 901 902 903
#ifdef DEBUG_CONSOLE
  setvbuf(stdout, NULL, _IONBF, 0);
  setvbuf(stderr, NULL, _IONBF, 0);
#endif

904 905 906
  PHY_VARS_UE *UE[MAX_NUM_CCs];

  mode = normal_txrx;
907
  memset(&openair0_cfg[0],0,sizeof(openair0_config_t)*MAX_CARDS);
908

909
  memset(tx_max_power,0,sizeof(int)*MAX_NUM_CCs);
910

knopp's avatar
knopp committed
911
  set_latency_target();
912 913


knopp's avatar
knopp committed
914
  // set default parameters
915
  if (UE_flag == 1) set_default_frame_parms(frame_parms);
916

917
  logInit();
knopp's avatar
knopp committed
918

919
  printf("Reading in command-line options\n");
920

921
  get_options (); 
922 923 924
  if (CONFIG_ISFLAGSET(CONFIG_ABORT)) {
      fprintf(stderr,"Getting configuration failed\n");
      exit(-1);
925
  }
knopp's avatar
knopp committed
926 927 928



929
#if T_TRACER
930
  T_init(T_port, T_wait, T_dont_fork);
931 932
#endif

933
  // initialize the log (see log.h for details)
934 935
  set_glog(glog_level, glog_verbosity);

936 937
  //randominit (0);
  set_taus_seed (0);
knopp's avatar
knopp committed
938

939 940
  if (UE_flag==1) {
    printf("configuring for UE\n");
941

942 943
    set_comp_log(HW,      LOG_DEBUG,  LOG_HIGH, 1);
    set_comp_log(PHY,     LOG_DEBUG,   LOG_HIGH, 1);
944
    set_comp_log(MAC,     LOG_INFO,   LOG_HIGH, 1);
945
    set_comp_log(RLC,     LOG_INFO,   LOG_HIGH | FLAG_THREAD, 1);
946 947 948
    set_comp_log(PDCP,    LOG_INFO,   LOG_HIGH, 1);
    set_comp_log(OTG,     LOG_INFO,   LOG_HIGH, 1);
    set_comp_log(RRC,     LOG_INFO,   LOG_HIGH, 1);
949
#if defined(ENABLE_ITTI)
950
    set_comp_log(EMU,     LOG_INFO,   LOG_MED, 1);
951
# if defined(ENABLE_USE_MME)
952
    set_comp_log(NAS,     LOG_INFO,   LOG_HIGH, 1);
953 954
# endif
#endif
955

956
  } else {
957
    printf("configuring for RAU/RRU\n");
958

959 960 961 962 963 964 965 966
    set_comp_log(HW,      hw_log_level, hw_log_verbosity, 1);
    set_comp_log(PHY,     phy_log_level,   phy_log_verbosity, 1);
    if (opt_enabled == 1 )
      set_comp_log(OPT,   opt_log_level,      opt_log_verbosity, 1);
    set_comp_log(MAC,     mac_log_level,  mac_log_verbosity, 1);
    set_comp_log(RLC,     rlc_log_level,   rlc_log_verbosity, 1);
    set_comp_log(PDCP,    pdcp_log_level,  pdcp_log_verbosity, 1);
    set_comp_log(RRC,     rrc_log_level,  rrc_log_verbosity, 1);
967
#if defined(ENABLE_ITTI)
968
    set_comp_log(EMU,     LOG_INFO,   LOG_MED, 1);
969
# if defined(ENABLE_USE_MME)
970 971 972 973
    set_comp_log(UDP_,    udp_log_level,   udp_log_verbosity, 1);
    set_comp_log(GTPU,    gtpu_log_level,   gtpu_log_verbosity, 1);
    set_comp_log(S1AP,    LOG_DEBUG,   LOG_HIGH, 1);
    set_comp_log(SCTP,    LOG_INFO,   LOG_HIGH, 1);
974
# endif
975
#if defined(ENABLE_SECURITY)
976
    set_comp_log(OSA,    osa_log_level,   osa_log_verbosity, 1);
977
#endif
978
#endif
979
#ifdef LOCALIZATION
980 981 982 983 984 985 986 987 988
    set_comp_log(LOCALIZE, LOG_DEBUG, LOG_LOW, 1);
    set_component_filelog(LOCALIZE);
#endif
    set_comp_log(ENB_APP, LOG_INFO, LOG_HIGH, 1);
    set_comp_log(OTG,     LOG_INFO,   LOG_HIGH, 1);

    if (online_log_messages == 1) {
      set_component_filelog(RRC);
      set_component_filelog(PDCP);
knopp's avatar
knopp committed
989
    }
990
  }
991

knopp's avatar
knopp committed
992 993
  if (ouput_vcd) {
    if (UE_flag==1)
gauthier's avatar
gauthier committed
994
      VCD_SIGNAL_DUMPER_INIT("/tmp/openair_dump_UE.vcd");
knopp's avatar
knopp committed
995
    else
gauthier's avatar
gauthier committed
996
      VCD_SIGNAL_DUMPER_INIT("/tmp/openair_dump_eNB.vcd");
knopp's avatar
knopp committed
997
  }
998

999
  if (opp_enabled ==1) {
1000
    reset_opp_meas();
1001 1002
  }
  cpuf=get_cpu_freq_GHz();
1003

1004
#if defined(ENABLE_ITTI)
1005

knopp's avatar
knopp committed
1006 1007
  if (UE_flag == 1) {
    log_set_instance_type (LOG_INSTANCE_UE);
1008
  } else {
knopp's avatar
knopp committed
1009 1010
    log_set_instance_type (LOG_INSTANCE_ENB);
  }
1011

knopp's avatar
knopp committed
1012
  itti_init(TASK_MAX, THREAD_MAX, MESSAGES_ID_MAX, tasks_info, messages_info, messages_definition_xml, itti_dump_file);
1013

1014 1015
  // initialize mscgen log after ITTI
  MSC_INIT(MSC_E_UTRAN, THREAD_MAX+TASK_MAX);
1016
#endif
1017

1018 1019
  if (opt_type != OPT_NONE) {
    radio_type_t radio_type;
1020

1021 1022
    if (frame_parms[0]->frame_type == FDD)
      radio_type = RADIO_TYPE_FDD;
1023
    else
1024
      radio_type = RADIO_TYPE_TDD;
1025

1026 1027 1028
    if (init_opt(in_path, in_ip, NULL, radio_type) == -1)
      LOG_E(OPT,"failed to run OPT \n");
  }
1029

1030
#ifdef PDCP_USE_NETLINK
knopp's avatar
knopp committed
1031
  netlink_init();
1032 1033 1034
#if defined(PDCP_USE_NETLINK_QUEUES)
  pdcp_netlink_init();
#endif
1035 1036
#endif

1037
#if !defined(ENABLE_ITTI)
knopp's avatar
knopp committed
1038 1039 1040
  // to make a graceful exit when ctrl-c is pressed
  signal(SIGSEGV, signal_handler);
  signal(SIGINT, signal_handler);
1041
#endif
1042

1043

knopp's avatar
knopp committed
1044 1045
  check_clock();

1046 1047 1048 1049 1050 1051
#ifndef PACKAGE_VERSION
#  define PACKAGE_VERSION "UNKNOWN-EXPERIMENTAL"
#endif

  LOG_I(HW, "Version: %s\n", PACKAGE_VERSION);

knopp's avatar
knopp committed
1052
  // init the parameters
1053 1054
  for (CC_id=0; CC_id<MAX_NUM_CCs; CC_id++) {

knopp's avatar
knopp committed
1055
    if (UE_flag==1) {
1056 1057
      frame_parms[CC_id]->nb_antennas_tx     = nb_antenna_tx;
      frame_parms[CC_id]->nb_antennas_rx     = nb_antenna_rx;
1058
      frame_parms[CC_id]->nb_antenna_ports_eNB = 1; //initial value overwritten by initial sync later
1059
    }
knopp's avatar
knopp committed
1060 1061 1062
  }


knopp's avatar
knopp committed
1063

1064

1065
  for (CC_id=0; CC_id<MAX_NUM_CCs; CC_id++) {
1066

1067

1068 1069 1070 1071 1072 1073 1074 1075
    if (UE_flag==1) {     
      NB_UE_INST=1;     
      NB_INST=1;     
      PHY_vars_UE_g = malloc(sizeof(PHY_VARS_UE**));     
      PHY_vars_UE_g[0] = malloc(sizeof(PHY_VARS_UE*)*MAX_NUM_CCs);
      
      
      
1076
      PHY_vars_UE_g[0][CC_id] = init_ue_vars(frame_parms[CC_id], 0,abstraction_flag);
1077 1078
      UE[CC_id] = PHY_vars_UE_g[0][CC_id];
      printf("PHY_vars_UE_g[0][%d] = %p\n",CC_id,UE[CC_id]);
1079
      
1080 1081 1082 1083
      if (phy_test==1)
	UE[CC_id]->mac_enabled = 0;
      else 
	UE[CC_id]->mac_enabled = 1;
1084
      
1085
      if (UE[CC_id]->mac_enabled == 0) {  //set default UL parameters for testing mode
1086 1087 1088 1089 1090 1091 1092 1093 1094
	for (i=0; i<NUMBER_OF_CONNECTED_eNB_MAX; i++) {
	  UE[CC_id]->pusch_config_dedicated[i].betaOffset_ACK_Index = beta_ACK;
	  UE[CC_id]->pusch_config_dedicated[i].betaOffset_RI_Index  = beta_RI;
	  UE[CC_id]->pusch_config_dedicated[i].betaOffset_CQI_Index = beta_CQI;
	  
	  UE[CC_id]->scheduling_request_config[i].sr_PUCCH_ResourceIndex = 0;
	  UE[CC_id]->scheduling_request_config[i].sr_ConfigIndex = 7+(0%3);
	  UE[CC_id]->scheduling_request_config[i].dsr_TransMax = sr_n4;
	}
knopp's avatar
knopp committed
1095
      }
1096
      
1097
      UE[CC_id]->UE_scan = UE_scan;
1098
      UE[CC_id]->UE_scan_carrier = UE_scan_carrier;
1099
      UE[CC_id]->mode    = mode;
Rohit Gupta's avatar
Rohit Gupta committed
1100
      printf("UE[%d]->mode = %d\n",CC_id,mode);
1101 1102 1103 1104 1105 1106 1107 1108
      
      if (UE[CC_id]->mac_enabled == 1) { 
	UE[CC_id]->pdcch_vars[0][0]->crnti = 0x1234;
	UE[CC_id]->pdcch_vars[1][0]->crnti = 0x1234;
      }else {
	UE[CC_id]->pdcch_vars[0][0]->crnti = 0x1235;
	UE[CC_id]->pdcch_vars[1][0]->crnti = 0x1235;
      }
1109
      UE[CC_id]->rx_total_gain_dB =  (int)rx_gain[CC_id][0] + rx_gain_off;
1110
      UE[CC_id]->tx_power_max_dBm = tx_max_power[CC_id];
1111 1112 1113 1114 1115 1116 1117 1118 1119 1120 1121
      
      if (frame_parms[CC_id]->frame_type==FDD) {
	UE[CC_id]->N_TA_offset = 0;
      }
      else {
	if (frame_parms[CC_id]->N_RB_DL == 100)
	  UE[CC_id]->N_TA_offset = 624;
	else if (frame_parms[CC_id]->N_RB_DL == 50)
	  UE[CC_id]->N_TA_offset = 624/2;
	else if (frame_parms[CC_id]->N_RB_DL == 25)
	  UE[CC_id]->N_TA_offset = 624/4;
1122
      }
1123
      
knopp's avatar
knopp committed
1124
    }
knopp's avatar
knopp committed
1125
  }
1126

1127 1128
  fill_modeled_runtime_table(runtime_phy_rx,runtime_phy_tx);
  cpuf=get_cpu_freq_GHz();
1129 1130 1131
  
  
  
laurent's avatar
laurent committed
1132
#ifndef DEADLINE_SCHEDULER
1133
  
1134
  /* Currently we set affinity for UHD to CPU 0 for eNB/UE and only if number of CPUS >2 */
1135 1136 1137 1138 1139
  
  cpu_set_t cpuset;
  int s;
  char cpu_affinity[1024];
  CPU_ZERO(&cpuset);
1140
#ifdef CPU_AFFINITY
1141 1142 1143
  if (get_nprocs() > 2) {
    CPU_SET(0, &cpuset);
    s = pthread_setaffinity_np(pthread_self(), sizeof(cpu_set_t), &cpuset);
1144
    if (s != 0) {
1145 1146
      perror( "pthread_setaffinity_np");
      exit_fun("Error setting processor affinity");
1147
    }
1148 1149
    LOG_I(HW, "Setting the affinity of main function to CPU 0, for device library to use CPU 0 only!\n");
  }
1150
#endif
1151
  
1152 1153
  /* Check the actual affinity mask assigned to the thread */
  s = pthread_getaffinity_np(pthread_self(), sizeof(cpu_set_t), &cpuset);
1154 1155 1156 1157
  if (s != 0) {
    perror( "pthread_getaffinity_np");
    exit_fun("Error getting processor affinity ");
  }