nfapi_pnf.c 96.7 KB
Newer Older
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30
/*
 * 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.1  (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
 */

#define _GNU_SOURCE

#include <stdio.h>
#include <stdlib.h>
#include <stdarg.h>
#include <string.h>
#include <unistd.h>

#include "debug.h"
frtabu's avatar
frtabu committed
31
#include "nfapi/oai_integration/vendor_ext.h"
32
#include "nfapi_pnf_interface.h"
MaheshK1995's avatar
MaheshK1995 committed
33 34 35
#include "nfapi_nr_interface.h"
#include "nfapi_nr_interface_scf.h"

36 37 38
#include "nfapi.h"
#include "nfapi_pnf.h"
#include "common/ran_context.h"
39
#include "openair2/PHY_INTERFACE/phy_stub_UE.h"
40 41 42 43 44 45 46 47 48 49 50

#include <sys/socket.h>
#include <sys/time.h>
#include <netinet/in.h>
#include <assert.h>
#include <arpa/inet.h>
#include <pthread.h>
#include <errno.h>

#include <vendor_ext.h>
#include "fapi_stub.h"
Rahul Gottipati's avatar
Rahul Gottipati committed
51

52
#include "common/utils/LOG/log.h"
53

54
#include "PHY/INIT/phy_init.h"
55
#include "PHY/INIT/nr_phy_init.h"
56
#include "PHY/LTE_TRANSPORT/transport_proto.h"
MaheshK1995's avatar
MaheshK1995 committed
57
#include "openair2/LAYER2/NR_MAC_gNB/mac_proto.h"
Aniq's avatar
Aniq committed
58 59
#include "openair1/SCHED_NR/fapi_nr_l1.h"
#include "openair1/PHY/NR_TRANSPORT/nr_dlsch.h"
Aniq's avatar
Aniq committed
60
#include "openair1/PHY/defs_gNB.h"
61 62
#include <openair1/SCHED/fapi_l1.h>
#include <openair1/PHY/NR_TRANSPORT/nr_transport_proto.h>
63
#include "executables/lte-softmodem.h"
Rahul Gottipati's avatar
Rahul Gottipati committed
64
#include "nfapi/open-nFAPI/pnf/inc/pnf_p7.h"
65

66 67 68 69
#define NUM_P5_PHY 2

#define _GNU_SOURCE

70
extern void phy_init_RU(RU_t *);
71
extern int config_sync_var;
72
extern RAN_CONTEXT_t RC;
73 74 75 76 77 78 79

extern pthread_cond_t nfapi_sync_cond;
extern pthread_mutex_t nfapi_sync_mutex;
extern int nfapi_sync_var;

extern int sync_var;

80
nfapi_tx_request_pdu_t *tx_request_pdu[1023][10][10]; // [frame][subframe][max_num_pdus]
Mahesh's avatar
Mahesh committed
81
uint8_t nr_tx_pdus[32][16][4096];
Mahesh's avatar
Mahesh committed
82
nfapi_nr_pdu_t *tx_data_request[1023][20][10]; //[frame][slot][max_num_pdus]
83 84
uint8_t tx_pdus[32][8][4096];

85
nfapi_ue_release_request_body_t release_rntis;
86

Mahesh's avatar
Mahesh committed
87
nfapi_nr_pnf_param_response_t g_pnf_param_resp;
88 89 90 91


nfapi_pnf_p7_config_t *p7_config_g = NULL;

92
void *pnf_allocate(size_t size) {
93 94 95
  return malloc(size);
}

96
void pnf_deallocate(void *ptr) {
97 98 99 100 101 102 103 104 105 106 107 108 109 110
  free(ptr);
}


typedef struct {
  //public:
  uint8_t enabled;
  uint32_t rx_port;
  uint32_t tx_port;
  //std::string tx_addr;
  char tx_addr[80];
} udp_data;

typedef struct {
111 112 113 114
  uint16_t index;
  uint16_t id;
  uint8_t rfs[2];
  uint8_t excluded_rfs[2];
115

116
  udp_data udp;
117

118 119
  char local_addr[80];
  int local_port;
120

121 122
  char *remote_addr;
  int remote_port;
123

124 125 126 127 128 129 130
  uint8_t duplex_mode;
  uint16_t dl_channel_bw_support;
  uint16_t ul_channel_bw_support;
  uint8_t num_dl_layers_supported;
  uint8_t num_ul_layers_supported;
  uint16_t release_supported;
  uint8_t nmm_modes_supported;
131

132 133
  uint8_t dl_ues_per_subframe;
  uint8_t ul_ues_per_subframe;
134

135
  uint8_t first_subframe_ind;
136

137 138 139 140
  // timing information recevied from the vnf
  uint8_t timing_window;
  uint8_t timing_info_mode;
  uint8_t timing_info_period;
141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159

} phy_info;

typedef struct {
  //public:
  uint16_t index;
  uint16_t band;
  int16_t max_transmit_power;
  int16_t min_transmit_power;
  uint8_t num_antennas_supported;
  uint32_t min_downlink_frequency;
  uint32_t max_downlink_frequency;
  uint32_t max_uplink_frequency;
  uint32_t min_uplink_frequency;
} rf_info;


typedef struct {

160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181
  int release;
  phy_info phys[2];
  rf_info rfs[2];

  uint8_t sync_mode;
  uint8_t location_mode;
  uint8_t location_coordinates[6];
  uint32_t dl_config_timing;
  uint32_t ul_config_timing;
  uint32_t tx_timing;
  uint32_t hi_dci0_timing;

  uint16_t max_phys;
  uint16_t max_total_bw;
  uint16_t max_total_dl_layers;
  uint16_t max_total_ul_layers;
  uint8_t shared_bands;
  uint8_t shared_pa;
  int16_t max_total_power;
  uint8_t oui;

  uint8_t wireshark_test_mode;
182 183 184 185 186

} pnf_info;

typedef struct {
  uint16_t phy_id;
187 188 189
  nfapi_pnf_config_t *config;
  phy_info *phy;
  nfapi_pnf_p7_config_t *p7_config;
190 191 192 193 194
} pnf_phy_user_data_t;

static pnf_info pnf;
static pthread_t pnf_start_pthread;

195 196
int nfapitooai_level(int nfapi_level) {
  switch(nfapi_level) {
197
    case NFAPI_TRACE_ERROR:
198
      return OAILOG_ERR;
199 200

    case NFAPI_TRACE_WARN:
201
      return OAILOG_WARNING;
202

203
    case NFAPI_TRACE_NOTE:
204
      return OAILOG_INFO;
205 206

    case NFAPI_TRACE_INFO:
207
      return OAILOG_DEBUG;
208 209
  }

210
  return OAILOG_ERR;
211 212
}

213
void pnf_nfapi_trace(nfapi_trace_level_t nfapi_level, const char *message, ...) {
214 215
  va_list args;
  va_start(args, message);
216
  VLOG( NFAPI_PNF, nfapitooai_level(nfapi_level), message, args);
217 218 219 220
  va_end(args);
}

void pnf_set_thread_priority(int priority) {
Michael Cook's avatar
Michael Cook committed
221
  set_priority(priority);
222

Michael Cook's avatar
Michael Cook committed
223
  pthread_attr_t ptAttr;
224 225 226 227 228 229 230
  if(pthread_attr_setschedpolicy(&ptAttr, SCHED_RR) != 0) {
    printf("failed to set pthread SCHED_RR %d\n", errno);
  }

  pthread_attr_setinheritsched(&ptAttr, PTHREAD_EXPLICIT_SCHED);
  struct sched_param thread_params;
  thread_params.sched_priority = 20;
231

232 233 234 235 236
  if(pthread_attr_setschedparam(&ptAttr, &thread_params) != 0) {
    printf("failed to set sched param\n");
  }
}

237
void *pnf_p7_thread_start(void *ptr) {
238 239
  NFAPI_TRACE(NFAPI_TRACE_INFO, "[PNF] P7 THREAD %s\n", __FUNCTION__);
  pnf_set_thread_priority(79);
240
  nfapi_pnf_p7_config_t *config = (nfapi_pnf_p7_config_t *)ptr;
241 242 243 244
  nfapi_pnf_p7_start(config);
  return 0;
}

Mahesh's avatar
Mahesh committed
245
void *pnf_nr_p7_thread_start(void *ptr) {
246
  NFAPI_TRACE(NFAPI_TRACE_INFO, "[NR_PNF] NR P7 THREAD %s\n", __FUNCTION__);
Mahesh's avatar
Mahesh committed
247 248 249 250 251 252
  pnf_set_thread_priority(79);
  nfapi_pnf_p7_config_t *config = (nfapi_pnf_p7_config_t *)ptr;
  nfapi_nr_pnf_p7_start(config);
  return 0;
}

253 254
int pnf_nr_param_request(nfapi_pnf_config_t *config, nfapi_nr_pnf_param_request_t *req)
{
Mahesh's avatar
Mahesh committed
255 256 257 258 259 260 261 262 263 264 265 266 267 268 269 270 271 272 273 274
  printf("[PNF] pnf param request\n");
  nfapi_nr_pnf_param_response_t resp;
  memset(&resp, 0, sizeof(resp));
  resp.header.message_id = NFAPI_PNF_PARAM_RESPONSE;
  resp.error_code = NFAPI_MSG_OK;
  pnf_info *pnf = (pnf_info *)(config->user_data);
  resp.pnf_param_general.tl.tag = NFAPI_PNF_PARAM_GENERAL_TAG;
  resp.pnf_param_general.nfapi_sync_mode = pnf->sync_mode;
  resp.pnf_param_general.location_mode = pnf->location_mode;
  resp.pnf_param_general.dl_config_timing = pnf->dl_config_timing;
  resp.pnf_param_general.tx_timing = pnf->tx_timing;
  resp.pnf_param_general.ul_config_timing = pnf->ul_config_timing;
  resp.pnf_param_general.hi_dci0_timing = pnf->hi_dci0_timing;
  resp.pnf_param_general.maximum_number_phys = pnf->max_phys;
  resp.pnf_param_general.maximum_total_bandwidth = pnf->max_total_bw;
  resp.pnf_param_general.maximum_total_number_dl_layers = pnf->max_total_dl_layers;
  resp.pnf_param_general.maximum_total_number_ul_layers = pnf->max_total_ul_layers;
  resp.pnf_param_general.shared_bands = pnf->shared_bands;
  resp.pnf_param_general.shared_pa = pnf->shared_pa;
  resp.pnf_param_general.maximum_total_power = pnf->max_total_power;
275
  resp.num_tlvs = 1;
Mahesh's avatar
Mahesh committed
276 277 278
  resp.pnf_phy.tl.tag = NFAPI_PNF_PHY_TAG;
  resp.pnf_phy.number_of_phys = 1;

279
  for (int i = 0; i < 1; ++i) {
Mahesh's avatar
Mahesh committed
280 281 282 283 284 285 286 287 288
    resp.pnf_phy.phy[i].phy_config_index = pnf->phys[i].index;
    resp.pnf_phy.phy[i].downlink_channel_bandwidth_supported = pnf->phys[i].dl_channel_bw_support;
    resp.pnf_phy.phy[i].uplink_channel_bandwidth_supported = pnf->phys[i].ul_channel_bw_support;
    resp.pnf_phy.phy[i].number_of_dl_layers_supported = pnf->phys[i].num_dl_layers_supported;
    resp.pnf_phy.phy[i].number_of_ul_layers_supported = pnf->phys[i].num_ul_layers_supported;
    resp.pnf_phy.phy[i].maximum_3gpp_release_supported = pnf->phys[i].release_supported;
    resp.pnf_phy.phy[i].nmm_modes_supported = pnf->phys[i].nmm_modes_supported;
    resp.pnf_phy.phy[i].number_of_rfs = 2;

289
    for (int j = 0; j < 1; ++j) {
Mahesh's avatar
Mahesh committed
290 291 292 293 294
      resp.pnf_phy.phy[i].rf_config[j].rf_config_index = pnf->phys[i].rfs[j];
    }

    resp.pnf_phy.phy[i].number_of_rf_exclusions = 0;

295
    for (int j = 0; j < 0; ++j) {
Mahesh's avatar
Mahesh committed
296 297
      resp.pnf_phy.phy[i].excluded_rf_config[j].rf_config_index = pnf->phys[i].excluded_rfs[j];
    }
298
    resp.num_tlvs++;
Mahesh's avatar
Mahesh committed
299
  }
Mahesh's avatar
Mahesh committed
300
  nfapi_nr_pnf_pnf_param_resp(config, &resp);
Mahesh's avatar
Mahesh committed
301 302
  return 0;
}
Mahesh's avatar
Mahesh committed
303

304
int pnf_param_request(nfapi_pnf_config_t *config, nfapi_pnf_param_request_t *req) {
305 306 307 308 309
  printf("[PNF] pnf param request\n");
  nfapi_pnf_param_response_t resp;
  memset(&resp, 0, sizeof(resp));
  resp.header.message_id = NFAPI_PNF_PARAM_RESPONSE;
  resp.error_code = NFAPI_MSG_OK;
310
  pnf_info *pnf = (pnf_info *)(config->user_data);
311 312 313 314 315 316 317 318 319 320 321 322 323 324 325 326 327 328
  resp.pnf_param_general.tl.tag = NFAPI_PNF_PARAM_GENERAL_TAG;
  resp.pnf_param_general.nfapi_sync_mode = pnf->sync_mode;
  resp.pnf_param_general.location_mode = pnf->location_mode;
  resp.pnf_param_general.dl_config_timing = pnf->dl_config_timing;
  resp.pnf_param_general.tx_timing = pnf->tx_timing;
  resp.pnf_param_general.ul_config_timing = pnf->ul_config_timing;
  resp.pnf_param_general.hi_dci0_timing = pnf->hi_dci0_timing;
  resp.pnf_param_general.maximum_number_phys = pnf->max_phys;
  resp.pnf_param_general.maximum_total_bandwidth = pnf->max_total_bw;
  resp.pnf_param_general.maximum_total_number_dl_layers = pnf->max_total_dl_layers;
  resp.pnf_param_general.maximum_total_number_ul_layers = pnf->max_total_ul_layers;
  resp.pnf_param_general.shared_bands = pnf->shared_bands;
  resp.pnf_param_general.shared_pa = pnf->shared_pa;
  resp.pnf_param_general.maximum_total_power = pnf->max_total_power;
  resp.pnf_phy.tl.tag = NFAPI_PNF_PHY_TAG;
  resp.pnf_phy.number_of_phys = 1;

  for(int i = 0; i < 1; ++i) {
329
    resp.pnf_phy.phy[i].phy_config_index = pnf->phys[i].index;
330 331 332 333 334 335 336
    resp.pnf_phy.phy[i].downlink_channel_bandwidth_supported = pnf->phys[i].dl_channel_bw_support;
    resp.pnf_phy.phy[i].uplink_channel_bandwidth_supported = pnf->phys[i].ul_channel_bw_support;
    resp.pnf_phy.phy[i].number_of_dl_layers_supported = pnf->phys[i].num_dl_layers_supported;
    resp.pnf_phy.phy[i].number_of_ul_layers_supported = pnf->phys[i].num_ul_layers_supported;
    resp.pnf_phy.phy[i].maximum_3gpp_release_supported = pnf->phys[i].release_supported;
    resp.pnf_phy.phy[i].nmm_modes_supported = pnf->phys[i].nmm_modes_supported;
    resp.pnf_phy.phy[i].number_of_rfs = 2;
337

338 339 340 341 342
    for(int j = 0; j < 1; ++j) {
      resp.pnf_phy.phy[i].rf_config[j].rf_config_index = pnf->phys[i].rfs[j];
    }

    resp.pnf_phy.phy[i].number_of_rf_exclusions = 0;
343

344 345 346 347
    for(int j = 0; j < 0; ++j) {
      resp.pnf_phy.phy[i].excluded_rf_config[j].rf_config_index = pnf->phys[i].excluded_rfs[j];
    }
  }
Mahesh's avatar
Mahesh committed
348

349 350 351 352
  resp.pnf_rf.tl.tag = NFAPI_PNF_RF_TAG;
  resp.pnf_rf.number_of_rfs = 2;

  for(int i = 0; i < 2; ++i) {
353
    resp.pnf_rf.rf[i].rf_config_index = pnf->rfs[i].index;
354
    resp.pnf_rf.rf[i].band = pnf->rfs[i].band;
355
    resp.pnf_rf.rf[i].maximum_transmit_power = pnf->rfs[i].max_transmit_power;
356 357 358 359 360 361 362 363 364 365 366 367
    resp.pnf_rf.rf[i].minimum_transmit_power = pnf->rfs[i].min_transmit_power;
    resp.pnf_rf.rf[i].number_of_antennas_suppported = pnf->rfs[i].num_antennas_supported;
    resp.pnf_rf.rf[i].minimum_downlink_frequency = pnf->rfs[i].min_downlink_frequency;
    resp.pnf_rf.rf[i].maximum_downlink_frequency = pnf->rfs[i].max_downlink_frequency;
    resp.pnf_rf.rf[i].minimum_uplink_frequency = pnf->rfs[i].min_uplink_frequency;
    resp.pnf_rf.rf[i].maximum_uplink_frequency = pnf->rfs[i].max_uplink_frequency;
  }

  if(pnf->release >= 10) {
    resp.pnf_phy_rel10.tl.tag = NFAPI_PNF_PHY_REL10_TAG;
    resp.pnf_phy_rel10.number_of_phys = 1;

368 369
    for(int i = 0; i < 1; ++i) {
      resp.pnf_phy_rel10.phy[i].phy_config_index = pnf->phys[i].index;
370 371 372 373 374 375 376 377 378 379 380 381 382 383
      resp.pnf_phy_rel10.phy[i].transmission_mode_7_supported = 0;
      resp.pnf_phy_rel10.phy[i].transmission_mode_8_supported = 1;
      resp.pnf_phy_rel10.phy[i].two_antenna_ports_for_pucch = 0;
      resp.pnf_phy_rel10.phy[i].transmission_mode_9_supported = 1;
      resp.pnf_phy_rel10.phy[i].simultaneous_pucch_pusch = 0;
      resp.pnf_phy_rel10.phy[i].four_layer_tx_with_tm3_and_tm4 = 1;
    }
  }

  if(pnf->release >= 11) {
    resp.pnf_phy_rel11.tl.tag = NFAPI_PNF_PHY_REL11_TAG;
    resp.pnf_phy_rel11.number_of_phys = 1;

    for(int i = 0; i < 1; ++i) {
384
      resp.pnf_phy_rel11.phy[i].phy_config_index = pnf->phys[i].index;
385 386 387 388 389 390 391 392 393 394 395 396 397
      resp.pnf_phy_rel11.phy[i].edpcch_supported = 0;
      resp.pnf_phy_rel11.phy[i].multi_ack_csi_reporting = 1;
      resp.pnf_phy_rel11.phy[i].pucch_tx_diversity = 0;
      resp.pnf_phy_rel11.phy[i].ul_comp_supported = 1;
      resp.pnf_phy_rel11.phy[i].transmission_mode_5_supported = 0;
    }
  }

  if(pnf->release >= 12) {
    resp.pnf_phy_rel12.tl.tag = NFAPI_PNF_PHY_REL12_TAG;
    resp.pnf_phy_rel12.number_of_phys = 1;

    for(int i = 0; i < 1; ++i) {
398
      resp.pnf_phy_rel12.phy[i].phy_config_index = pnf->phys[i].index;
399 400 401 402 403 404 405 406 407 408 409 410 411 412
      resp.pnf_phy_rel12.phy[i].csi_subframe_set = 0;
      resp.pnf_phy_rel12.phy[i].enhanced_4tx_codebook = 2;
      resp.pnf_phy_rel12.phy[i].drs_supported = 0;
      resp.pnf_phy_rel12.phy[i].ul_64qam_supported = 1;
      resp.pnf_phy_rel12.phy[i].transmission_mode_10_supported = 0;
      resp.pnf_phy_rel12.phy[i].alternative_bts_indices = 1;
    }
  }

  if(pnf->release >= 13) {
    resp.pnf_phy_rel13.tl.tag = NFAPI_PNF_PHY_REL13_TAG;
    resp.pnf_phy_rel13.number_of_phys = 1;

    for(int i = 0; i < 1; ++i) {
413
      resp.pnf_phy_rel13.phy[i].phy_config_index = pnf->phys[i].index;
414 415 416 417 418 419 420 421 422 423 424 425 426 427 428 429
      resp.pnf_phy_rel13.phy[i].pucch_format4_supported = 0;
      resp.pnf_phy_rel13.phy[i].pucch_format5_supported = 1;
      resp.pnf_phy_rel13.phy[i].more_than_5_ca_support = 0;
      resp.pnf_phy_rel13.phy[i].laa_supported = 1;
      resp.pnf_phy_rel13.phy[i].laa_ending_in_dwpts_supported = 0;
      resp.pnf_phy_rel13.phy[i].laa_starting_in_second_slot_supported = 1;
      resp.pnf_phy_rel13.phy[i].beamforming_supported = 0;
      resp.pnf_phy_rel13.phy[i].csi_rs_enhancement_supported = 1;
      resp.pnf_phy_rel13.phy[i].drms_enhancement_supported = 0;
      resp.pnf_phy_rel13.phy[i].srs_enhancement_supported = 1;
    }

    resp.pnf_phy_rel13_nb_iot.tl.tag = NFAPI_PNF_PHY_REL13_NB_IOT_TAG;
    resp.pnf_phy_rel13_nb_iot.number_of_phys = 1;

    for(int i = 0; i < 1; ++i) {
430
      resp.pnf_phy_rel13_nb_iot.phy[i].phy_config_index = pnf->phys[i].index;
431
      resp.pnf_phy_rel13_nb_iot.phy[i].number_of_rfs = 1;
432

433 434 435 436 437
      for(int j = 0; j < 1; ++j) {
        resp.pnf_phy_rel13_nb_iot.phy[i].rf_config[j].rf_config_index = pnf->phys[i].rfs[j];
      }

      resp.pnf_phy_rel13_nb_iot.phy[i].number_of_rf_exclusions = 1;
438

439 440 441 442 443 444 445 446 447 448
      for(int j = 0; j < 1; ++j) {
        resp.pnf_phy_rel13_nb_iot.phy[i].excluded_rf_config[j].rf_config_index = pnf->phys[i].excluded_rfs[j];
      }

      resp.pnf_phy_rel13_nb_iot.phy[i].number_of_dl_layers_supported = pnf->phys[i].num_dl_layers_supported;
      resp.pnf_phy_rel13_nb_iot.phy[i].number_of_ul_layers_supported = pnf->phys[i].num_ul_layers_supported;
      resp.pnf_phy_rel13_nb_iot.phy[i].maximum_3gpp_release_supported = pnf->phys[i].release_supported;
      resp.pnf_phy_rel13_nb_iot.phy[i].nmm_modes_supported = pnf->phys[i].nmm_modes_supported;
    }
  }
Mahesh's avatar
Mahesh committed
449

450 451 452 453
  nfapi_pnf_pnf_param_resp(config, &resp);
  return 0;
}

454
int pnf_config_request(nfapi_pnf_config_t *config, nfapi_pnf_config_request_t *req) {
455
  printf("[PNF] pnf config request\n");
456
  pnf_info *pnf = (pnf_info *)(config->user_data);
457 458 459 460 461 462 463 464 465 466 467 468
  phy_info *phy = pnf->phys;
  phy->id = req->pnf_phy_rf_config.phy_rf_config[0].phy_id;
  printf("[PNF] pnf config request assigned phy_id %d to phy_config_index %d\n", phy->id, req->pnf_phy_rf_config.phy_rf_config[0].phy_config_index);
  nfapi_pnf_config_response_t resp;
  memset(&resp, 0, sizeof(resp));
  resp.header.message_id = NFAPI_PNF_CONFIG_RESPONSE;
  resp.error_code = NFAPI_MSG_OK;
  nfapi_pnf_pnf_config_resp(config, &resp);
  printf("[PNF] Sent pnf_config_resp\n");
  return 0;
}

Mahesh's avatar
Mahesh committed
469 470 471 472 473 474 475 476 477 478 479 480 481 482 483
int pnf_nr_config_request(nfapi_pnf_config_t *config, nfapi_nr_pnf_config_request_t *req) {
  printf("[PNF] pnf config request\n");
  pnf_info *pnf = (pnf_info *)(config->user_data);
  phy_info *phy = pnf->phys;
  phy->id = req->pnf_phy_rf_config.phy_rf_config[0].phy_id;
  printf("[PNF] pnf config request assigned phy_id %d to phy_config_index %d\n", phy->id, req->pnf_phy_rf_config.phy_rf_config[0].phy_config_index);
  nfapi_nr_pnf_config_response_t resp;
  memset(&resp, 0, sizeof(resp));
  resp.header.message_id = NFAPI_NR_PHY_MSG_TYPE_PNF_CONFIG_RESPONSE;
  resp.error_code = NFAPI_MSG_OK;
  nfapi_nr_pnf_pnf_config_resp(config, &resp);
  printf("[PNF] Sent pnf_config_resp\n");
  return 0;
}

484
void nfapi_send_pnf_start_resp(nfapi_pnf_config_t *config, uint16_t phy_id) {
485
  printf("Sending NFAPI_START_RESPONSE config:%p phy_id:%d\n", config, phy_id);
Mahesh's avatar
Mahesh committed
486
  nfapi_start_response_t start_resp;
487 488 489 490 491 492 493
  memset(&start_resp, 0, sizeof(start_resp));
  start_resp.header.message_id = NFAPI_START_RESPONSE;
  start_resp.header.phy_id = phy_id;
  start_resp.error_code = NFAPI_MSG_OK;
  nfapi_pnf_start_resp(config, &start_resp);
}

Mahesh's avatar
Mahesh committed
494 495 496 497
void nfapi_nr_send_pnf_start_resp(nfapi_pnf_config_t *config, uint16_t phy_id) {
  printf("Sending NFAPI_START_RESPONSE config:%p phy_id:%d\n", config, phy_id);
  nfapi_nr_start_response_scf_t start_resp;
  memset(&start_resp, 0, sizeof(start_resp));
498
  start_resp.header.message_id = NFAPI_NR_PHY_MSG_TYPE_START_RESPONSE;
Mahesh's avatar
Mahesh committed
499
  start_resp.header.phy_id = phy_id;
500
  start_resp.error_code = NFAPI_NR_START_MSG_OK;
Mahesh's avatar
Mahesh committed
501 502 503
  nfapi_nr_pnf_start_resp(config, &start_resp);
}

504
int pnf_start_request(nfapi_pnf_config_t *config, nfapi_pnf_start_request_t *req) {
505
  printf("Received NFAPI_PNF_START_REQUEST\n");
506
  pnf_info *pnf = (pnf_info *)(config->user_data);
507
  // start all phys that have been configured
508
  phy_info *phy = pnf->phys;
509 510 511 512 513 514 515 516 517

  if(phy->id != 0) {
    nfapi_pnf_start_response_t resp;
    memset(&resp, 0, sizeof(resp));
    resp.header.message_id = NFAPI_PNF_START_RESPONSE;
    resp.error_code = NFAPI_MSG_OK;
    nfapi_pnf_pnf_start_resp(config, &resp);
    printf("[PNF] Sent NFAPI_PNF_START_RESP\n");
  }
518

519 520 521
  return 0;
}

Mahesh's avatar
Mahesh committed
522 523 524 525 526 527 528 529 530 531 532 533 534 535 536 537 538 539
int pnf_nr_start_request(nfapi_pnf_config_t *config, nfapi_nr_pnf_start_request_t *req) {
  printf("Received NFAPI_PNF_START_REQUEST\n");
  pnf_info *pnf = (pnf_info *)(config->user_data);
  // start all phys that have been configured
  phy_info *phy = pnf->phys;

  if(phy->id != 0) {
    nfapi_nr_pnf_start_response_t resp;
    memset(&resp, 0, sizeof(resp));
    resp.header.message_id = NFAPI_NR_PHY_MSG_TYPE_PNF_START_RESPONSE;
    resp.error_code = NFAPI_MSG_OK;
    nfapi_nr_pnf_pnf_start_resp(config, &resp);
    printf("[PNF] Sent NFAPI_PNF_START_RESP\n");
  }

  return 0;
}

540
int pnf_stop_request(nfapi_pnf_config_t *config, nfapi_pnf_stop_request_t *req) {
541 542 543 544 545 546 547 548 549 550
  printf("[PNF] Received NFAPI_PNF_STOP_REQ\n");
  nfapi_pnf_stop_response_t resp;
  memset(&resp, 0, sizeof(resp));
  resp.header.message_id = NFAPI_PNF_STOP_RESPONSE;
  resp.error_code = NFAPI_MSG_OK;
  nfapi_pnf_pnf_stop_resp(config, &resp);
  printf("[PNF] Sent NFAPI_PNF_STOP_REQ\n");
  return 0;
}

Mahesh's avatar
Mahesh committed
551
int param_request(nfapi_pnf_config_t *config, nfapi_pnf_phy_config_t *phy, nfapi_param_request_t *req) {
552
  printf("[PNF] Received NFAPI_PARAM_REQUEST phy_id:%d\n", req->header.phy_id);
Mahesh's avatar
Mahesh committed
553
  nfapi_param_response_t nfapi_resp;
554
  pnf_info *pnf = (pnf_info *)(config->user_data);
555 556 557
  memset(&nfapi_resp, 0, sizeof(nfapi_resp));
  nfapi_resp.header.message_id = NFAPI_PARAM_RESPONSE;
  nfapi_resp.header.phy_id = req->header.phy_id;
558
  nfapi_resp.error_code = 0;
559
  struct sockaddr_in pnf_p7_sockaddr;
Mahesh's avatar
Mahesh committed
560 561 562 563 564 565
  pnf_p7_sockaddr.sin_addr.s_addr = inet_addr(pnf->phys[0].local_addr);
  nfapi_resp.nfapi_config.p7_pnf_address_ipv4.tl.tag = NFAPI_NFAPI_P7_PNF_ADDRESS_IPV4_TAG;
  memcpy(nfapi_resp.nfapi_config.p7_pnf_address_ipv4.address, &pnf_p7_sockaddr.sin_addr.s_addr, 4);
  nfapi_resp.num_tlv++;
  // P7 PNF Port
  nfapi_resp.nfapi_config.p7_pnf_port.tl.tag = NFAPI_NFAPI_P7_PNF_PORT_TAG;
566
  nfapi_resp.nfapi_config.p7_pnf_port.value = htons(pnf->phys[0].udp.rx_port);
Mahesh's avatar
Mahesh committed
567 568 569 570 571 572 573 574 575 576 577 578 579 580
  nfapi_resp.num_tlv++;
  nfapi_pnf_param_resp(config, &nfapi_resp);
  printf("[PNF] Sent NFAPI_PARAM_RESPONSE phy_id:%d number_of_tlvs:%u\n", req->header.phy_id, nfapi_resp.num_tlv);
  printf("[PNF] param request .. exit\n");
  return 0;
}

int nr_param_request(nfapi_pnf_config_t *config, nfapi_pnf_phy_config_t *phy, nfapi_nr_param_request_scf_t *req) {
  printf("[PNF] Received NFAPI_PARAM_REQUEST phy_id:%d\n", req->header.phy_id);
  nfapi_nr_param_response_scf_t nfapi_resp;
  pnf_info *pnf = (pnf_info *)(config->user_data);
  memset(&nfapi_resp, 0, sizeof(nfapi_resp));
  nfapi_resp.header.message_id = NFAPI_NR_PHY_MSG_TYPE_PARAM_RESPONSE;
  nfapi_resp.header.phy_id = req->header.phy_id;
581
  nfapi_resp.error_code = 0;
Mahesh's avatar
Mahesh committed
582
  struct sockaddr_in pnf_p7_sockaddr;
MaheshK1995's avatar
MaheshK1995 committed
583 584 585 586 587 588 589 590 591 592 593 594 595 596 597 598 599 600 601 602 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 632 633 634 635 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 674 675 676 677 678 679 680 681 682 683 684 685 686 687 688 689 690 691 692 693 694 695 696 697 698 699 700 701 702 703 704 705 706 707 708 709 710 711 712 713 714 715 716 717 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 747 748 749 750 751 752 753 754 755
  
  // ASSIGN TAGS
  {
  nfapi_resp.cell_param.release_capability.tl.tag = NFAPI_NR_PARAM_TLV_RELEASE_CAPABILITY_TAG;
  nfapi_resp.num_tlv++;

  nfapi_resp.cell_param.phy_state.tl.tag =			 NFAPI_NR_PARAM_TLV_PHY_STATE_TAG;
  nfapi_resp.num_tlv++;

  nfapi_resp.cell_param.skip_blank_dl_config.tl.tag =			 NFAPI_NR_PARAM_TLV_SKIP_BLANK_DL_CONFIG_TAG;
  nfapi_resp.num_tlv++;

  nfapi_resp.cell_param.skip_blank_ul_config.tl.tag =			 NFAPI_NR_PARAM_TLV_SKIP_BLANK_UL_CONFIG_TAG;
  nfapi_resp.num_tlv++;

  nfapi_resp.cell_param.num_config_tlvs_to_report .tl.tag =			 NFAPI_NR_PARAM_TLV_NUM_CONFIG_TLVS_TO_REPORT_TAG;
  nfapi_resp.num_tlv++;

  nfapi_resp.carrier_param.cyclic_prefix.tl.tag =			 NFAPI_NR_PARAM_TLV_CYCLIC_PREFIX_TAG;
  nfapi_resp.num_tlv++;

  nfapi_resp.carrier_param.supported_subcarrier_spacings_dl.tl.tag =			 NFAPI_NR_PARAM_TLV_SUPPORTED_SUBCARRIER_SPACINGS_DL_TAG;
  nfapi_resp.num_tlv++;

  nfapi_resp.carrier_param.supported_bandwidth_dl.tl.tag =			 NFAPI_NR_PARAM_TLV_SUPPORTED_BANDWIDTH_DL_TAG;
  nfapi_resp.num_tlv++;

  nfapi_resp.carrier_param.supported_subcarrier_spacings_ul.tl.tag =			 NFAPI_NR_PARAM_TLV_SUPPORTED_SUBCARRIER_SPACINGS_UL_TAG;
  nfapi_resp.num_tlv++;

  nfapi_resp.carrier_param.supported_bandwidth_ul.tl.tag =			 NFAPI_NR_PARAM_TLV_SUPPORTED_BANDWIDTH_UL_TAG;
  nfapi_resp.num_tlv++;

  nfapi_resp.pdcch_param.cce_mapping_type.tl.tag =			 NFAPI_NR_PARAM_TLV_CCE_MAPPING_TYPE_TAG;
  nfapi_resp.num_tlv++;

  nfapi_resp.pdcch_param.coreset_outside_first_3_of_ofdm_syms_of_slot.tl.tag =			 NFAPI_NR_PARAM_TLV_CORESET_OUTSIDE_FIRST_3_OFDM_SYMS_OF_SLOT_TAG;
  nfapi_resp.num_tlv++;

  nfapi_resp.pdcch_param.coreset_precoder_granularity_coreset.tl.tag =			 NFAPI_NR_PARAM_TLV_PRECODER_GRANULARITY_CORESET_TAG;
  nfapi_resp.num_tlv++;

  nfapi_resp.pdcch_param.pdcch_mu_mimo.tl.tag =			 NFAPI_NR_PARAM_TLV_PDCCH_MU_MIMO_TAG;
  nfapi_resp.num_tlv++;

  nfapi_resp.pdcch_param.pdcch_precoder_cycling.tl.tag =			 NFAPI_NR_PARAM_TLV_PDCCH_PRECODER_CYCLING_TAG;
  nfapi_resp.num_tlv++;

  nfapi_resp.pdcch_param.max_pdcch_per_slot.tl.tag =			 NFAPI_NR_PARAM_TLV_MAX_PDCCHS_PER_SLOT_TAG;
  nfapi_resp.num_tlv++;

  nfapi_resp.pucch_param.pucch_formats.tl.tag =			 NFAPI_NR_PARAM_TLV_PUCCH_FORMATS_TAG;
  nfapi_resp.num_tlv++;

  nfapi_resp.pucch_param.max_pucchs_per_slot.tl.tag =			 NFAPI_NR_PARAM_TLV_MAX_PUCCHS_PER_SLOT_TAG;
  nfapi_resp.num_tlv++;

  nfapi_resp.pdsch_param.pdsch_mapping_type.tl.tag =			 NFAPI_NR_PARAM_TLV_PDSCH_MAPPING_TYPE_TAG;
  nfapi_resp.num_tlv++;

  nfapi_resp.pdsch_param.pdsch_dmrs_additional_pos.tl.tag =			 NFAPI_NR_PARAM_TLV_PDSCH_DMRS_ADDITIONAL_POS_TAG;
  nfapi_resp.num_tlv++;

  nfapi_resp.pdsch_param.pdsch_allocation_types.tl.tag =			 NFAPI_NR_PARAM_TLV_PDSCH_ALLOCATION_TYPES_TAG;
  nfapi_resp.num_tlv++;

  nfapi_resp.pdsch_param.pdsch_vrb_to_prb_mapping.tl.tag =			 NFAPI_NR_PARAM_TLV_PDSCH_VRB_TO_PRB_MAPPING_TAG;
  nfapi_resp.num_tlv++;

  nfapi_resp.pdsch_param.pdsch_cbg.tl.tag =			 NFAPI_NR_PARAM_TLV_PDSCH_CBG_TAG;
  nfapi_resp.num_tlv++;

  nfapi_resp.pdsch_param.pdsch_dmrs_config_types.tl.tag =			 NFAPI_NR_PARAM_TLV_PDSCH_DMRS_CONFIG_TYPES_TAG;
  nfapi_resp.num_tlv++;

  nfapi_resp.pdsch_param.max_number_mimo_layers_pdsch.tl.tag =			 NFAPI_NR_PARAM_TLV_MAX_NUMBER_MIMO_LAYERS_PDSCH_TAG;
  nfapi_resp.num_tlv++;

  nfapi_resp.pdsch_param.max_mu_mimo_users_dl.tl.tag =			 NFAPI_NR_PARAM_TLV_MAX_MU_MIMO_USERS_DL_TAG;
  nfapi_resp.num_tlv++;

  nfapi_resp.pdsch_param.pdsch_data_in_dmrs_symbols.tl.tag =			 NFAPI_NR_PARAM_TLV_PDSCH_DATA_IN_DMRS_SYMBOLS_TAG;
  nfapi_resp.num_tlv++;

  nfapi_resp.pdsch_param.premption_support.tl.tag =			 NFAPI_NR_PARAM_TLV_PREMPTION_SUPPORT_TAG;
  nfapi_resp.num_tlv++;

  nfapi_resp.pdsch_param.pdsch_non_slot_support.tl.tag =			 NFAPI_NR_PARAM_TLV_PDSCH_NON_SLOT_SUPPORT_TAG;
  nfapi_resp.num_tlv++;

  nfapi_resp.pusch_param.uci_mux_ulsch_in_pusch.tl.tag =			 NFAPI_NR_PARAM_TLV_UCI_MUX_ULSCH_IN_PUSCH_TAG;
  nfapi_resp.num_tlv++;

  nfapi_resp.pusch_param.uci_only_pusch.tl.tag =			 NFAPI_NR_PARAM_TLV_UCI_ONLY_PUSCH_TAG;
  nfapi_resp.num_tlv++;

  nfapi_resp.pusch_param.pusch_frequency_hopping.tl.tag =			 NFAPI_NR_PARAM_TLV_PUSCH_FREQUENCY_HOPPING_TAG;
  nfapi_resp.num_tlv++;

  nfapi_resp.pusch_param.pusch_dmrs_config_types.tl.tag =			 NFAPI_NR_PARAM_TLV_PUSCH_DMRS_CONFIG_TYPES_TAG;
  nfapi_resp.num_tlv++;

  nfapi_resp.pusch_param.pusch_dmrs_max_len.tl.tag =			 NFAPI_NR_PARAM_TLV_PUSCH_DMRS_MAX_LEN_TAG;
  nfapi_resp.num_tlv++;

  nfapi_resp.pusch_param.pusch_dmrs_additional_pos.tl.tag =			 NFAPI_NR_PARAM_TLV_PUSCH_DMRS_ADDITIONAL_POS_TAG;
  nfapi_resp.num_tlv++;

  nfapi_resp.pusch_param.pusch_cbg.tl.tag =			 NFAPI_NR_PARAM_TLV_PUSCH_CBG_TAG;
  nfapi_resp.num_tlv++;

  nfapi_resp.pusch_param.pusch_mapping_type.tl.tag =			 NFAPI_NR_PARAM_TLV_PUSCH_MAPPING_TYPE_TAG;
  nfapi_resp.num_tlv++;

  nfapi_resp.pusch_param.pusch_allocation_types.tl.tag =			 NFAPI_NR_PARAM_TLV_PUSCH_ALLOCATION_TYPES_TAG;
  nfapi_resp.num_tlv++;

  nfapi_resp.pusch_param.pusch_vrb_to_prb_mapping.tl.tag =			 NFAPI_NR_PARAM_TLV_PUSCH_VRB_TO_PRB_MAPPING_TAG;
  nfapi_resp.num_tlv++;

  nfapi_resp.pusch_param.pusch_max_ptrs_ports.tl.tag =			 NFAPI_NR_PARAM_TLV_PUSCH_MAX_PTRS_PORTS_TAG;
  nfapi_resp.num_tlv++;

  nfapi_resp.pusch_param.max_pduschs_tbs_per_slot.tl.tag =			 NFAPI_NR_PARAM_TLV_MAX_PDUSCHS_TBS_PER_SLOT_TAG;
  nfapi_resp.num_tlv++;

  nfapi_resp.pusch_param.max_number_mimo_layers_non_cb_pusch.tl.tag =			 NFAPI_NR_PARAM_TLV_MAX_NUMBER_MIMO_LAYERS_NON_CB_PUSCH_TAG;
  nfapi_resp.num_tlv++;

  nfapi_resp.pusch_param.supported_modulation_order_ul.tl.tag =			 NFAPI_NR_PARAM_TLV_SUPPORTED_MODULATION_ORDER_UL_TAG;
  nfapi_resp.num_tlv++;

  nfapi_resp.pusch_param.max_mu_mimo_users_ul.tl.tag =			 NFAPI_NR_PARAM_TLV_MAX_MU_MIMO_USERS_UL_TAG;
  nfapi_resp.num_tlv++;

  nfapi_resp.pusch_param.dfts_ofdm_support.tl.tag =			 NFAPI_NR_PARAM_TLV_DFTS_OFDM_SUPPORT_TAG;
  nfapi_resp.num_tlv++;

  nfapi_resp.pusch_param.pusch_aggregation_factor.tl.tag =			 NFAPI_NR_PARAM_TLV_PUSCH_AGGREGATION_FACTOR_TAG;
  nfapi_resp.num_tlv++;

  nfapi_resp.prach_param.prach_long_formats.tl.tag =             NFAPI_NR_PARAM_TLV_PRACH_LONG_FORMATS_TAG;
  nfapi_resp.num_tlv++;

  nfapi_resp.prach_param.prach_short_formats.tl.tag =			 NFAPI_NR_PARAM_TLV_PRACH_SHORT_FORMATS_TAG;
  nfapi_resp.num_tlv++;

  nfapi_resp.prach_param.prach_restricted_sets.tl.tag =			 NFAPI_NR_PARAM_TLV_PRACH_RESTRICTED_SETS_TAG;
  nfapi_resp.num_tlv++;

  nfapi_resp.prach_param.max_prach_fd_occasions_in_a_slot.tl.tag =			 NFAPI_NR_PARAM_TLV_MAX_PRACH_FD_OCCASIONS_IN_A_SLOT_TAG;
  nfapi_resp.num_tlv++;

  nfapi_resp.measurement_param.rssi_measurement_support.tl.tag =			 NFAPI_NR_PARAM_TLV_RSSI_MEASUREMENT_SUPPORT_TAG;
  nfapi_resp.num_tlv++;

  nfapi_resp.nfapi_config.p7_vnf_address_ipv4.tl.tag =			 NFAPI_NR_NFAPI_P7_VNF_ADDRESS_IPV4_TAG;
  nfapi_resp.num_tlv++;

  nfapi_resp.nfapi_config.p7_vnf_address_ipv6.tl.tag =			 NFAPI_NR_NFAPI_P7_VNF_ADDRESS_IPV6_TAG;
  nfapi_resp.num_tlv++;

  nfapi_resp.nfapi_config.p7_vnf_port.tl.tag =			 NFAPI_NR_NFAPI_P7_VNF_PORT_TAG;
  nfapi_resp.num_tlv++;

  nfapi_resp.nfapi_config.p7_pnf_address_ipv4.tl.tag =			 NFAPI_NR_NFAPI_P7_PNF_ADDRESS_IPV4_TAG;
  nfapi_resp.num_tlv++;

  nfapi_resp.nfapi_config.p7_pnf_address_ipv6.tl.tag =			 NFAPI_NR_NFAPI_P7_PNF_ADDRESS_IPV6_TAG;
  nfapi_resp.num_tlv++;

  nfapi_resp.nfapi_config.p7_pnf_port.tl.tag =			 NFAPI_NR_NFAPI_P7_PNF_PORT_TAG;
  nfapi_resp.num_tlv++;
756
/*
MaheshK1995's avatar
MaheshK1995 committed
757 758 759 760 761 762 763 764
  nfapi_resp.nfapi_config.dl_ue_per_sf.tl.tag =			 NFAPI_NR_NFAPI_DOWNLINK_UES_PER_SUBFRAME_TAG;
  nfapi_resp.num_tlv++;

  nfapi_resp.nfapi_config.ul_ue_per_sf.tl.tag =			 NFAPI_NR_NFAPI_UPLINK_UES_PER_SUBFRAME_TAG;
  nfapi_resp.num_tlv++;

  nfapi_resp.nfapi_config.rf_bands.tl.tag =			 NFAPI_NR_NFAPI_RF_BANDS_TAG;
  nfapi_resp.num_tlv++;
765 766 767
  nfapi_resp.nfapi_config.max_transmit_power.tl.tag =			 NFAPI_NR_NFAPI_MAXIMUM_TRANSMIT_POWER_TAG;
  nfapi_resp.num_tlv++;
*/
MaheshK1995's avatar
MaheshK1995 committed
768 769 770 771 772 773 774 775 776 777
  nfapi_resp.nfapi_config.timing_window.tl.tag =			 NFAPI_NR_NFAPI_TIMING_WINDOW_TAG;
  nfapi_resp.num_tlv++;

  nfapi_resp.nfapi_config.timing_info_mode.tl.tag =			 NFAPI_NR_NFAPI_TIMING_INFO_MODE_TAG;
  nfapi_resp.num_tlv++;

  nfapi_resp.nfapi_config.timing_info_period.tl.tag =			 NFAPI_NR_NFAPI_TIMING_INFO_PERIOD_TAG;
  nfapi_resp.num_tlv++;
  }

778
  nfapi_resp.nfapi_config.p7_pnf_port.value = htons(pnf->phys[0].udp.rx_port);
MaheshK1995's avatar
MaheshK1995 committed
779
  nfapi_resp.num_tlv++;
780
  pnf_p7_sockaddr.sin_addr.s_addr = inet_addr(pnf->phys[0].local_addr);
MaheshK1995's avatar
MaheshK1995 committed
781
  
782 783 784
  memcpy(nfapi_resp.nfapi_config.p7_pnf_address_ipv4.address, &pnf_p7_sockaddr.sin_addr.s_addr, 4);
  nfapi_resp.num_tlv++;
  // P7 PNF Port
785
  printf("TAG value :%d",nfapi_resp.cell_param.phy_state.tl.tag);
Mahesh's avatar
Mahesh committed
786
  nfapi_nr_pnf_param_resp(config, &nfapi_resp);
MaheshK1995's avatar
MaheshK1995 committed
787

MaheshK1995's avatar
MaheshK1995 committed
788
  printf("[PNF] Sent NFAPI_PNF_PARAM_RESPONSE phy_id:%d number_of_tlvs:%u\n", req->header.phy_id, nfapi_resp.num_tlv);
789 790 791 792
  printf("[PNF] param request .. exit\n");
  return 0;
}

Mahesh's avatar
Mahesh committed
793 794 795 796 797 798 799 800 801 802
int config_request(nfapi_pnf_config_t *config, nfapi_pnf_phy_config_t *phy, nfapi_config_request_t *req) 
{
  printf("[PNF] Received NFAPI_CONFIG_REQ phy_id:%d\n", req->header.phy_id);
  pnf_info *pnf = (pnf_info *)(config->user_data);
  uint8_t num_tlv = 0;
  //struct PHY_VARS_eNB_s *eNB = RC.eNB[0][0];
  //  In the case of nfapi_mode = 3 (UE = PNF) we should not have dependency on any eNB var. So we aim
  // to keep only the necessary just to keep the nfapi FSM rolling by sending a dummy response.
  LTE_DL_FRAME_PARMS *fp;

803
  if (NFAPI_MODE!=NFAPI_UE_STUB_PNF && NFAPI_MODE!=NFAPI_MODE_STANDALONE_PNF) {
Mahesh's avatar
Mahesh committed
804 805 806 807 808 809 810 811 812 813 814 815 816 817 818 819 820 821 822 823 824 825 826 827 828 829 830 831 832 833 834 835 836 837 838 839 840 841 842 843 844 845 846 847 848 849 850 851 852 853 854 855 856 857 858 859 860 861 862 863 864 865 866 867 868 869 870 871 872 873 874 875 876 877 878 879
    struct PHY_VARS_eNB_s *eNB = RC.eNB[0][0];
    fp = &eNB->frame_parms;
  } else {
    fp = (LTE_DL_FRAME_PARMS *) malloc(sizeof(LTE_DL_FRAME_PARMS));
  }

  phy_info *phy_info = pnf->phys;

  if(req->nfapi_config.timing_window.tl.tag == NFAPI_NFAPI_TIMING_WINDOW_TAG) {
    phy_info->timing_window = req->nfapi_config.timing_window.value;
    printf("Phy_info:Timing window:%u NFAPI_CONFIG:timing_window:%u\n", phy_info->timing_window, req->nfapi_config.timing_window.value);
    num_tlv++;
  }

  if(req->nfapi_config.timing_info_mode.tl.tag == NFAPI_NFAPI_TIMING_INFO_MODE_TAG) {
    printf("timing info mode:%d\n", req->nfapi_config.timing_info_mode.value);
    phy_info->timing_info_mode = req->nfapi_config.timing_info_mode.value;
    num_tlv++;
  } else {
    phy_info->timing_info_mode = 0;
    printf("NO timing info mode provided\n");
  }

  if(req->nfapi_config.timing_info_period.tl.tag == NFAPI_NFAPI_TIMING_INFO_PERIOD_TAG) {
    printf("timing info period provided value:%d\n", req->nfapi_config.timing_info_period.value);
    phy_info->timing_info_period = req->nfapi_config.timing_info_period.value;
    num_tlv++;
  } else {
    phy_info->timing_info_period = 0;
  }

  if(req->rf_config.dl_channel_bandwidth.tl.tag == NFAPI_RF_CONFIG_DL_CHANNEL_BANDWIDTH_TAG) {
    phy_info->dl_channel_bw_support = req->rf_config.dl_channel_bandwidth.value;
    fp->N_RB_DL = req->rf_config.dl_channel_bandwidth.value;
    num_tlv++;
    NFAPI_TRACE(NFAPI_TRACE_ERROR, "%s() NFAPI_RF_CONFIG_DL_CHANNEL_BANDWIDTH_TAG N_RB_DL:%u\n", __FUNCTION__, fp->N_RB_DL);
  } else {
    NFAPI_TRACE(NFAPI_TRACE_ERROR, "%s() Missing NFAPI_RF_CONFIG_DL_CHANNEL_BANDWIDTH_TAG\n", __FUNCTION__);
  }

  if(req->rf_config.ul_channel_bandwidth.tl.tag == NFAPI_RF_CONFIG_UL_CHANNEL_BANDWIDTH_TAG) {
    phy_info->ul_channel_bw_support = req->rf_config.ul_channel_bandwidth.value;
    fp->N_RB_UL = req->rf_config.ul_channel_bandwidth.value;
    num_tlv++;
  }

  if(req->nfapi_config.rf_bands.tl.tag == NFAPI_NFAPI_RF_BANDS_TAG) {
    pnf->rfs[0].band = req->nfapi_config.rf_bands.rf_band[0];
    fp->eutra_band = req->nfapi_config.rf_bands.rf_band[0];
    num_tlv++;
  }

  if(req->nfapi_config.earfcn.tl.tag == NFAPI_NFAPI_EARFCN_TAG) {
    fp->dl_CarrierFreq = from_earfcn(fp->eutra_band, req->nfapi_config.earfcn.value);
    fp->ul_CarrierFreq = fp->dl_CarrierFreq - (get_uldl_offset(fp->eutra_band) * 1e5);
    num_tlv++;
    NFAPI_TRACE(NFAPI_TRACE_INFO, "%s() earfcn:%u dl_carrierFreq:%u ul_CarrierFreq:%u band:%u N_RB_DL:%u\n",
                __FUNCTION__, req->nfapi_config.earfcn.value, fp->dl_CarrierFreq, fp->ul_CarrierFreq, pnf->rfs[0].band, fp->N_RB_DL);
  }

  if (req->subframe_config.duplex_mode.tl.tag == NFAPI_SUBFRAME_CONFIG_DUPLEX_MODE_TAG) {
    fp->frame_type = req->subframe_config.duplex_mode.value==0 ? TDD : FDD;
    num_tlv++;
    NFAPI_TRACE(NFAPI_TRACE_INFO, "%s() frame_type:%d\n", __FUNCTION__, fp->frame_type);
  }

  if (req->subframe_config.dl_cyclic_prefix_type.tl.tag == NFAPI_SUBFRAME_CONFIG_DL_CYCLIC_PREFIX_TYPE_TAG) {
    fp->Ncp = req->subframe_config.dl_cyclic_prefix_type.value;
    num_tlv++;
  }

  if (req->subframe_config.ul_cyclic_prefix_type.tl.tag == NFAPI_SUBFRAME_CONFIG_UL_CYCLIC_PREFIX_TYPE_TAG) {
    fp->Ncp_UL = req->subframe_config.ul_cyclic_prefix_type.value;
    num_tlv++;
  }

880
  fp->num_MBSFN_config = 0; // hard code alert
Mahesh's avatar
Mahesh committed
881 882 883 884 885 886 887 888 889 890 891 892 893 894 895 896 897 898 899 900 901 902 903 904 905 906 907 908 909 910 911 912 913 914 915 916 917 918 919 920 921 922 923 924 925 926 927 928 929 930

  if (req->sch_config.physical_cell_id.tl.tag == NFAPI_SCH_CONFIG_PHYSICAL_CELL_ID_TAG) {
    fp->Nid_cell = req->sch_config.physical_cell_id.value;
    num_tlv++;
  }

  if (req->rf_config.tx_antenna_ports.tl.tag == NFAPI_RF_CONFIG_TX_ANTENNA_PORTS_TAG) {
    fp->nb_antennas_tx = req->rf_config.tx_antenna_ports.value;
    fp->nb_antenna_ports_eNB = 1;
    num_tlv++;
  }

  if (req->rf_config.rx_antenna_ports.tl.tag == NFAPI_RF_CONFIG_RX_ANTENNA_PORTS_TAG) {
    fp->nb_antennas_rx = req->rf_config.rx_antenna_ports.value;
    num_tlv++;
  }

  if (req->phich_config.phich_resource.tl.tag == NFAPI_PHICH_CONFIG_PHICH_RESOURCE_TAG) {
    fp->phich_config_common.phich_resource = req->phich_config.phich_resource.value;
    num_tlv++;
  }

  if (req->phich_config.phich_duration.tl.tag == NFAPI_PHICH_CONFIG_PHICH_DURATION_TAG) {
    fp->phich_config_common.phich_duration = req->phich_config.phich_duration.value;
    num_tlv++;
  }

  if (req->phich_config.phich_power_offset.tl.tag == NFAPI_PHICH_CONFIG_PHICH_POWER_OFFSET_TAG) {
    LOG_E(PHY, "%s() NFAPI_PHICH_CONFIG_PHICH_POWER_OFFSET_TAG tag:%d not supported\n", __FUNCTION__, req->phich_config.phich_power_offset.tl.tag);
    //fp->phich_config_common.phich_power_offset = req->phich_config.
    num_tlv++;
  }

  // UL RS Config
  if (req->uplink_reference_signal_config.cyclic_shift_1_for_drms.tl.tag == NFAPI_UPLINK_REFERENCE_SIGNAL_CONFIG_CYCLIC_SHIFT_1_FOR_DRMS_TAG) {
    fp->pusch_config_common.ul_ReferenceSignalsPUSCH.cyclicShift = req->uplink_reference_signal_config.cyclic_shift_1_for_drms.value;
    num_tlv++;
  }

  if (req->uplink_reference_signal_config.uplink_rs_hopping.tl.tag == NFAPI_UPLINK_REFERENCE_SIGNAL_CONFIG_UPLINK_RS_HOPPING_TAG) {
    fp->pusch_config_common.ul_ReferenceSignalsPUSCH.groupHoppingEnabled = req->uplink_reference_signal_config.uplink_rs_hopping.value;
    num_tlv++;
  }

  if (req->uplink_reference_signal_config.group_assignment.tl.tag == NFAPI_UPLINK_REFERENCE_SIGNAL_CONFIG_GROUP_ASSIGNMENT_TAG) {
    fp->pusch_config_common.ul_ReferenceSignalsPUSCH.groupAssignmentPUSCH = req->uplink_reference_signal_config.group_assignment.value;
    num_tlv++;
  }

  if (req->pusch_config.hopping_mode.tl.tag == NFAPI_PUSCH_CONFIG_HOPPING_MODE_TAG) {
931
  }  // not being handled?
Mahesh's avatar
Mahesh committed
932 933

  if (req->pusch_config.hopping_offset.tl.tag == NFAPI_PUSCH_CONFIG_HOPPING_OFFSET_TAG) {
934
  }  // not being handled?
Mahesh's avatar
Mahesh committed
935 936

  if (req->pusch_config.number_of_subbands.tl.tag == NFAPI_PUSCH_CONFIG_NUMBER_OF_SUBBANDS_TAG) {
937
  }  // not being handled?
Mahesh's avatar
Mahesh committed
938 939 940 941 942 943 944 945 946 947 948 949 950 951 952 953 954 955 956 957 958 959 960 961 962 963

  if (req->prach_config.configuration_index.tl.tag == NFAPI_PRACH_CONFIG_CONFIGURATION_INDEX_TAG) {
    fp->prach_config_common.prach_ConfigInfo.prach_ConfigIndex=req->prach_config.configuration_index.value;
    num_tlv++;
  }

  if (req->prach_config.root_sequence_index.tl.tag == NFAPI_PRACH_CONFIG_ROOT_SEQUENCE_INDEX_TAG) {
    fp->prach_config_common.rootSequenceIndex=req->prach_config.root_sequence_index.value;
    num_tlv++;
  }

  if (req->prach_config.zero_correlation_zone_configuration.tl.tag == NFAPI_PRACH_CONFIG_ZERO_CORRELATION_ZONE_CONFIGURATION_TAG) {
    fp->prach_config_common.prach_ConfigInfo.zeroCorrelationZoneConfig=req->prach_config.zero_correlation_zone_configuration.value;
    num_tlv++;
  }

  if (req->prach_config.high_speed_flag.tl.tag == NFAPI_PRACH_CONFIG_HIGH_SPEED_FLAG_TAG) {
    fp->prach_config_common.prach_ConfigInfo.highSpeedFlag=req->prach_config.high_speed_flag.value;
    num_tlv++;
  }

  if (req->prach_config.frequency_offset.tl.tag == NFAPI_PRACH_CONFIG_FREQUENCY_OFFSET_TAG) {
    fp->prach_config_common.prach_ConfigInfo.prach_FreqOffset=req->prach_config.frequency_offset.value;
    num_tlv++;
  }

964
  if(NFAPI_MODE!=NFAPI_UE_STUB_PNF && NFAPI_MODE!=NFAPI_MODE_STANDALONE_PNF) {
Mahesh's avatar
Mahesh committed
965
    printf("[PNF] CONFIG_REQUEST[num_tlv:%d] TLVs processed:%d\n", req->num_tlv, num_tlv);
966
    printf("[PNF] Simulating PHY CONFIG\n");
Mahesh's avatar
Mahesh committed
967 968 969 970 971 972 973 974 975 976 977 978 979 980 981 982 983
    PHY_Config_t phy_config;
    phy_config.Mod_id = 0;
    phy_config.CC_id=0;
    phy_config.cfg = req;
    phy_config_request(&phy_config);
    dump_frame_parms(fp);
  }
    phy_info->remote_port = req->nfapi_config.p7_vnf_port.value;
  struct sockaddr_in vnf_p7_sockaddr;
  memcpy(&vnf_p7_sockaddr.sin_addr.s_addr, &(req->nfapi_config.p7_vnf_address_ipv4.address[0]), 4);
  phy_info->remote_addr = inet_ntoa(vnf_p7_sockaddr.sin_addr);
  printf("[PNF] %d vnf p7 %s:%d timing %d %d %d\n", phy_info->id, phy_info->remote_addr, phy_info->remote_port,
         phy_info->timing_window, phy_info->timing_info_mode, phy_info->timing_info_period);
  nfapi_config_response_t nfapi_resp;
  memset(&nfapi_resp, 0, sizeof(nfapi_resp));
  nfapi_resp.header.message_id = NFAPI_CONFIG_RESPONSE;
  nfapi_resp.header.phy_id = phy_info->id;
984
  nfapi_resp.error_code = 0;
Mahesh's avatar
Mahesh committed
985 986 987
  nfapi_pnf_config_resp(config, &nfapi_resp);
  printf("[PNF] Sent NFAPI_CONFIG_RESPONSE phy_id:%d\n", phy_info->id);

988
  if(NFAPI_MODE==NFAPI_UE_STUB_PNF || NFAPI_MODE==NFAPI_MODE_STANDALONE_PNF)
Mahesh's avatar
Mahesh committed
989 990 991 992 993
    free(fp);

  return 0;
}

994
int nr_config_request(nfapi_pnf_config_t *config, nfapi_pnf_phy_config_t *phy, nfapi_nr_config_request_scf_t *req)
Mahesh's avatar
Mahesh committed
995
{
996
  printf("[PNF] Received NFAPI_CONFIG_REQ phy_id:%d\n", req->header.phy_id);
997
  pnf_info *pnf = (pnf_info *)(config->user_data);
998
  uint8_t num_tlv = 0;
999 1000 1001
  // struct PHY_VARS_eNB_s *eNB = RC.eNB[0][0];
  //   In the case of nfapi_mode = 3 (UE = PNF) we should not have dependency on any eNB var. So we aim
  //  to keep only the necessary just to keep the nfapi FSM rolling by sending a dummy response.
MaheshK1995's avatar
MaheshK1995 committed
1002
  NR_DL_FRAME_PARMS *fp;
1003

1004
  if (NFAPI_MODE != NFAPI_UE_STUB_PNF) {
MaheshK1995's avatar
MaheshK1995 committed
1005 1006
    struct PHY_VARS_gNB_s *gNB = RC.gNB[0];
    fp = &gNB->frame_parms;
1007
  } else {
1008
    fp = (NR_DL_FRAME_PARMS *)malloc(sizeof(NR_DL_FRAME_PARMS));
1009
  }
1010

1011
  phy_info *phy_info = pnf->phys;
1012

1013 1014
  printf("\nTiming window tag: %d\n", NFAPI_NR_NFAPI_TIMING_WINDOW_TAG);
  if (req->nfapi_config.timing_window.tl.tag == NFAPI_NR_NFAPI_TIMING_WINDOW_TAG) {
1015
    phy_info->timing_window = req->nfapi_config.timing_window.value;
1016 1017 1018
    printf("Phy_info:Timing window:%u NFAPI_CONFIG:timing_window:%u\n",
           phy_info->timing_window,
           req->nfapi_config.timing_window.value);
1019 1020 1021
    num_tlv++;
  }

1022
  if (req->nfapi_config.timing_info_mode.tl.tag == NFAPI_NR_NFAPI_TIMING_INFO_MODE_TAG) {
1023 1024 1025 1026 1027 1028 1029
    printf("timing info mode:%d\n", req->nfapi_config.timing_info_mode.value);
    phy_info->timing_info_mode = req->nfapi_config.timing_info_mode.value;
    num_tlv++;
  } else {
    phy_info->timing_info_mode = 0;
    printf("NO timing info mode provided\n");
  }
1030 1031
  // TODO: Read the P7 message offset values
  if (req->nfapi_config.timing_info_period.tl.tag == NFAPI_NR_NFAPI_TIMING_INFO_PERIOD_TAG) {
1032 1033 1034 1035 1036 1037 1038
    printf("timing info period provided value:%d\n", req->nfapi_config.timing_info_period.value);
    phy_info->timing_info_period = req->nfapi_config.timing_info_period.value;
    num_tlv++;
  } else {
    phy_info->timing_info_period = 0;
  }

1039 1040 1041
  if (req->carrier_config.dl_bandwidth.tl.tag == NFAPI_NR_CONFIG_DL_BANDWIDTH_TAG) {
    phy_info->dl_channel_bw_support = req->carrier_config.dl_bandwidth.value; // rf_config.dl_channel_bandwidth.value;
    fp->N_RB_DL = req->carrier_config.dl_bandwidth.value; // rf_config.dl_channel_bandwidth.value;
1042
    num_tlv++;
MaheshK1995's avatar
MaheshK1995 committed
1043
    NFAPI_TRACE(NFAPI_TRACE_ERROR, "%s() NFAPI_NR_CONFIG_DL_BANDWIDTH_TAG N_RB_DL:%u\n", __FUNCTION__, fp->N_RB_DL);
1044
  } else {
MaheshK1995's avatar
MaheshK1995 committed
1045
    NFAPI_TRACE(NFAPI_TRACE_ERROR, "%s() Missing NFAPI_NR_CONFIG_DL_BANDWIDTH_TAG\n", __FUNCTION__);
1046 1047
  }

1048 1049 1050
  if (req->carrier_config.uplink_bandwidth.tl.tag == NFAPI_NR_CONFIG_UPLINK_BANDWIDTH_TAG) {
    phy_info->ul_channel_bw_support = req->carrier_config.uplink_bandwidth.value; // req->rf_config.ul_channel_bandwidth.value;
    fp->N_RB_UL = req->carrier_config.uplink_bandwidth.value; // req->rf_config.ul_channel_bandwidth.value;
1051 1052 1053
    num_tlv++;
  }

MaheshK1995's avatar
MaheshK1995 committed
1054
  if (req->cell_config.phy_cell_id.tl.tag == NFAPI_NR_CONFIG_PHY_CELL_ID_TAG) {
1055
    fp->Nid_cell = req->cell_config.phy_cell_id.value; // sch_config.physical_cell_id.value;
1056 1057 1058
    num_tlv++;
  }

1059
  if (NFAPI_MODE != NFAPI_UE_STUB_PNF) {
1060
    printf("[PNF] CONFIG_REQUEST[num_tlv:%d] TLVs processed:%d\n", req->num_tlv, num_tlv);
1061
    printf("[PNF] Simulating PHY CONFIG\n");
MaheshK1995's avatar
MaheshK1995 committed
1062 1063
    NR_PHY_Config_t nr_phy_config;
    nr_phy_config.Mod_id = 0;
1064
    nr_phy_config.CC_id = 0;
MaheshK1995's avatar
MaheshK1995 committed
1065 1066 1067 1068
    nr_phy_config.cfg = req;
    nr_phy_config_request(&nr_phy_config);
    nr_dump_frame_parms(fp);
  }
1069 1070 1071 1072
  phy_info->remote_port = req->nfapi_config.p7_vnf_port.value;
  struct sockaddr_in vnf_p7_sockaddr;
  memcpy(&vnf_p7_sockaddr.sin_addr.s_addr, &(req->nfapi_config.p7_vnf_address_ipv4.address[0]), 4);
  phy_info->remote_addr = inet_ntoa(vnf_p7_sockaddr.sin_addr);
1073 1074 1075 1076 1077 1078 1079
  printf("[PNF] %d vnf p7 %s:%d timing %d %d %d\n",
         phy_info->id,
         phy_info->remote_addr,
         phy_info->remote_port,
         phy_info->timing_window,
         phy_info->timing_info_mode,
         phy_info->timing_info_period);
1080
  nfapi_nr_config_response_scf_t nfapi_resp;
1081
  memset(&nfapi_resp, 0, sizeof(nfapi_resp));
Mahesh's avatar
Mahesh committed
1082
  nfapi_resp.header.message_id = NFAPI_NR_PHY_MSG_TYPE_CONFIG_RESPONSE;
1083
  nfapi_resp.header.phy_id = phy_info->id;
1084
  nfapi_resp.error_code = 0;
1085 1086 1087 1088
  nfapi_resp.num_invalid_tlvs = 0;
  nfapi_resp.num_invalid_tlvs_configured_in_idle = 0;
  nfapi_resp.num_invalid_tlvs_configured_in_running = 0;
  nfapi_resp.num_missing_tlvs = 0;
Mahesh's avatar
Mahesh committed
1089
  nfapi_nr_pnf_config_resp(config, &nfapi_resp);
MaheshK1995's avatar
MaheshK1995 committed
1090
  printf("[PNF] Sent NFAPI_PNF_CONFIG_RESPONSE phy_id:%d\n", phy_info->id);
1091

1092
  if (NFAPI_MODE == NFAPI_UE_STUB_PNF)
1093
    free(fp);
1094

1095 1096 1097
  return 0;
}

1098
nfapi_p7_message_header_t *pnf_phy_allocate_p7_vendor_ext(uint16_t message_id, uint16_t *msg_size) {
1099 1100
  if(message_id == P7_VENDOR_EXT_REQ) {
    (*msg_size) = sizeof(vendor_ext_p7_req);
1101
    return (nfapi_p7_message_header_t *)malloc(sizeof(vendor_ext_p7_req));
1102 1103 1104 1105 1106
  }

  return 0;
}

1107
void pnf_phy_deallocate_p7_vendor_ext(nfapi_p7_message_header_t *header) {
1108 1109 1110
  free(header);
}

1111 1112 1113
notifiedFIFO_elt_t *l1tx_message_extract(PHY_VARS_gNB *gNB, int frame, int slot) {
  notifiedFIFO_elt_t *res;

1114
  //TODO: This needs to be reworked for nfapi to work
1115
  res = pullNotifiedFIFO(&gNB->L1_tx_free);
1116
  return res;
1117
}
Aniq's avatar
Aniq committed
1118

Aniq's avatar
Aniq committed
1119
int pnf_phy_ul_dci_req(gNB_L1_rxtx_proc_t *proc, nfapi_pnf_p7_config_t *pnf_p7, nfapi_nr_ul_dci_request_t *req) {
Mahesh's avatar
Mahesh committed
1120
  
Aniq's avatar
Aniq committed
1121 1122 1123
  //   LOG_D(PHY,"[PNF] HI_DCI0_REQUEST SFN/SF:%05d dci:%d hi:%d\n", NFAPI_SFNSF2DEC(req->sfn_sf), req->hi_dci0_request_body.number_of_dci, req->hi_dci0_request_body.number_of_hi);

  struct PHY_VARS_gNB_s *gNB = RC.gNB[0];
1124 1125 1126 1127 1128 1129

  // extract the next available thread message (priority to message with current slot, then free message)
  notifiedFIFO_elt_t *res;
  res = l1tx_message_extract(gNB, req->SFN, req->Slot);
  processingData_L1tx_t *msgTx = (processingData_L1tx_t *)NotifiedFifoData(res);

Aniq's avatar
Aniq committed
1130 1131 1132
  if (proc ==NULL) 
    proc = &gNB->proc.L1_proc;

1133
  if (req->numPdus > 0) {
1134
    for (int i=0; i<req->numPdus; i++) {
1135
      if (req->ul_dci_pdu_list[i].PDUType == NFAPI_NR_DL_TTI_PDCCH_PDU_TYPE) // only possible value 0: PDCCH PDU
1136 1137 1138
        msgTx->ul_pdcch_pdu[i] = req->ul_dci_pdu_list[i];
      else
        LOG_E(PHY,"[PNF] UL_DCI_REQ sfn_slot:%d PDU[%d] - unknown pdu type:%d\n", NFAPI_SFNSLOT2DEC(req->SFN, req->Slot), req->numPdus-1, req->ul_dci_pdu_list[req->numPdus-1].PDUType);
Aniq's avatar
Aniq committed
1139 1140 1141
    }
  }

1142
  pushNotifiedFIFO(&gNB->L1_tx_filled, res);
1143

Aniq's avatar
Aniq committed
1144 1145 1146 1147
  return 0;
}


1148
int pnf_phy_hi_dci0_req(L1_rxtx_proc_t *proc, nfapi_pnf_p7_config_t *pnf_p7, nfapi_hi_dci0_request_t *req) {
1149 1150 1151 1152 1153
  if (req->hi_dci0_request_body.number_of_dci == 0 && req->hi_dci0_request_body.number_of_hi == 0)
    LOG_D(PHY,"[PNF] HI_DCI0_REQUEST SFN/SF:%05d dci:%d hi:%d\n", NFAPI_SFNSF2DEC(req->sfn_sf), req->hi_dci0_request_body.number_of_dci, req->hi_dci0_request_body.number_of_hi);

  //phy_info* phy = (phy_info*)(pnf_p7->user_data);
  struct PHY_VARS_eNB_s *eNB = RC.eNB[0][0];
1154 1155
  if (proc ==NULL) 
    proc = &eNB->proc.L1_proc;
1156 1157 1158 1159 1160 1161 1162 1163 1164 1165 1166 1167 1168 1169 1170 1171 1172 1173 1174 1175

  for (int i=0; i<req->hi_dci0_request_body.number_of_dci + req->hi_dci0_request_body.number_of_hi; i++) {
    //LOG_D(PHY,"[PNF] HI_DCI0_REQ sfn_sf:%d PDU[%d]\n", NFAPI_SFNSF2DEC(req->sfn_sf), i);
    if (req->hi_dci0_request_body.hi_dci0_pdu_list[i].pdu_type == NFAPI_HI_DCI0_DCI_PDU_TYPE) {
      //LOG_D(PHY,"[PNF] HI_DCI0_REQ sfn_sf:%d PDU[%d] - NFAPI_HI_DCI0_DCI_PDU_TYPE\n", NFAPI_SFNSF2DEC(req->sfn_sf), i);
      nfapi_hi_dci0_request_pdu_t *hi_dci0_req_pdu = &req->hi_dci0_request_body.hi_dci0_pdu_list[i];
      handle_nfapi_hi_dci0_dci_pdu(eNB,NFAPI_SFNSF2SFN(req->sfn_sf),NFAPI_SFNSF2SF(req->sfn_sf),proc,hi_dci0_req_pdu);
      eNB->pdcch_vars[NFAPI_SFNSF2SF(req->sfn_sf)&1].num_dci++;
    } else if (req->hi_dci0_request_body.hi_dci0_pdu_list[i].pdu_type == NFAPI_HI_DCI0_HI_PDU_TYPE) {
      LOG_D(PHY,"[PNF] HI_DCI0_REQ sfn_sf:%d PDU[%d] - NFAPI_HI_DCI0_HI_PDU_TYPE\n", NFAPI_SFNSF2DEC(req->sfn_sf), i);
      nfapi_hi_dci0_request_pdu_t *hi_dci0_req_pdu = &req->hi_dci0_request_body.hi_dci0_pdu_list[i];
      handle_nfapi_hi_dci0_hi_pdu(eNB, NFAPI_SFNSF2SFN(req->sfn_sf),NFAPI_SFNSF2SF(req->sfn_sf), proc, hi_dci0_req_pdu);
    } else {
      LOG_E(PHY,"[PNF] HI_DCI0_REQ sfn_sf:%d PDU[%d] - unknown pdu type:%d\n", NFAPI_SFNSF2DEC(req->sfn_sf), i, req->hi_dci0_request_body.hi_dci0_pdu_list[i].pdu_type);
    }
  }

  return 0;
}

Aniq's avatar
Aniq committed
1176

Aniq's avatar
Aniq committed
1177
int pnf_phy_dl_tti_req(gNB_L1_rxtx_proc_t *proc, nfapi_pnf_p7_config_t *pnf_p7, nfapi_nr_dl_tti_request_t *req) {
Aniq's avatar
Aniq committed
1178 1179 1180 1181 1182 1183 1184 1185 1186 1187 1188 1189 1190 1191 1192 1193 1194 1195 1196 1197 1198 1199
  if (RC.ru == 0) {
    return -1;
  }

  if (RC.gNB == 0) {
    return -2;
  }

  if (RC.gNB[0] == 0) {
    return -3;
  }

  if (sync_var != 0) {
    NFAPI_TRACE(NFAPI_TRACE_INFO, "%s() Main system not up - is this a dummy subframe?\n", __FUNCTION__);
    return -4;
  }

  int sfn = req->SFN;
  int slot =  req->Slot;
  struct PHY_VARS_gNB_s *gNB = RC.gNB[0];
  if (proc==NULL)
     proc = &gNB->proc.L1_proc;
Mahesh's avatar
Mahesh committed
1200
  nfapi_nr_dl_tti_request_pdu_t *dl_tti_pdu_list = req->dl_tti_request_body.dl_tti_pdu_list;
Aniq's avatar
Aniq committed
1201

Mahesh's avatar
Mahesh committed
1202
  if (req->dl_tti_request_body.nPDUs)
1203
    NFAPI_TRACE(NFAPI_TRACE_INFO, "%s() TX:%d/%d RX:%d/%d; sfn:%d, slot:%d, nGroup:%u, nPDUs: %u, nUE: %p, PduIdx: %p,\n",
Aniq's avatar
Aniq committed
1204
                __FUNCTION__, proc->frame_tx, proc->slot_tx, proc->frame_rx, proc->slot_rx, // TODO: change subframes to slot
Aniq's avatar
Aniq committed
1205 1206
                req->SFN,
                req->Slot,
Mahesh's avatar
Mahesh committed
1207 1208 1209 1210
                req->dl_tti_request_body.nGroup,
                req->dl_tti_request_body.nPDUs,
                req->dl_tti_request_body.nUe,
                req->dl_tti_request_body.PduIdx);
Aniq's avatar
Aniq committed
1211

Mahesh's avatar
Mahesh committed
1212
  for (int i=0; i<req->dl_tti_request_body.nPDUs; i++) {
Aniq's avatar
Aniq committed
1213
    // NFAPI_TRACE(NFAPI_TRACE_INFO, "%s() sfn/sf:%d PDU[%d] size:%d pdcch_vars->num_dci:%d\n", __FUNCTION__, NFAPI_SFNSF2DEC(req->sfn_sf), i, dl_config_pdu_list[i].pdu_size,pdcch_vars->num_dci);
1214 1215 1216
    notifiedFIFO_elt_t *res;
    res = l1tx_message_extract(gNB, sfn, slot);
    processingData_L1tx_t *msgTx = (processingData_L1tx_t *)NotifiedFifoData(res);
Aniq's avatar
Aniq committed
1217 1218

    if (dl_tti_pdu_list[i].PDUType == NFAPI_NR_DL_TTI_PDCCH_PDU_TYPE) {
1219
      msgTx->pdcch_pdu[i] = dl_tti_pdu_list[i].pdcch_pdu; // copies all the received PDCCH PDUs
Rahul Gottipati's avatar
Rahul Gottipati committed
1220 1221 1222
    } 
    else if (dl_tti_pdu_list[i].PDUType == NFAPI_NR_DL_TTI_SSB_PDU_TYPE) {
      //NFAPI_TRACE(NFAPI_TRACE_INFO, "%s() PDU:%d BCH: pdu_index:%u pdu_length:%d sdu_length:%d BCH_SDU:%x,%x,%x\n", __FUNCTION__, i, pdu_index, bch_pdu->bch_pdu_rel8.length, tx_request_pdu[sfn][sf][pdu_index]->segments[0].segment_length, sdu[0], sdu[1], sdu[2]);
1223
      handle_nr_nfapi_ssb_pdu(msgTx, sfn, slot, &dl_tti_pdu_list[i]);
1224
    }
Rahul Gottipati's avatar
Rahul Gottipati committed
1225
    else if (dl_tti_pdu_list[i].PDUType == NFAPI_NR_DL_TTI_PDSCH_PDU_TYPE) {
Aniq's avatar
Aniq committed
1226 1227
      nfapi_nr_dl_tti_pdsch_pdu *pdsch_pdu = &dl_tti_pdu_list[i].pdsch_pdu;
      nfapi_nr_dl_tti_pdsch_pdu_rel15_t *rel15_pdu = &pdsch_pdu->pdsch_pdu_rel15;
1228
      nfapi_nr_pdu_t *tx_data = tx_data_request[sfn][slot][rel15_pdu->pduIndex];
Aniq's avatar
Aniq committed
1229 1230

      if (tx_data != NULL) {
1231
        uint8_t *dlsch_sdu = (uint8_t *)tx_data->TLVs[0].value.direct;
Aniq's avatar
Aniq committed
1232
        //NFAPI_TRACE(NFAPI_TRACE_INFO, "%s() DLSCH:pdu_index:%d handle_nfapi_dlsch_pdu(eNB, proc_rxtx, dlsch_pdu, transport_blocks:%d sdu:%p) eNB->pdcch_vars[proc->subframe_tx & 1].num_pdcch_symbols:%d\n", __FUNCTION__, rel8_pdu->pdu_index, rel8_pdu->transport_blocks, dlsch_sdu, eNB->pdcch_vars[proc->subframe_tx & 1].num_pdcch_symbols);
francescomani's avatar
francescomani committed
1233 1234 1235 1236
        AssertFatal(msgTx->num_pdsch_slot < gNB->max_nb_pdsch,
                    "Number of PDSCH PDUs %d exceeded the limit %d\n",
                    msgTx->num_pdsch_slot,
                    gNB->max_nb_pdsch);
1237
        handle_nr_nfapi_pdsch_pdu(msgTx, pdsch_pdu, dlsch_sdu);
Rahul Gottipati's avatar
Rahul Gottipati committed
1238 1239 1240 1241 1242 1243 1244
      } 
      else {
        NFAPI_TRACE(NFAPI_TRACE_ERROR, "%s() DLSCH NULL TX PDU SFN/SF:%d PDU_INDEX:%d\n", __FUNCTION__, NFAPI_SFNSLOT2DEC(sfn,slot), rel15_pdu->pduIndex);     
      }
    }
    else if (dl_tti_pdu_list[i].PDUType == NFAPI_NR_DL_TTI_CSI_RS_PDU_TYPE) {
      nfapi_nr_dl_tti_csi_rs_pdu *csi_rs_pdu = &dl_tti_pdu_list[i].csi_rs_pdu;
1245
      handle_nfapi_nr_csirs_pdu(msgTx, sfn, slot, csi_rs_pdu);
Rahul Gottipati's avatar
Rahul Gottipati committed
1246 1247
    }
    else {
Aniq's avatar
Aniq committed
1248 1249
      NFAPI_TRACE(NFAPI_TRACE_ERROR, "%s() UNKNOWN:%d\n", __FUNCTION__, dl_tti_pdu_list[i].PDUType);
    }
1250
    pushNotifiedFIFO(&gNB->L1_tx_filled, res);
Aniq's avatar
Aniq committed
1251 1252 1253 1254 1255 1256 1257 1258 1259
  }

  if(req->vendor_extension)
    free(req->vendor_extension);

  return 0;
}


1260
int pnf_phy_dl_config_req(L1_rxtx_proc_t *proc, nfapi_pnf_p7_config_t *pnf_p7, nfapi_dl_config_request_t *req) {
1261 1262 1263 1264 1265 1266 1267 1268 1269

  if (RC.eNB == 0) {
    return -2;
  }

  if (RC.eNB[0][0] == 0) {
    return -3;
  }

1270
  if (sync_var != 0) {
1271 1272 1273 1274 1275 1276 1277
    NFAPI_TRACE(NFAPI_TRACE_INFO, "%s() Main system not up - is this a dummy subframe?\n", __FUNCTION__);
    return -4;
  }

  int sfn = NFAPI_SFNSF2SFN(req->sfn_sf);
  int sf = NFAPI_SFNSF2SF(req->sfn_sf);
  struct PHY_VARS_eNB_s *eNB = RC.eNB[0][0];
1278 1279
  if (proc==NULL)
     proc = &eNB->proc.L1_proc;
1280
  nfapi_dl_config_request_pdu_t *dl_config_pdu_list = req->dl_config_request_body.dl_config_pdu_list;
1281 1282 1283 1284
  LTE_eNB_PDCCH *pdcch_vars = &eNB->pdcch_vars[sf&1];
  pdcch_vars->num_pdcch_symbols = req->dl_config_request_body.number_pdcch_ofdm_symbols;
  pdcch_vars->num_dci = 0;

1285
  if (req->dl_config_request_body.number_dci ||
1286 1287
      req->dl_config_request_body.number_pdu ||
      req->dl_config_request_body.number_pdsch_rnti)
1288 1289 1290 1291 1292 1293 1294 1295 1296 1297
    NFAPI_TRACE(NFAPI_TRACE_INFO, "%s() TX:%d/%d RX:%d/%d sfn_sf:%d pdcch:%u dl_cfg[dci:%u pdus:%d pdsch_rnti:%d] pcfich:%u\n",
                __FUNCTION__, proc->frame_tx, proc->subframe_tx, proc->frame_rx, proc->subframe_rx,
                NFAPI_SFNSF2DEC(req->sfn_sf),
                req->dl_config_request_body.number_pdcch_ofdm_symbols,
                req->dl_config_request_body.number_dci,
                req->dl_config_request_body.number_pdu,
                req->dl_config_request_body.number_pdsch_rnti,
                req->dl_config_request_body.transmission_power_pcfich);

  for (int i=0; i<req->dl_config_request_body.number_pdu; i++) {
1298 1299 1300 1301 1302 1303 1304 1305 1306 1307 1308 1309 1310 1311 1312
    NFAPI_TRACE(NFAPI_TRACE_INFO, "%s() sfn/sf:%d PDU[%d] size:%d pdcch_vars->num_dci:%d\n", __FUNCTION__, NFAPI_SFNSF2DEC(req->sfn_sf), i, dl_config_pdu_list[i].pdu_size,pdcch_vars->num_dci);

    if (dl_config_pdu_list[i].pdu_type == NFAPI_DL_CONFIG_DCI_DL_PDU_TYPE) {
      handle_nfapi_dci_dl_pdu(eNB,NFAPI_SFNSF2SFN(req->sfn_sf),NFAPI_SFNSF2SF(req->sfn_sf),proc,&dl_config_pdu_list[i]);
      pdcch_vars->num_dci++; // Is actually number of DCI PDUs
      NFAPI_TRACE(NFAPI_TRACE_INFO, "%s() pdcch_vars->num_dci:%d\n", __FUNCTION__, pdcch_vars->num_dci);
    } else if (dl_config_pdu_list[i].pdu_type == NFAPI_DL_CONFIG_BCH_PDU_TYPE) {
      nfapi_dl_config_bch_pdu *bch_pdu = &dl_config_pdu_list[i].bch_pdu;
      uint16_t pdu_index = bch_pdu->bch_pdu_rel8.pdu_index;

      if (tx_request_pdu[sfn][sf][pdu_index] != NULL) {
        //NFAPI_TRACE(NFAPI_TRACE_INFO, "%s() PDU:%d BCH: pdu_index:%u pdu_length:%d sdu_length:%d BCH_SDU:%x,%x,%x\n", __FUNCTION__, i, pdu_index, bch_pdu->bch_pdu_rel8.length, tx_request_pdu[sfn][sf][pdu_index]->segments[0].segment_length, sdu[0], sdu[1], sdu[2]);
        handle_nfapi_bch_pdu(eNB, proc, &dl_config_pdu_list[i], tx_request_pdu[sfn][sf][pdu_index]->segments[0].segment_data);
        eNB->pbch_configured=1;
      } else {
1313
        NFAPI_TRACE(NFAPI_TRACE_ERROR, "%s() BCH NULL TX PDU SFN/SF:%d PDU_INDEX:%d\n", __FUNCTION__, NFAPI_SFNSF2DEC(req->sfn_sf), pdu_index);
1314 1315 1316 1317 1318 1319 1320 1321 1322 1323 1324 1325
      }
    } else if (dl_config_pdu_list[i].pdu_type == NFAPI_DL_CONFIG_DLSCH_PDU_TYPE) {
      nfapi_dl_config_dlsch_pdu *dlsch_pdu = &dl_config_pdu_list[i].dlsch_pdu;
      nfapi_dl_config_dlsch_pdu_rel8_t *rel8_pdu = &dlsch_pdu->dlsch_pdu_rel8;
      nfapi_tx_request_pdu_t *tx_pdu = tx_request_pdu[sfn][sf][rel8_pdu->pdu_index];

      if (tx_pdu != NULL) {
        int UE_id = find_dlsch(rel8_pdu->rnti,eNB,SEARCH_EXIST_OR_FREE);
        AssertFatal(UE_id!=-1,"no free or exiting dlsch_context\n");
        AssertFatal(UE_id<NUMBER_OF_UE_MAX,"returned UE_id %d >= %d(NUMBER_OF_UE_MAX)\n",UE_id,NUMBER_OF_UE_MAX);
        LTE_eNB_DLSCH_t *dlsch0 = eNB->dlsch[UE_id][0];
        //LTE_eNB_DLSCH_t *dlsch1 = eNB->dlsch[UE_id][1];
1326
        int harq_pid = dlsch0->harq_ids[sfn%2][sf];
1327

1328 1329 1330 1331
        if(harq_pid >= dlsch0->Mdlharq) {
          LOG_E(PHY,"pnf_phy_dl_config_req illegal harq_pid %d\n", harq_pid);
          return(-1);
        }
1332

1333 1334 1335
        uint8_t *dlsch_sdu = tx_pdus[UE_id][harq_pid];
        memcpy(dlsch_sdu, tx_pdu->segments[0].segment_data, tx_pdu->segments[0].segment_length);
        //NFAPI_TRACE(NFAPI_TRACE_INFO, "%s() DLSCH:pdu_index:%d handle_nfapi_dlsch_pdu(eNB, proc_rxtx, dlsch_pdu, transport_blocks:%d sdu:%p) eNB->pdcch_vars[proc->subframe_tx & 1].num_pdcch_symbols:%d\n", __FUNCTION__, rel8_pdu->pdu_index, rel8_pdu->transport_blocks, dlsch_sdu, eNB->pdcch_vars[proc->subframe_tx & 1].num_pdcch_symbols);
1336
        handle_nfapi_dlsch_pdu( eNB, sfn,sf, proc, &dl_config_pdu_list[i], rel8_pdu->transport_blocks-1, dlsch_sdu);
1337 1338 1339 1340 1341 1342 1343 1344 1345 1346 1347 1348 1349 1350
      } else {
        NFAPI_TRACE(NFAPI_TRACE_ERROR, "%s() DLSCH NULL TX PDU SFN/SF:%d PDU_INDEX:%d\n", __FUNCTION__, NFAPI_SFNSF2DEC(req->sfn_sf), rel8_pdu->pdu_index);
      }
    } else {
      NFAPI_TRACE(NFAPI_TRACE_ERROR, "%s() UNKNOWN:%d\n", __FUNCTION__, dl_config_pdu_list[i].pdu_type);
    }
  }

  if(req->vendor_extension)
    free(req->vendor_extension);

  return 0;
}

Aniq's avatar
Aniq committed
1351 1352 1353 1354 1355 1356 1357 1358 1359


int pnf_phy_tx_data_req(nfapi_pnf_p7_config_t *pnf_p7, nfapi_nr_tx_data_request_t *req) {
  uint16_t sfn = req->SFN;
  uint16_t slot = req->Slot;

  if (req->Number_of_PDUs == 0)
    LOG_D(PHY,"%s() SFN/SLOT:%d%d PDUs:%d\n", __FUNCTION__, sfn, slot, req->Number_of_PDUs);

Mahesh's avatar
Mahesh committed
1360
  //if (req->pdu_list[0].TLVs->tag ==  NFAPI_NR_PHY_MSG_TYPE_TX_DATA_REQUEST) {
Aniq's avatar
Aniq committed
1361 1362 1363 1364 1365 1366 1367 1368 1369 1370 1371 1372 1373
    for (int i=0; i<req->Number_of_PDUs; i++) {
      // LOG_D(PHY,"%s() SFN/SF:%d%d number_of_pdus:%d [PDU:%d] pdu_length:%d pdu_index:%d num_segments:%d\n",
      //       __FUNCTION__,
      //       sfn, sf,
      //       req->tx_request_body.number_of_pdus,
      //       i,
      //       req->tx_request_body.tx_pdu_list[i].pdu_length,
      //       req->tx_request_body.tx_pdu_list[i].pdu_index,
      //       req->tx_request_body.tx_pdu_list[i].num_segments
      //      );
      // tx_request_pdu[sfn][sf][i] = &req->tx_request_body.tx_pdu_list[i];
      tx_data_request[sfn][slot][i] = &req->pdu_list[i];
    }
Mahesh's avatar
Mahesh committed
1374
  //}
Aniq's avatar
Aniq committed
1375 1376 1377 1378 1379

  return 0;
}


1380
int pnf_phy_tx_req(nfapi_pnf_p7_config_t *pnf_p7, nfapi_tx_request_t *req) {
1381 1382 1383 1384 1385 1386 1387 1388 1389
  uint16_t sfn = NFAPI_SFNSF2SFN(req->sfn_sf);
  uint16_t sf = NFAPI_SFNSF2SF(req->sfn_sf);

  if (req->tx_request_body.number_of_pdus==0)
    LOG_D(PHY,"%s() SFN/SF:%d%d PDUs:%d\n", __FUNCTION__, sfn, sf, req->tx_request_body.number_of_pdus);

  if (req->tx_request_body.tl.tag==NFAPI_TX_REQUEST_BODY_TAG) {
    for (int i=0; i<req->tx_request_body.number_of_pdus; i++) {
      LOG_D(PHY,"%s() SFN/SF:%d%d number_of_pdus:%d [PDU:%d] pdu_length:%d pdu_index:%d num_segments:%d\n",
1390 1391 1392 1393 1394 1395 1396 1397
            __FUNCTION__,
            sfn, sf,
            req->tx_request_body.number_of_pdus,
            i,
            req->tx_request_body.tx_pdu_list[i].pdu_length,
            req->tx_request_body.tx_pdu_list[i].pdu_index,
            req->tx_request_body.tx_pdu_list[i].num_segments
           );
1398 1399 1400 1401 1402 1403 1404
      tx_request_pdu[sfn][sf][i] = &req->tx_request_body.tx_pdu_list[i];
    }
  }

  return 0;
}

1405 1406


Aniq's avatar
Aniq committed
1407
int pnf_phy_ul_tti_req(gNB_L1_rxtx_proc_t *proc, nfapi_pnf_p7_config_t *pnf_p7, nfapi_nr_ul_tti_request_t *req) {
1408 1409 1410 1411
  LOG_D(PHY,"[PNF] UL_TTI_REQ recvd, writing into structs, SFN/slot:%d.%d pdu:%d \n",
                req->SFN,req->Slot,
                req->n_pdus
               );
1412 1413 1414 1415 1416 1417 1418 1419 1420 1421 1422 1423 1424 1425 1426 1427 1428 1429 1430 1431 1432 1433 1434 1435 1436 1437 1438

  if (RC.ru == 0) {
    return -1;
  }

  if (RC.gNB == 0) {
    return -2;
  }

  if (RC.gNB[0] == 0) {
    return -3;
  }

  if (sync_var != 0) {
    NFAPI_TRACE(NFAPI_TRACE_INFO, "%s() Main system not up - is this a dummy slot?\n", __FUNCTION__);
    return -4;
  }
  uint16_t curr_sfn = req->SFN;
  uint16_t curr_slot = req->Slot;
  struct PHY_VARS_gNB_s *gNB = RC.gNB[0];

  if (proc==NULL)
     proc = &gNB->proc.L1_proc;

  nfapi_nr_ul_tti_request_number_of_pdus_t *ul_tti_pdu_list = req->pdus_list;

  for (int i=0; i< req->n_pdus; i++) {
Mahesh's avatar
Mahesh committed
1439 1440 1441
    switch (ul_tti_pdu_list[i].pdu_type) {
      case NFAPI_NR_UL_CONFIG_PUSCH_PDU_TYPE:
        //LOG_D(PHY,"frame %d, slot %d, Got NFAPI_NR_UL_TTI_PUSCH_PDU_TYPE for %d.%d\n", frame, slot, UL_tti_req->SFN, UL_tti_req->Slot);
David Kim's avatar
David Kim committed
1442
        //curr_sfn = curr_sfn + 3; //Gokul
Mahesh's avatar
Mahesh committed
1443 1444 1445 1446 1447 1448 1449 1450 1451 1452 1453 1454
        nr_fill_ulsch(gNB,curr_sfn, curr_slot, &ul_tti_pdu_list[i].pusch_pdu);
        break;
      case NFAPI_NR_UL_CONFIG_PUCCH_PDU_TYPE:
        //LOG_D(PHY,"frame %d, slot %d, Got NFAPI_NR_UL_TTI_PUCCH_PDU_TYPE for %d.%d\n", frame, slot, UL_tti_req->SFN, UL_tti_req->Slot);
        nr_fill_pucch(gNB,curr_sfn, curr_slot, &ul_tti_pdu_list[i].pucch_pdu);
        break;
      case NFAPI_NR_UL_CONFIG_PRACH_PDU_TYPE:
        //LOG_D(PHY,"frame %d, slot %d, Got NFAPI_NR_UL_TTI_PRACH_PDU_TYPE for %d.%d\n", frame, slot, UL_tti_req->SFN, UL_tti_req->Slot);
        nr_fill_prach(gNB, curr_sfn, curr_slot, &ul_tti_pdu_list[i].prach_pdu);
        if (gNB->RU_list[0]->if_south == LOCAL_RF) nr_fill_prach_ru(gNB->RU_list[0], curr_sfn, curr_slot, &ul_tti_pdu_list[i].prach_pdu);
        break;
      default:
1455
      NFAPI_TRACE(NFAPI_TRACE_ERROR, "%s() PDU:%i UNKNOWN type :%d\n", __FUNCTION__, i, ul_tti_pdu_list[i].pdu_type);
Mahesh's avatar
Mahesh committed
1456 1457
      break;

1458
    }
Mahesh's avatar
Mahesh committed
1459 1460 1461 1462 1463 1464 1465 1466 1467 1468 1469 1470 1471 1472 1473
    // //LOG_D(PHY, "%s() sfn/sf:%d PDU[%d] size:%d\n", __FUNCTION__, NFAPI_SFNSF2DEC(req->sfn_sf), i, ul_config_pdu_list[i].pdu_size);
    // if (
    //   ul_tti_pdu_list[i].pdu_type == NFAPI_NR_UL_CONFIG_PRACH_PDU_TYPE ||
    //   ul_tti_pdu_list[i].pdu_type == NFAPI_NR_UL_CONFIG_PUSCH_PDU_TYPE ||
    //   ul_tti_pdu_list[i].pdu_type == NFAPI_NR_UL_CONFIG_PUCCH_PDU_TYPE ||
    //   ul_tti_pdu_list[i].pdu_type == NFAPI_NR_UL_CONFIG_SRS_PDU_TYPE
    // ) {
    //   //LOG_D(PHY, "%s() handle_nfapi_ul_pdu() for PDU:%d\n", __FUNCTION__, i);
    //   // handle_nfapi_ul_pdu(eNB,proc,&ul_config_pdu_list[i],curr_sfn,curr_sf,req->ul_config_request_body.srs_present);
      
    //   // TODO: dont have an NR function for this, also srs_present flag not there
      
    // } else {
    //   NFAPI_TRACE(NFAPI_TRACE_ERROR, "%s() PDU:%i UNKNOWN type :%d\n", __FUNCTION__, i, ul_tti_pdu_list[i].pdu_type);
    // }
1474 1475 1476 1477 1478
  }

  return 0;
}

1479
int pnf_phy_ul_config_req(L1_rxtx_proc_t *proc, nfapi_pnf_p7_config_t *pnf_p7, nfapi_ul_config_request_t *req) {
1480 1481 1482 1483 1484 1485 1486
  if (0)LOG_D(PHY,"[PNF] UL_CONFIG_REQ %s() sfn_sf:%d pdu:%d rach_prach_frequency_resources:%d srs_present:%u\n",
                __FUNCTION__,
                NFAPI_SFNSF2DEC(req->sfn_sf),
                req->ul_config_request_body.number_of_pdus,
                req->ul_config_request_body.rach_prach_frequency_resources,
                req->ul_config_request_body.srs_present
               );
1487 1488 1489 1490 1491 1492 1493 1494 1495 1496


  if (RC.eNB == 0) {
    return -2;
  }

  if (RC.eNB[0][0] == 0) {
    return -3;
  }

1497
  if (sync_var != 0) {
1498 1499 1500 1501 1502 1503 1504
    NFAPI_TRACE(NFAPI_TRACE_INFO, "%s() Main system not up - is this a dummy subframe?\n", __FUNCTION__);
    return -4;
  }

  uint16_t curr_sfn = NFAPI_SFNSF2SFN(req->sfn_sf);
  uint16_t curr_sf = NFAPI_SFNSF2SF(req->sfn_sf);
  struct PHY_VARS_eNB_s *eNB = RC.eNB[0][0];
1505 1506
  if (proc==NULL)
     proc = &eNB->proc.L1_proc;
1507
  nfapi_ul_config_request_pdu_t *ul_config_pdu_list = req->ul_config_request_body.ul_config_pdu_list;
1508

1509
  for (int i=0; i<req->ul_config_request_body.number_of_pdus; i++) {
1510 1511
    //LOG_D(PHY, "%s() sfn/sf:%d PDU[%d] size:%d\n", __FUNCTION__, NFAPI_SFNSF2DEC(req->sfn_sf), i, ul_config_pdu_list[i].pdu_size);
    if (
1512 1513 1514 1515 1516 1517 1518 1519
      ul_config_pdu_list[i].pdu_type == NFAPI_UL_CONFIG_ULSCH_PDU_TYPE ||
      ul_config_pdu_list[i].pdu_type == NFAPI_UL_CONFIG_ULSCH_HARQ_PDU_TYPE ||
      ul_config_pdu_list[i].pdu_type == NFAPI_UL_CONFIG_ULSCH_CQI_RI_PDU_TYPE ||
      ul_config_pdu_list[i].pdu_type == NFAPI_UL_CONFIG_ULSCH_CQI_HARQ_RI_PDU_TYPE ||
      ul_config_pdu_list[i].pdu_type == NFAPI_UL_CONFIG_UCI_HARQ_PDU_TYPE ||
      ul_config_pdu_list[i].pdu_type == NFAPI_UL_CONFIG_UCI_SR_PDU_TYPE ||
      ul_config_pdu_list[i].pdu_type == NFAPI_UL_CONFIG_UCI_SR_HARQ_PDU_TYPE
    ) {
1520 1521 1522 1523 1524 1525 1526 1527 1528 1529
      //LOG_D(PHY, "%s() handle_nfapi_ul_pdu() for PDU:%d\n", __FUNCTION__, i);
      handle_nfapi_ul_pdu(eNB,proc,&ul_config_pdu_list[i],curr_sfn,curr_sf,req->ul_config_request_body.srs_present);
    } else {
      NFAPI_TRACE(NFAPI_TRACE_ERROR, "%s() PDU:%i UNKNOWN type :%d\n", __FUNCTION__, i, ul_config_pdu_list[i].pdu_type);
    }
  }

  return 0;
}

1530
int pnf_phy_lbt_dl_config_req(nfapi_pnf_p7_config_t *config, nfapi_lbt_dl_config_request_t *req) {
1531 1532 1533 1534
  //printf("[PNF] lbt dl config request\n");
  return 0;
}

1535 1536 1537 1538 1539 1540 1541 1542 1543
int pnf_phy_ue_release_req(nfapi_pnf_p7_config_t* config, nfapi_ue_release_request_t* req) {
  if (req->ue_release_request_body.number_of_TLVs==0)
    return -1;

  release_rntis.number_of_TLVs = req->ue_release_request_body.number_of_TLVs;
  memcpy(&release_rntis.ue_release_request_TLVs_list, req->ue_release_request_body.ue_release_request_TLVs_list, sizeof(nfapi_ue_release_request_TLVs_t)*req->ue_release_request_body.number_of_TLVs);
  return 0;
}

1544
int pnf_phy_vendor_ext(nfapi_pnf_p7_config_t *config, nfapi_p7_message_header_t *msg) {
1545 1546 1547 1548 1549 1550
  if(msg->message_id == P7_VENDOR_EXT_REQ) {
    //vendor_ext_p7_req* req = (vendor_ext_p7_req*)msg;
    //printf("[PNF] vendor request (1:%d 2:%d)\n", req->dummy1, req->dummy2);
  } else {
    printf("[PNF] unknown vendor ext\n");
  }
1551

1552 1553 1554
  return 0;
}

1555
int pnf_phy_pack_p7_vendor_extension(nfapi_p7_message_header_t *header, uint8_t **ppWritePackedMsg, uint8_t *end, nfapi_p7_codec_config_t *codex) {
1556 1557
  //NFAPI_TRACE(NFAPI_TRACE_INFO, "%s\n", __FUNCTION__);
  if(header->message_id == P7_VENDOR_EXT_IND) {
1558 1559
    vendor_ext_p7_ind *ind = (vendor_ext_p7_ind *)(header);

1560 1561 1562 1563 1564
    if(!push16(ind->error_code, ppWritePackedMsg, end))
      return 0;

    return 1;
  }
1565

1566 1567 1568
  return -1;
}

1569
int pnf_phy_unpack_p7_vendor_extension(nfapi_p7_message_header_t *header, uint8_t **ppReadPackedMessage, uint8_t *end, nfapi_p7_codec_config_t *codec) {
1570 1571
  if(header->message_id == P7_VENDOR_EXT_REQ) {
    //NFAPI_TRACE(NFAPI_TRACE_INFO, "%s\n", __FUNCTION__);
1572 1573
    vendor_ext_p7_req *req = (vendor_ext_p7_req *)(header);

1574
    if(!(pull16(ppReadPackedMessage, &req->dummy1, end) &&
1575
         pull16(ppReadPackedMessage, &req->dummy2, end)))
1576
      return 0;
1577

1578 1579
    return 1;
  }
1580

1581 1582 1583
  return -1;
}

1584
int pnf_phy_unpack_vendor_extension_tlv(nfapi_tl_t *tl, uint8_t **ppReadPackedMessage, uint8_t *end, void **ve, nfapi_p7_codec_config_t *config) {
1585
  //NFAPI_TRACE(NFAPI_TRACE_INFO, "pnf_phy_unpack_vendor_extension_tlv\n");
1586
  switch(tl->tag) {
1587 1588
    case VENDOR_EXT_TLV_1_TAG:
      *ve = malloc(sizeof(vendor_ext_tlv_1));
1589 1590 1591

      if(!pull32(ppReadPackedMessage, &((vendor_ext_tlv_1 *)(*ve))->dummy, end))
        return 0;
1592 1593 1594 1595 1596 1597 1598 1599

      return 1;
      break;
  }

  return -1;
}

1600
int pnf_phy_pack_vendor_extention_tlv(void *ve, uint8_t **ppWritePackedMsg, uint8_t *end, nfapi_p7_codec_config_t *config) {
1601 1602 1603 1604 1605 1606
  //printf("%s\n", __FUNCTION__);
  (void)ve;
  (void)ppWritePackedMsg;
  return -1;
}

1607
int pnf_sim_unpack_vendor_extension_tlv(nfapi_tl_t *tl, uint8_t **ppReadPackedMessage, uint8_t *end, void **ve, nfapi_p4_p5_codec_config_t *config) {
1608
  //NFAPI_TRACE(NFAPI_TRACE_INFO, "pnf_sim_unpack_vendor_extension_tlv\n");
1609
  switch(tl->tag) {
1610 1611
    case VENDOR_EXT_TLV_2_TAG:
      *ve = malloc(sizeof(vendor_ext_tlv_2));
1612 1613 1614

      if(!pull32(ppReadPackedMessage, &((vendor_ext_tlv_2 *)(*ve))->dummy, end))
        return 0;
1615 1616 1617 1618 1619 1620 1621 1622

      return 1;
      break;
  }

  return -1;
}

1623
int pnf_sim_pack_vendor_extention_tlv(void *ve, uint8_t **ppWritePackedMsg, uint8_t *end, nfapi_p4_p5_codec_config_t *config) {
1624 1625 1626
  //printf("%s\n", __FUNCTION__);
  (void)ve;
  (void)ppWritePackedMsg;
MaheshK1995's avatar
MaheshK1995 committed
1627

1628 1629 1630 1631 1632 1633 1634 1635
  return -1;
}

nfapi_dl_config_request_t dummy_dl_config_req;
nfapi_tx_request_t dummy_tx_req;

nfapi_pnf_p7_subframe_buffer_t dummy_subframe;

Mahesh's avatar
Mahesh committed
1636 1637 1638 1639 1640 1641 1642 1643
int start_request(nfapi_pnf_config_t *config, nfapi_pnf_phy_config_t *phy, nfapi_start_request_t *req) {
  printf("[PNF] Received NFAPI_START_REQ phy_id:%d\n", req->header.phy_id);
  pnf_info *pnf = (pnf_info *)(config->user_data);
  phy_info *phy_info = pnf->phys;
  nfapi_pnf_p7_config_t *p7_config = nfapi_pnf_p7_config_create();
  p7_config->phy_id = phy->phy_id;
  p7_config->remote_p7_port = phy_info->remote_port;
  p7_config->remote_p7_addr = phy_info->remote_addr;
1644
  p7_config->local_p7_port = phy_info->udp.rx_port;
Mahesh's avatar
Mahesh committed
1645 1646 1647 1648 1649 1650 1651 1652 1653 1654 1655 1656 1657 1658 1659 1660 1661 1662 1663 1664 1665 1666 1667 1668 1669 1670 1671
  p7_config->local_p7_addr = phy_info->local_addr;
  printf("[PNF] P7 remote:%s:%d local:%s:%d\n", p7_config->remote_p7_addr, p7_config->remote_p7_port, p7_config->local_p7_addr, p7_config->local_p7_port);
  p7_config->user_data = phy_info;
  p7_config->malloc = &pnf_allocate;
  p7_config->free = &pnf_deallocate;
  p7_config->codec_config.allocate = &pnf_allocate;
  p7_config->codec_config.deallocate = &pnf_deallocate;
  p7_config->trace = &pnf_nfapi_trace;
  phy->user_data = p7_config;
  p7_config->subframe_buffer_size = phy_info->timing_window;
  printf("subframe_buffer_size configured using phy_info->timing_window:%d\n", phy_info->timing_window);

  if(phy_info->timing_info_mode & 0x1) {
    p7_config->timing_info_mode_periodic = 1;
    p7_config->timing_info_period = phy_info->timing_info_period;
  }

  if(phy_info->timing_info_mode & 0x2) {
    p7_config->timing_info_mode_aperiodic = 1;
  }

  p7_config->dl_config_req = &pnf_phy_dl_config_req;
  p7_config->ul_config_req = &pnf_phy_ul_config_req;
  p7_config->hi_dci0_req = &pnf_phy_hi_dci0_req;
  p7_config->tx_req = &pnf_phy_tx_req;
  p7_config->lbt_dl_config_req = &pnf_phy_lbt_dl_config_req;
  p7_config->ue_release_req = &pnf_phy_ue_release_req;
1672
  if (NFAPI_MODE==NFAPI_UE_STUB_PNF || NFAPI_MODE==NFAPI_MODE_STANDALONE_PNF) {
1673 1674 1675 1676
    p7_config->dl_config_req = NULL;
    p7_config->ul_config_req = NULL;
    p7_config->hi_dci0_req = NULL;
    p7_config->tx_req = NULL;
Mahesh's avatar
Mahesh committed
1677 1678 1679 1680 1681 1682 1683 1684 1685 1686 1687 1688 1689 1690 1691 1692 1693 1694 1695 1696 1697 1698 1699 1700 1701 1702 1703 1704 1705 1706 1707 1708 1709 1710 1711 1712 1713 1714
  } else {
    p7_config->dl_config_req = &pnf_phy_dl_config_req;
    p7_config->ul_config_req = &pnf_phy_ul_config_req;
    p7_config->hi_dci0_req = &pnf_phy_hi_dci0_req;
    p7_config->tx_req = &pnf_phy_tx_req;
  }

  p7_config->lbt_dl_config_req = &pnf_phy_lbt_dl_config_req;
  memset(&dummy_dl_config_req, 0, sizeof(dummy_dl_config_req));
  dummy_dl_config_req.dl_config_request_body.tl.tag=NFAPI_DL_CONFIG_REQUEST_BODY_TAG;
  dummy_dl_config_req.dl_config_request_body.number_pdcch_ofdm_symbols=1;
  dummy_dl_config_req.dl_config_request_body.number_dci=0;
  dummy_dl_config_req.dl_config_request_body.number_pdu=0;
  dummy_dl_config_req.dl_config_request_body.number_pdsch_rnti=0;
  dummy_dl_config_req.dl_config_request_body.transmission_power_pcfich=6000;
  dummy_dl_config_req.dl_config_request_body.dl_config_pdu_list=0;
  memset(&dummy_tx_req, 0, sizeof(dummy_tx_req));
  dummy_tx_req.tx_request_body.number_of_pdus=0;
  dummy_tx_req.tx_request_body.tl.tag=NFAPI_TX_REQUEST_BODY_TAG;
  dummy_subframe.dl_config_req = &dummy_dl_config_req;
  dummy_subframe.tx_req = 0;//&dummy_tx_req;
  dummy_subframe.ul_config_req=0;
  dummy_subframe.hi_dci0_req=0;
  dummy_subframe.lbt_dl_config_req=0;
  p7_config->dummy_subframe = dummy_subframe;
  p7_config->vendor_ext = &pnf_phy_vendor_ext;
  p7_config->allocate_p7_vendor_ext = &pnf_phy_allocate_p7_vendor_ext;
  p7_config->deallocate_p7_vendor_ext = &pnf_phy_deallocate_p7_vendor_ext;
  p7_config->codec_config.unpack_p7_vendor_extension = &pnf_phy_unpack_p7_vendor_extension;
  p7_config->codec_config.pack_p7_vendor_extension = &pnf_phy_pack_p7_vendor_extension;
  p7_config->codec_config.unpack_vendor_extension_tlv = &pnf_phy_unpack_vendor_extension_tlv;
  p7_config->codec_config.pack_vendor_extension_tlv = &pnf_phy_pack_vendor_extention_tlv;
  NFAPI_TRACE(NFAPI_TRACE_INFO, "[PNF] Creating P7 thread %s\n", __FUNCTION__);
  pthread_t p7_thread;
  pthread_create(&p7_thread, NULL, &pnf_p7_thread_start, p7_config);
  //((pnf_phy_user_data_t*)(phy_info->fapi->user_data))->p7_config = p7_config;
  NFAPI_TRACE(NFAPI_TRACE_INFO, "[PNF] Calling l1_north_init_eNB() %s\n", __FUNCTION__);
  l1_north_init_eNB();
1715
  NFAPI_TRACE(NFAPI_TRACE_INFO, "[PNF] HACK - Set p7_config global ready for subframe ind%s\n", __FUNCTION__);
Mahesh's avatar
Mahesh committed
1716 1717 1718 1719 1720 1721 1722 1723 1724 1725 1726 1727 1728
  p7_config_g = p7_config;

  // Need to wait for main thread to create RU structures
  while(config_sync_var<0) {
    usleep(5000000);
    printf("[PNF] waiting for OAI to be configured (eNB/RU)\n");
  }

  printf("[PNF] OAI eNB/RU configured\n");
  //printf("[PNF] About to call phy_init_RU() for RC.ru[0]:%p\n", RC.ru[0]);
  //phy_init_RU(RC.ru[0]);
  printf("[PNF] About to call init_eNB_afterRU()\n");

1729
  if (NFAPI_MODE!=NFAPI_UE_STUB_PNF && NFAPI_MODE!=NFAPI_MODE_STANDALONE_PNF) {
Mahesh's avatar
Mahesh committed
1730 1731 1732 1733 1734 1735 1736 1737 1738 1739 1740 1741 1742 1743 1744 1745 1746 1747 1748
    init_eNB_afterRU();
  }

  // Signal to main thread that it can carry on - otherwise RU will startup too quickly and it is not initialised
  {
    pthread_mutex_lock(&nfapi_sync_mutex);
    nfapi_sync_var=0;
    pthread_cond_broadcast(&nfapi_sync_cond);
    pthread_mutex_unlock(&nfapi_sync_mutex);
  }

  while(sync_var<0) {
    usleep(5000000);
    printf("[PNF] waiting for OAI to be started\n");
  }

  printf("[PNF] Sending PNF_START_RESP\n");
  nfapi_send_pnf_start_resp(config, p7_config->phy_id);
  printf("[PNF] Sending first P7 subframe ind\n");
1749
  nfapi_pnf_p7_subframe_ind(p7_config, p7_config->phy_id, 0); // SFN_SF set to zero - correct???
Mahesh's avatar
Mahesh committed
1750 1751 1752 1753 1754
  printf("[PNF] Sent first P7 subframe ind\n");
  return 0;
}

int nr_start_request(nfapi_pnf_config_t *config, nfapi_pnf_phy_config_t *phy,  nfapi_nr_start_request_scf_t *req) {
1755
  printf("[PNF] Received NFAPI_START_REQ phy_id:%d\n", req->header.phy_id);
1756 1757 1758
  pnf_info *pnf = (pnf_info *)(config->user_data);
  phy_info *phy_info = pnf->phys;
  nfapi_pnf_p7_config_t *p7_config = nfapi_pnf_p7_config_create();
1759 1760 1761
  p7_config->phy_id = phy->phy_id;
  p7_config->remote_p7_port = phy_info->remote_port;
  p7_config->remote_p7_addr = phy_info->remote_addr;
1762 1763

  p7_config->local_p7_port = phy_info->udp.rx_port;
1764 1765 1766 1767 1768 1769 1770 1771 1772 1773
  p7_config->local_p7_addr = phy_info->local_addr;
  printf("[PNF] P7 remote:%s:%d local:%s:%d\n", p7_config->remote_p7_addr, p7_config->remote_p7_port, p7_config->local_p7_addr, p7_config->local_p7_port);
  p7_config->user_data = phy_info;
  p7_config->malloc = &pnf_allocate;
  p7_config->free = &pnf_deallocate;
  p7_config->codec_config.allocate = &pnf_allocate;
  p7_config->codec_config.deallocate = &pnf_deallocate;
  p7_config->trace = &pnf_nfapi_trace;
  phy->user_data = p7_config;
  p7_config->subframe_buffer_size = phy_info->timing_window;
MaheshK1995's avatar
MaheshK1995 committed
1774
  p7_config->slot_buffer_size = phy_info->timing_window; // TODO: check if correct for NR
1775
  printf("subframe_buffer_size configured using phy_info->timing_window:%d\n", phy_info->timing_window);
1776

1777 1778 1779 1780 1781 1782 1783 1784 1785
  if(phy_info->timing_info_mode & 0x1) {
    p7_config->timing_info_mode_periodic = 1;
    p7_config->timing_info_period = phy_info->timing_info_period;
  }

  if(phy_info->timing_info_mode & 0x2) {
    p7_config->timing_info_mode_aperiodic = 1;
  }

Aniq's avatar
Aniq committed
1786
  // NR
Aniq's avatar
Aniq committed
1787 1788 1789 1790
  p7_config->dl_tti_req_fn  = &pnf_phy_dl_tti_req;
  p7_config->ul_tti_req_fn  = &pnf_phy_ul_tti_req;
  p7_config->ul_dci_req_fn  = &pnf_phy_ul_dci_req;
  p7_config->tx_data_req_fn = &pnf_phy_tx_data_req;
Aniq's avatar
Aniq committed
1791 1792

  // LTE
1793 1794 1795 1796 1797
  p7_config->dl_config_req = &pnf_phy_dl_config_req;
  p7_config->ul_config_req = &pnf_phy_ul_config_req;
  p7_config->hi_dci0_req = &pnf_phy_hi_dci0_req;
  p7_config->tx_req = &pnf_phy_tx_req;
  p7_config->lbt_dl_config_req = &pnf_phy_lbt_dl_config_req;
1798
  p7_config->ue_release_req = &pnf_phy_ue_release_req;
frtabu's avatar
frtabu committed
1799
  if (NFAPI_MODE==NFAPI_UE_STUB_PNF) {
1800 1801 1802 1803
    p7_config->dl_config_req = NULL;
    p7_config->ul_config_req = NULL;
    p7_config->hi_dci0_req = NULL;
    p7_config->tx_req = NULL;
1804 1805 1806 1807 1808 1809
  } else {
    p7_config->dl_config_req = &pnf_phy_dl_config_req;
    p7_config->ul_config_req = &pnf_phy_ul_config_req;
    p7_config->hi_dci0_req = &pnf_phy_hi_dci0_req;
    p7_config->tx_req = &pnf_phy_tx_req;
  }
1810

1811 1812 1813 1814 1815 1816 1817 1818 1819 1820 1821 1822 1823 1824 1825 1826 1827 1828 1829 1830 1831 1832 1833 1834 1835 1836 1837
  p7_config->lbt_dl_config_req = &pnf_phy_lbt_dl_config_req;
  memset(&dummy_dl_config_req, 0, sizeof(dummy_dl_config_req));
  dummy_dl_config_req.dl_config_request_body.tl.tag=NFAPI_DL_CONFIG_REQUEST_BODY_TAG;
  dummy_dl_config_req.dl_config_request_body.number_pdcch_ofdm_symbols=1;
  dummy_dl_config_req.dl_config_request_body.number_dci=0;
  dummy_dl_config_req.dl_config_request_body.number_pdu=0;
  dummy_dl_config_req.dl_config_request_body.number_pdsch_rnti=0;
  dummy_dl_config_req.dl_config_request_body.transmission_power_pcfich=6000;
  dummy_dl_config_req.dl_config_request_body.dl_config_pdu_list=0;
  memset(&dummy_tx_req, 0, sizeof(dummy_tx_req));
  dummy_tx_req.tx_request_body.number_of_pdus=0;
  dummy_tx_req.tx_request_body.tl.tag=NFAPI_TX_REQUEST_BODY_TAG;
  dummy_subframe.dl_config_req = &dummy_dl_config_req;
  dummy_subframe.tx_req = 0;//&dummy_tx_req;
  dummy_subframe.ul_config_req=0;
  dummy_subframe.hi_dci0_req=0;
  dummy_subframe.lbt_dl_config_req=0;
  p7_config->dummy_subframe = dummy_subframe;
  p7_config->vendor_ext = &pnf_phy_vendor_ext;
  p7_config->allocate_p7_vendor_ext = &pnf_phy_allocate_p7_vendor_ext;
  p7_config->deallocate_p7_vendor_ext = &pnf_phy_deallocate_p7_vendor_ext;
  p7_config->codec_config.unpack_p7_vendor_extension = &pnf_phy_unpack_p7_vendor_extension;
  p7_config->codec_config.pack_p7_vendor_extension = &pnf_phy_pack_p7_vendor_extension;
  p7_config->codec_config.unpack_vendor_extension_tlv = &pnf_phy_unpack_vendor_extension_tlv;
  p7_config->codec_config.pack_vendor_extension_tlv = &pnf_phy_pack_vendor_extention_tlv;
  NFAPI_TRACE(NFAPI_TRACE_INFO, "[PNF] Creating P7 thread %s\n", __FUNCTION__);
  pthread_t p7_thread;
Mahesh's avatar
Mahesh committed
1838
  pthread_create(&p7_thread, NULL, &pnf_nr_p7_thread_start, p7_config);
1839
  NFAPI_TRACE(NFAPI_TRACE_INFO, "[PNF] Calling l1_north_init_eNB() %s\n", __FUNCTION__);
1840
  l1_north_init_gNB();
1841
  NFAPI_TRACE(NFAPI_TRACE_INFO, "[PNF] HACK - Set p7_config global ready for subframe ind%s\n", __FUNCTION__);
1842 1843 1844 1845 1846 1847 1848 1849 1850 1851 1852 1853 1854
  p7_config_g = p7_config;

  // Need to wait for main thread to create RU structures
  while(config_sync_var<0) {
    usleep(5000000);
    printf("[PNF] waiting for OAI to be configured (eNB/RU)\n");
  }

  printf("[PNF] OAI eNB/RU configured\n");
  //printf("[PNF] About to call phy_init_RU() for RC.ru[0]:%p\n", RC.ru[0]);
  //phy_init_RU(RC.ru[0]);
  printf("[PNF] About to call init_eNB_afterRU()\n");

frtabu's avatar
frtabu committed
1855
  if (NFAPI_MODE!=NFAPI_UE_STUB_PNF) {
1856 1857 1858 1859 1860 1861 1862 1863 1864 1865
    init_eNB_afterRU();
  }

  // Signal to main thread that it can carry on - otherwise RU will startup too quickly and it is not initialised
  {
    pthread_mutex_lock(&nfapi_sync_mutex);
    nfapi_sync_var=0;
    pthread_cond_broadcast(&nfapi_sync_cond);
    pthread_mutex_unlock(&nfapi_sync_mutex);
  }
1866

1867 1868 1869 1870
  while(sync_var<0) {
    usleep(5000000);
    printf("[PNF] waiting for OAI to be started\n");
  }
1871

1872
  printf("[PNF] Sending PNF_START_RESP\n");
Mahesh's avatar
Mahesh committed
1873
  nfapi_nr_send_pnf_start_resp(config, p7_config->phy_id);
MaheshK1995's avatar
MaheshK1995 committed
1874 1875 1876 1877 1878
  printf("[PNF] Sending first P7 slot indication\n");
#if 1
  nfapi_pnf_p7_slot_ind(p7_config, p7_config->phy_id, 0, 0);
  printf("[PNF] Sent first P7 slot ind\n");
#else
1879
  nfapi_pnf_p7_subframe_ind(p7_config, p7_config->phy_id, 0); // SFN_SF set to zero - correct???
1880
  printf("[PNF] Sent first P7 subframe ind\n");
MaheshK1995's avatar
MaheshK1995 committed
1881 1882 1883
#endif
  
  
1884 1885 1886
  return 0;
}

1887
int measurement_request(nfapi_pnf_config_t *config, nfapi_pnf_phy_config_t *phy, nfapi_measurement_request_t *req) {
1888 1889 1890 1891 1892 1893 1894 1895 1896
  nfapi_measurement_response_t resp;
  memset(&resp, 0, sizeof(resp));
  resp.header.message_id = NFAPI_MEASUREMENT_RESPONSE;
  resp.header.phy_id = req->header.phy_id;
  resp.error_code = NFAPI_MSG_OK;
  nfapi_pnf_measurement_resp(config, &resp);
  return 0;
}

1897
int rssi_request(nfapi_pnf_config_t *config, nfapi_pnf_phy_config_t *phy, nfapi_rssi_request_t *req) {
1898 1899 1900 1901 1902 1903 1904 1905 1906 1907 1908 1909 1910 1911 1912 1913 1914 1915
  nfapi_rssi_response_t resp;
  memset(&resp, 0, sizeof(resp));
  resp.header.message_id = NFAPI_RSSI_RESPONSE;
  resp.header.phy_id = req->header.phy_id;
  resp.error_code = NFAPI_P4_MSG_OK;
  nfapi_pnf_rssi_resp(config, &resp);
  nfapi_rssi_indication_t ind;
  memset(&ind, 0, sizeof(ind));
  ind.header.message_id = NFAPI_RSSI_INDICATION;
  ind.header.phy_id = req->header.phy_id;
  ind.error_code = NFAPI_P4_MSG_OK;
  ind.rssi_indication_body.tl.tag = NFAPI_RSSI_INDICATION_TAG;
  ind.rssi_indication_body.number_of_rssi = 1;
  ind.rssi_indication_body.rssi[0] = -42;
  nfapi_pnf_rssi_ind(config, &ind);
  return 0;
}

1916
int cell_search_request(nfapi_pnf_config_t *config, nfapi_pnf_phy_config_t *phy, nfapi_cell_search_request_t *req) {
1917 1918 1919 1920 1921 1922 1923 1924 1925 1926 1927 1928 1929 1930 1931 1932 1933 1934 1935 1936 1937 1938
  nfapi_cell_search_response_t resp;
  memset(&resp, 0, sizeof(resp));
  resp.header.message_id = NFAPI_CELL_SEARCH_RESPONSE;
  resp.header.phy_id = req->header.phy_id;
  resp.error_code = NFAPI_P4_MSG_OK;
  nfapi_pnf_cell_search_resp(config, &resp);
  nfapi_cell_search_indication_t ind;
  memset(&ind, 0, sizeof(ind));
  ind.header.message_id = NFAPI_CELL_SEARCH_INDICATION;
  ind.header.phy_id = req->header.phy_id;
  ind.error_code = NFAPI_P4_MSG_OK;

  switch(req->rat_type) {
    case NFAPI_RAT_TYPE_LTE:
      ind.lte_cell_search_indication.tl.tag = NFAPI_LTE_CELL_SEARCH_INDICATION_TAG;
      ind.lte_cell_search_indication.number_of_lte_cells_found = 1;
      ind.lte_cell_search_indication.lte_found_cells[0].pci = 123;
      ind.lte_cell_search_indication.lte_found_cells[0].rsrp = 123;
      ind.lte_cell_search_indication.lte_found_cells[0].rsrq = 123;
      ind.lte_cell_search_indication.lte_found_cells[0].frequency_offset = 123;
      break;

1939 1940 1941 1942 1943 1944 1945 1946 1947 1948 1949 1950 1951 1952 1953 1954 1955 1956 1957 1958
    case NFAPI_RAT_TYPE_UTRAN: {
      ind.utran_cell_search_indication.tl.tag = NFAPI_UTRAN_CELL_SEARCH_INDICATION_TAG;
      ind.utran_cell_search_indication.number_of_utran_cells_found = 1;
      ind.utran_cell_search_indication.utran_found_cells[0].psc = 89;
      ind.utran_cell_search_indication.utran_found_cells[0].rscp = 89;
      ind.utran_cell_search_indication.utran_found_cells[0].ecno = 89;
      ind.utran_cell_search_indication.utran_found_cells[0].frequency_offset = -89;
    }
    break;

    case NFAPI_RAT_TYPE_GERAN: {
      ind.geran_cell_search_indication.tl.tag = NFAPI_GERAN_CELL_SEARCH_INDICATION_TAG;
      ind.geran_cell_search_indication.number_of_gsm_cells_found = 1;
      ind.geran_cell_search_indication.gsm_found_cells[0].bsic = 23;
      ind.geran_cell_search_indication.gsm_found_cells[0].rxlev = 23;
      ind.geran_cell_search_indication.gsm_found_cells[0].rxqual = 23;
      ind.geran_cell_search_indication.gsm_found_cells[0].frequency_offset = -23;
      ind.geran_cell_search_indication.gsm_found_cells[0].sfn_offset = 230;
    }
    break;
1959 1960 1961 1962
  }

  ind.pnf_cell_search_state.tl.tag = NFAPI_PNF_CELL_SEARCH_STATE_TAG;
  ind.pnf_cell_search_state.length = 3;
1963
  nfapi_pnf_cell_search_ind(config, &ind);
1964 1965 1966
  return 0;
}

1967
int broadcast_detect_request(nfapi_pnf_config_t *config, nfapi_pnf_phy_config_t *phy, nfapi_broadcast_detect_request_t *req) {
1968 1969 1970 1971 1972 1973 1974 1975 1976 1977 1978 1979
  nfapi_broadcast_detect_response_t resp;
  memset(&resp, 0, sizeof(resp));
  resp.header.message_id = NFAPI_BROADCAST_DETECT_RESPONSE;
  resp.header.phy_id = req->header.phy_id;
  resp.error_code = NFAPI_P4_MSG_OK;
  nfapi_pnf_broadcast_detect_resp(config, &resp);
  nfapi_broadcast_detect_indication_t ind;
  memset(&ind, 0, sizeof(ind));
  ind.header.message_id = NFAPI_BROADCAST_DETECT_INDICATION;
  ind.header.phy_id = req->header.phy_id;
  ind.error_code = NFAPI_P4_MSG_OK;

1980 1981 1982 1983 1984 1985 1986 1987 1988
  switch(req->rat_type) {
    case NFAPI_RAT_TYPE_LTE: {
      ind.lte_broadcast_detect_indication.tl.tag = NFAPI_LTE_BROADCAST_DETECT_INDICATION_TAG;
      ind.lte_broadcast_detect_indication.number_of_tx_antenna = 1;
      ind.lte_broadcast_detect_indication.mib_length = 4;
      //ind.lte_broadcast_detect_indication.mib...
      ind.lte_broadcast_detect_indication.sfn_offset = 77;
    }
    break;
1989

1990 1991 1992 1993 1994
    case NFAPI_RAT_TYPE_UTRAN: {
      ind.utran_broadcast_detect_indication.tl.tag = NFAPI_UTRAN_BROADCAST_DETECT_INDICATION_TAG;
      ind.utran_broadcast_detect_indication.mib_length = 4;
    }
    break;
1995 1996 1997 1998
  }

  ind.pnf_cell_broadcast_state.tl.tag = NFAPI_PNF_CELL_BROADCAST_STATE_TAG;
  ind.pnf_cell_broadcast_state.length = 3;
1999
  nfapi_pnf_broadcast_detect_ind(config, &ind);
2000 2001 2002
  return 0;
}

2003
int system_information_schedule_request(nfapi_pnf_config_t *config, nfapi_pnf_phy_config_t *phy, nfapi_system_information_schedule_request_t *req) {
2004 2005 2006 2007 2008 2009 2010 2011 2012 2013 2014 2015 2016 2017 2018
  nfapi_system_information_schedule_response_t resp;
  memset(&resp, 0, sizeof(resp));
  resp.header.message_id = NFAPI_SYSTEM_INFORMATION_SCHEDULE_RESPONSE;
  resp.header.phy_id = req->header.phy_id;
  resp.error_code = NFAPI_P4_MSG_OK;
  nfapi_pnf_system_information_schedule_resp(config, &resp);
  nfapi_system_information_schedule_indication_t ind;
  memset(&ind, 0, sizeof(ind));
  ind.header.message_id = NFAPI_SYSTEM_INFORMATION_SCHEDULE_INDICATION;
  ind.header.phy_id = req->header.phy_id;
  ind.error_code = NFAPI_P4_MSG_OK;
  ind.lte_system_information_indication.tl.tag = NFAPI_LTE_SYSTEM_INFORMATION_INDICATION_TAG;
  ind.lte_system_information_indication.sib_type = 3;
  ind.lte_system_information_indication.sib_length = 5;
  //ind.lte_system_information_indication.sib...
2019
  nfapi_pnf_system_information_schedule_ind(config, &ind);
2020 2021 2022
  return 0;
}

2023
int system_information_request(nfapi_pnf_config_t *config, nfapi_pnf_phy_config_t *phy, nfapi_system_information_request_t *req) {
2024 2025 2026 2027 2028 2029 2030 2031 2032 2033 2034 2035
  nfapi_system_information_response_t resp;
  memset(&resp, 0, sizeof(resp));
  resp.header.message_id = NFAPI_SYSTEM_INFORMATION_RESPONSE;
  resp.header.phy_id = req->header.phy_id;
  resp.error_code = NFAPI_P4_MSG_OK;
  nfapi_pnf_system_information_resp(config, &resp);
  nfapi_system_information_indication_t ind;
  memset(&ind, 0, sizeof(ind));
  ind.header.message_id = NFAPI_SYSTEM_INFORMATION_INDICATION;
  ind.header.phy_id = req->header.phy_id;
  ind.error_code = NFAPI_P4_MSG_OK;

2036 2037 2038 2039 2040 2041 2042 2043
  switch(req->rat_type) {
    case NFAPI_RAT_TYPE_LTE: {
      ind.lte_system_information_indication.tl.tag = NFAPI_LTE_SYSTEM_INFORMATION_INDICATION_TAG;
      ind.lte_system_information_indication.sib_type = 1;
      ind.lte_system_information_indication.sib_length = 3;
      //ind.lte_system_information_indication.sib...
    }
    break;
2044

2045 2046 2047 2048 2049 2050
    case NFAPI_RAT_TYPE_UTRAN: {
      ind.utran_system_information_indication.tl.tag = NFAPI_UTRAN_SYSTEM_INFORMATION_INDICATION_TAG;
      ind.utran_system_information_indication.sib_length = 3;
      //ind.utran_system_information_indication.sib...
    }
    break;
2051

2052 2053 2054 2055 2056 2057
    case NFAPI_RAT_TYPE_GERAN: {
      ind.geran_system_information_indication.tl.tag = NFAPI_GERAN_SYSTEM_INFORMATION_INDICATION_TAG;
      ind.geran_system_information_indication.si_length = 3;
      //ind.geran_system_information_indication.si...
    }
    break;
2058 2059
  }

2060
  nfapi_pnf_system_information_ind(config, &ind);
2061 2062 2063
  return 0;
}

2064
int nmm_stop_request(nfapi_pnf_config_t *config, nfapi_pnf_phy_config_t *phy, nfapi_nmm_stop_request_t *req) {
2065 2066 2067 2068 2069 2070 2071 2072 2073
  nfapi_nmm_stop_response_t resp;
  memset(&resp, 0, sizeof(resp));
  resp.header.message_id = NFAPI_NMM_STOP_RESPONSE;
  resp.header.phy_id = req->header.phy_id;
  resp.error_code = NFAPI_P4_MSG_OK;
  nfapi_pnf_nmm_stop_resp(config, &resp);
  return 0;
}

2074
int vendor_ext(nfapi_pnf_config_t *config, nfapi_p4_p5_message_header_t *msg) {
2075 2076
  NFAPI_TRACE(NFAPI_TRACE_INFO, "[PNF] P5 %s %p\n", __FUNCTION__, msg);

2077 2078 2079 2080 2081 2082 2083 2084 2085 2086 2087 2088
  switch(msg->message_id) {
    case P5_VENDOR_EXT_REQ: {
      vendor_ext_p5_req *req = (vendor_ext_p5_req *)msg;
      NFAPI_TRACE(NFAPI_TRACE_INFO, "[PNF] P5 Vendor Ext Req (%d %d)\n", req->dummy1, req->dummy2);
      // send back the P5_VENDOR_EXT_RSP
      vendor_ext_p5_rsp rsp;
      memset(&rsp, 0, sizeof(rsp));
      rsp.header.message_id = P5_VENDOR_EXT_RSP;
      rsp.error_code = NFAPI_MSG_OK;
      nfapi_pnf_vendor_extension(config, &rsp.header, sizeof(vendor_ext_p5_rsp));
    }
    break;
2089 2090 2091 2092 2093
  }

  return 0;
}

2094
nfapi_p4_p5_message_header_t *pnf_sim_allocate_p4_p5_vendor_ext(uint16_t message_id, uint16_t *msg_size) {
2095 2096
  if(message_id == P5_VENDOR_EXT_REQ) {
    (*msg_size) = sizeof(vendor_ext_p5_req);
2097
    return (nfapi_p4_p5_message_header_t *)malloc(sizeof(vendor_ext_p5_req));
2098 2099 2100 2101 2102
  }

  return 0;
}

2103
void pnf_sim_deallocate_p4_p5_vendor_ext(nfapi_p4_p5_message_header_t *header) {
2104 2105 2106
  free(header);
}

2107
int pnf_sim_pack_p4_p5_vendor_extension(nfapi_p4_p5_message_header_t *header, uint8_t **ppWritePackedMsg, uint8_t *end, nfapi_p4_p5_codec_config_t *config) {
2108 2109
  //NFAPI_TRACE(NFAPI_TRACE_INFO, "%s\n", __FUNCTION__);
  if(header->message_id == P5_VENDOR_EXT_RSP) {
2110
    vendor_ext_p5_rsp *rsp = (vendor_ext_p5_rsp *)(header);
2111 2112
    return (!push16(rsp->error_code, ppWritePackedMsg, end));
  }
2113

2114 2115 2116
  return 0;
}

2117
int pnf_sim_unpack_p4_p5_vendor_extension(nfapi_p4_p5_message_header_t *header, uint8_t **ppReadPackedMessage, uint8_t *end, nfapi_p4_p5_codec_config_t *codec) {
2118 2119
  //NFAPI_TRACE(NFAPI_TRACE_INFO, "%s\n", __FUNCTION__);
  if(header->message_id == P5_VENDOR_EXT_REQ) {
2120
    vendor_ext_p5_req *req = (vendor_ext_p5_req *)(header);
2121
    return (!(pull16(ppReadPackedMessage, &req->dummy1, end) &&
2122
              pull16(ppReadPackedMessage, &req->dummy2, end)));
2123 2124
    //NFAPI_TRACE(NFAPI_TRACE_INFO, "%s (%d %d)\n", __FUNCTION__, req->dummy1, req->dummy2);
  }
2125

2126 2127 2128 2129
  return 0;
}

/*------------------------------------------------------------------------------*/
2130
void *pnf_start_thread(void *ptr) {
2131
  NFAPI_TRACE(NFAPI_TRACE_INFO, "[PNF] IN PNF NFAPI start thread %s\n", __FUNCTION__);
2132
  nfapi_pnf_config_t *config = (nfapi_pnf_config_t *)ptr;
2133 2134 2135 2136
  struct sched_param sp;
  sp.sched_priority = 20;
  pthread_setschedparam(pthread_self(),SCHED_FIFO,&sp);
  nfapi_pnf_start(config);
2137
  return (void *)0;
2138 2139
}

Mahesh's avatar
Mahesh committed
2140 2141 2142 2143 2144 2145 2146 2147 2148 2149 2150
void *pnf_nr_start_thread(void *ptr) {
  NFAPI_TRACE(NFAPI_TRACE_INFO, "[PNF] IN PNF NFAPI start thread %s\n", __FUNCTION__);
  nfapi_pnf_config_t *config = (nfapi_pnf_config_t *)ptr;
  struct sched_param sp;
  sp.sched_priority = 20;
  pthread_setschedparam(pthread_self(),SCHED_FIFO,&sp);
  nfapi_nr_pnf_start(config);
  return (void *)0;
}

void configure_nr_nfapi_pnf(char *vnf_ip_addr, int vnf_p5_port, char *pnf_ip_addr, int pnf_p7_port, int vnf_p7_port) {
2151
  printf("%s() PNF\n\n\n\n\n\n", __FUNCTION__);
2152
    nfapi_setmode(NFAPI_MODE_PNF);  // PNF!
2153

2154
  nfapi_pnf_config_t *config = nfapi_pnf_config_create();
2155 2156 2157
  config->vnf_ip_addr = vnf_ip_addr;
  config->vnf_p5_port = vnf_p5_port;
  pnf.phys[0].udp.enabled = 1;
2158
  pnf.phys[0].udp.rx_port = pnf_p7_port;
2159 2160 2161
  pnf.phys[0].udp.tx_port = vnf_p7_port;
  strcpy(pnf.phys[0].udp.tx_addr, vnf_ip_addr);
  strcpy(pnf.phys[0].local_addr, pnf_ip_addr);
2162 2163 2164 2165
  printf("%s() VNF:%s:%d PNF_PHY[addr:%s UDP:tx_addr:%s:%u rx:%u]\n",
         __FUNCTION__,
         config->vnf_ip_addr,
         config->vnf_p5_port,
2166
         pnf.phys[0].local_addr,
2167 2168
         pnf.phys[0].udp.tx_addr,
         pnf.phys[0].udp.tx_port,
2169
         pnf.phys[0].udp.rx_port);
Mahesh's avatar
Mahesh committed
2170 2171 2172 2173
  config->cell_search_req = &cell_search_request;
         
    
  //config->pnf_nr_param_req = &pnf_nr_param_request;
Mahesh's avatar
Mahesh committed
2174 2175 2176 2177 2178 2179 2180 2181 2182 2183 2184 2185 2186 2187 2188 2189 2190 2191 2192 2193 2194 2195 2196 2197 2198 2199 2200 2201 2202 2203 2204
  config->pnf_nr_param_req = &pnf_nr_param_request;
  config->pnf_nr_config_req = &pnf_nr_config_request;
  config->pnf_nr_start_req = &pnf_nr_start_request;
  config->pnf_stop_req = &pnf_stop_request;
  config->nr_param_req = &nr_param_request;
  config->nr_config_req = &nr_config_request;
  config->nr_start_req = &nr_start_request;
  config->measurement_req = &measurement_request;
  config->rssi_req = &rssi_request;
  config->broadcast_detect_req = &broadcast_detect_request;
  config->system_information_schedule_req = &system_information_schedule_request;
  config->system_information_req = &system_information_request;
  config->nmm_stop_req = &nmm_stop_request;
  config->vendor_ext = &vendor_ext;
  config->trace = &pnf_nfapi_trace;
  config->user_data = &pnf;
  // To allow custom vendor extentions to be added to nfapi
  config->codec_config.unpack_vendor_extension_tlv = &pnf_sim_unpack_vendor_extension_tlv;
  config->codec_config.pack_vendor_extension_tlv = &pnf_sim_pack_vendor_extention_tlv;
  config->allocate_p4_p5_vendor_ext = &pnf_sim_allocate_p4_p5_vendor_ext;
  config->deallocate_p4_p5_vendor_ext = &pnf_sim_deallocate_p4_p5_vendor_ext;
  config->codec_config.unpack_p4_p5_vendor_extension = &pnf_sim_unpack_p4_p5_vendor_extension;
  config->codec_config.pack_p4_p5_vendor_extension = &pnf_sim_pack_p4_p5_vendor_extension;
  NFAPI_TRACE(NFAPI_TRACE_INFO, "[PNF] Creating PNF NFAPI start thread %s\n", __FUNCTION__);
  pthread_create(&pnf_start_pthread, NULL, &pnf_nr_start_thread, config);
  pthread_setname_np(pnf_start_pthread, "NFAPI_PNF");
}

void configure_nfapi_pnf(char *vnf_ip_addr, int vnf_p5_port, char *pnf_ip_addr, int pnf_p7_port, int vnf_p7_port) {
  printf("%s() PNF\n\n\n\n\n\n", __FUNCTION__);

2205
  if(NFAPI_MODE!=NFAPI_UE_STUB_PNF && NFAPI_MODE!=NFAPI_MODE_STANDALONE_PNF) {
Mahesh's avatar
Mahesh committed
2206 2207 2208 2209 2210 2211
    nfapi_setmode(NFAPI_MODE_PNF);  // PNF!
  }
  nfapi_pnf_config_t *config = nfapi_pnf_config_create();
  config->vnf_ip_addr = vnf_ip_addr;
  config->vnf_p5_port = vnf_p5_port;
  pnf.phys[0].udp.enabled = 1;
2212
  pnf.phys[0].udp.rx_port = pnf_p7_port;
Mahesh's avatar
Mahesh committed
2213 2214 2215
  pnf.phys[0].udp.tx_port = vnf_p7_port;
  strcpy(pnf.phys[0].udp.tx_addr, vnf_ip_addr);
  strcpy(pnf.phys[0].local_addr, pnf_ip_addr);
2216
  printf("%s() VNF:%s:%d PNF_PHY[addr:%s UDP:tx_addr:%s:%u rx:%u]\n",
Mahesh's avatar
Mahesh committed
2217
         __FUNCTION__,
2218 2219
         config->vnf_ip_addr,
         config->vnf_p5_port,
Mahesh's avatar
Mahesh committed
2220
         pnf.phys[0].local_addr,
2221 2222
         pnf.phys[0].udp.tx_addr,
         pnf.phys[0].udp.tx_port,
Mahesh's avatar
Mahesh committed
2223
         pnf.phys[0].udp.rx_port);
2224 2225 2226 2227 2228 2229 2230 2231 2232
  config->pnf_param_req = &pnf_param_request;
  config->pnf_config_req = &pnf_config_request;
  config->pnf_start_req = &pnf_start_request;
  config->pnf_stop_req = &pnf_stop_request;
  config->param_req = &param_request;
  config->config_req = &config_request;
  config->start_req = &start_request;
  config->measurement_req = &measurement_request;
  config->rssi_req = &rssi_request;
Mahesh's avatar
Mahesh committed
2233
  config->cell_search_req = &cell_search_request;
2234 2235 2236 2237 2238 2239 2240 2241 2242 2243 2244 2245 2246 2247 2248 2249 2250 2251 2252 2253 2254 2255
  config->broadcast_detect_req = &broadcast_detect_request;
  config->system_information_schedule_req = &system_information_schedule_request;
  config->system_information_req = &system_information_request;
  config->nmm_stop_req = &nmm_stop_request;
  config->vendor_ext = &vendor_ext;
  config->trace = &pnf_nfapi_trace;
  config->user_data = &pnf;
  // To allow custom vendor extentions to be added to nfapi
  config->codec_config.unpack_vendor_extension_tlv = &pnf_sim_unpack_vendor_extension_tlv;
  config->codec_config.pack_vendor_extension_tlv = &pnf_sim_pack_vendor_extention_tlv;
  config->allocate_p4_p5_vendor_ext = &pnf_sim_allocate_p4_p5_vendor_ext;
  config->deallocate_p4_p5_vendor_ext = &pnf_sim_deallocate_p4_p5_vendor_ext;
  config->codec_config.unpack_p4_p5_vendor_extension = &pnf_sim_unpack_p4_p5_vendor_extension;
  config->codec_config.pack_p4_p5_vendor_extension = &pnf_sim_pack_p4_p5_vendor_extension;
  NFAPI_TRACE(NFAPI_TRACE_INFO, "[PNF] Creating PNF NFAPI start thread %s\n", __FUNCTION__);
  pthread_create(&pnf_start_pthread, NULL, &pnf_start_thread, config);
  pthread_setname_np(pnf_start_pthread, "NFAPI_PNF");
}

void oai_subframe_ind(uint16_t sfn, uint16_t sf) {
  //LOG_D(PHY,"%s(sfn:%d, sf:%d)\n", __FUNCTION__, sfn, sf);

2256
  //TODO FIXME - HACK - using a global to bodge it in
MaheshK1995's avatar
MaheshK1995 committed
2257 2258 2259 2260
  if (p7_config_g != NULL && sync_var==0) {
    uint16_t sfn_sf_tx = sfn<<4 | sf; 

    if ((sfn % 100 == 0) && sf==0) {
2261
      NFAPI_TRACE(NFAPI_TRACE_INFO, "[PNF] (sfn:%u sf:%u) SFN/SF(TX):%u\n", sfn, sf, NFAPI_SFNSF2DEC(sfn_sf_tx));
MaheshK1995's avatar
MaheshK1995 committed
2262 2263 2264 2265 2266
    }

    int subframe_ret = nfapi_pnf_p7_subframe_ind(p7_config_g, p7_config_g->phy_id, sfn_sf_tx);

    if (subframe_ret) {
2267
      NFAPI_TRACE(NFAPI_TRACE_INFO, "[PNF] (frame:%u subframe:%u) SFN/SF(TX):%u - PROBLEM with pnf_p7_subframe_ind()\n", sfn, sf, sfn_sf_tx);
MaheshK1995's avatar
MaheshK1995 committed
2268 2269 2270 2271 2272 2273 2274
    } else {
      //NFAPI_TRACE(NFAPI_TRACE_INFO, "***NFAPI subframe handler finished *** \n");
    }
  } else {
  }
}

2275
void handle_nr_slot_ind(uint16_t sfn, uint16_t slot) {
MaheshK1995's avatar
MaheshK1995 committed
2276

2277 2278 2279 2280 2281 2282 2283
    //send VNF slot indication, which is aligned with TX thread, so that it can call the scheduler
    nfapi_nr_slot_indication_scf_t *ind;
    ind = (nfapi_nr_slot_indication_scf_t *) malloc(sizeof(nfapi_nr_slot_indication_scf_t));
    uint8_t slot_ahead = 6;
    uint32_t sfn_slot_tx = sfnslot_add_slot(sfn, slot, slot_ahead);
    uint16_t sfn_tx = NFAPI_SFNSLOT2SFN(sfn_slot_tx);
    uint8_t slot_tx = NFAPI_SFNSLOT2SLOT(sfn_slot_tx);
MaheshK1995's avatar
MaheshK1995 committed
2284

2285 2286 2287 2288 2289
    ind->sfn = sfn_tx;
    ind->slot = slot_tx;
    oai_nfapi_nr_slot_indication(ind); 

    //copy data from appropriate p7 slot buffers into channel structures for PHY processing
2290
    nfapi_pnf_p7_slot_ind(p7_config_g, p7_config_g->phy_id, sfn, slot); 
MaheshK1995's avatar
MaheshK1995 committed
2291

2292
    return;
2293 2294 2295
}

int oai_nfapi_rach_ind(nfapi_rach_indication_t *rach_ind) {
2296
  rach_ind->header.phy_id = 1; // HACK TODO FIXME - need to pass this around!!!!
2297 2298 2299 2300 2301
  LOG_D(PHY, "%s() sfn_sf:%d preambles:%d\n", __FUNCTION__, NFAPI_SFNSF2DEC(rach_ind->sfn_sf), rach_ind->rach_indication_body.number_of_preambles);
  return nfapi_pnf_p7_rach_ind(p7_config_g, rach_ind);
}

int oai_nfapi_harq_indication(nfapi_harq_indication_t *harq_ind) {
2302
  harq_ind->header.phy_id = 1; // HACK TODO FIXME - need to pass this around!!!!
2303 2304 2305 2306 2307 2308 2309 2310 2311 2312 2313
  harq_ind->header.message_id = NFAPI_HARQ_INDICATION;
  LOG_D(PHY, "%s() sfn_sf:%d number_of_harqs:%d\n", __FUNCTION__, NFAPI_SFNSF2DEC(harq_ind->sfn_sf), harq_ind->harq_indication_body.number_of_harqs);
  int retval = nfapi_pnf_p7_harq_ind(p7_config_g, harq_ind);

  if (retval != 0)
    LOG_E(PHY, "%s() sfn_sf:%d number_of_harqs:%d nfapi_pnf_p7_harq_ind()=%d\n", __FUNCTION__, NFAPI_SFNSF2DEC(harq_ind->sfn_sf), harq_ind->harq_indication_body.number_of_harqs, retval);

  return retval;
}

int oai_nfapi_crc_indication(nfapi_crc_indication_t *crc_ind) {
2314
  crc_ind->header.phy_id = 1; // HACK TODO FIXME - need to pass this around!!!!
2315 2316 2317 2318 2319 2320
  crc_ind->header.message_id = NFAPI_CRC_INDICATION;
  //LOG_D(PHY, "%s() sfn_sf:%d number_of_crcs:%d\n", __FUNCTION__, NFAPI_SFNSF2DEC(crc_ind->sfn_sf), crc_ind->crc_indication_body.number_of_crcs);
  return nfapi_pnf_p7_crc_ind(p7_config_g, crc_ind);
}

int oai_nfapi_cqi_indication(nfapi_cqi_indication_t *ind) {
2321
  ind->header.phy_id = 1; // HACK TODO FIXME - need to pass this around!!!!
2322 2323 2324 2325 2326 2327
  ind->header.message_id = NFAPI_RX_CQI_INDICATION;
  //LOG_D(PHY, "%s() sfn_sf:%d number_of_cqis:%d\n", __FUNCTION__, NFAPI_SFNSF2DEC(ind->sfn_sf), ind->cqi_indication_body.number_of_cqis);
  return nfapi_pnf_p7_cqi_ind(p7_config_g, ind);
}

int oai_nfapi_rx_ind(nfapi_rx_indication_t *ind) {
2328
  ind->header.phy_id = 1; // HACK TODO FIXME - need to pass this around!!!!
2329 2330 2331 2332 2333 2334 2335 2336
  ind->header.message_id = NFAPI_RX_ULSCH_INDICATION;
  int retval = nfapi_pnf_p7_rx_ind(p7_config_g, ind);
  //LOG_D(PHY,"%s() SFN/SF:%d pdus:%d retval:%d\n", __FUNCTION__, NFAPI_SFNSF2DEC(ind->sfn_sf), ind->rx_indication_body.number_of_pdus, retval);
  //free(ind.rx_indication_body.rx_pdu_list);
  return retval;
}

int oai_nfapi_sr_indication(nfapi_sr_indication_t *ind) {
2337
  ind->header.phy_id = 1; // HACK TODO FIXME - need to pass this around!!!!
2338 2339 2340 2341 2342
  int retval = nfapi_pnf_p7_sr_ind(p7_config_g, ind);
  //LOG_D(PHY,"%s() SFN/SF:%d srs:%d retval:%d\n", __FUNCTION__, NFAPI_SFNSF2DEC(ind->sfn_sf), ind->sr_indication_body.number_of_srs, retval);
  //free(ind.rx_indication_body.rx_pdu_list);
  return retval;
}
Mahesh's avatar
Mahesh committed
2343 2344 2345

//NR UPLINK INDICATION

2346 2347 2348 2349 2350 2351
int oai_nfapi_nr_slot_indication(nfapi_nr_slot_indication_scf_t *ind) {
  ind->header.phy_id = 1;
  ind->header.message_id = NFAPI_NR_PHY_MSG_TYPE_SLOT_INDICATION;
  return nfapi_pnf_p7_nr_slot_ind(p7_config_g, ind);
}

Mahesh's avatar
Mahesh committed
2352
int oai_nfapi_nr_rx_data_indication(nfapi_nr_rx_data_indication_t *ind) {
2353
  ind->header.phy_id = 1; // HACK TODO FIXME - need to pass this around!!!!
Mahesh's avatar
Mahesh committed
2354 2355 2356 2357 2358
  ind->header.message_id = NFAPI_NR_PHY_MSG_TYPE_RX_DATA_INDICATION;
  return nfapi_pnf_p7_nr_rx_data_ind(p7_config_g, ind);
}

int oai_nfapi_nr_crc_indication(nfapi_nr_crc_indication_t *ind) {
2359
  ind->header.phy_id = 1; // HACK TODO FIXME - need to pass this around!!!!
Mahesh's avatar
Mahesh committed
2360 2361 2362 2363 2364
  ind->header.message_id = NFAPI_NR_PHY_MSG_TYPE_CRC_INDICATION;
  return nfapi_pnf_p7_nr_crc_ind(p7_config_g, ind);
}

int oai_nfapi_nr_srs_indication(nfapi_nr_srs_indication_t *ind) {
2365
  ind->header.phy_id = 1; // HACK TODO FIXME - need to pass this around!!!!
Mahesh's avatar
Mahesh committed
2366 2367 2368 2369 2370
  ind->header.message_id = NFAPI_NR_PHY_MSG_TYPE_SRS_INDICATION;
  return nfapi_pnf_p7_nr_srs_ind(p7_config_g, ind);
}

int oai_nfapi_nr_uci_indication(nfapi_nr_uci_indication_t *ind) {
2371
  ind->header.phy_id = 1; // HACK TODO FIXME - need to pass this around!!!!
Mahesh's avatar
Mahesh committed
2372 2373 2374 2375 2376
  ind->header.message_id = NFAPI_NR_PHY_MSG_TYPE_UCI_INDICATION;
  return nfapi_pnf_p7_nr_uci_ind(p7_config_g, ind);
}

int oai_nfapi_nr_rach_indication(nfapi_nr_rach_indication_t *ind) {
2377
  ind->header.phy_id = 1; // HACK TODO FIXME - need to pass this around!!!!
Mahesh's avatar
Mahesh committed
2378 2379 2380 2381
  ind->header.message_id = NFAPI_NR_PHY_MSG_TYPE_RACH_INDICATION;
  return nfapi_pnf_p7_nr_rach_ind(p7_config_g, ind);
}