diff --git a/cmake_targets/CMakeLists.txt b/cmake_targets/CMakeLists.txt index 613d00e70f74133b73b3a54ac8db4d3a622de9f7..05d32b74df3ec07a38b5b5427b105fbb5afeecf9 100644 --- a/cmake_targets/CMakeLists.txt +++ b/cmake_targets/CMakeLists.txt @@ -1330,6 +1330,9 @@ add_library(ldpc MODULE ${PHY_LDPC_OPTIM8SEGMULTI_SRC} ) add_library(coding MODULE ${PHY_TURBOSRC} ) +add_library(dfts MODULE ${OPENAIR1_DIR}/PHY/TOOLS/oai_dfts.c ) + + set(PHY_SRC_COMMON ${OPENAIR1_DIR}/PHY/LTE_TRANSPORT/dci_tools_common.c ${OPENAIR1_DIR}/PHY/LTE_TRANSPORT/lte_mcs.c @@ -1370,7 +1373,7 @@ set(PHY_SRC_COMMON ${OPENAIR1_DIR}/PHY/INIT/lte_parms.c ${OPENAIR1_DIR}/PHY/INIT/lte_param_init.c ${OPENAIR1_DIR}/PHY/TOOLS/cadd_vv.c - ${OPENAIR1_DIR}/PHY/TOOLS/lte_dfts.c + ${OPENAIR1_DIR}/PHY/TOOLS/dfts_load.c ${OPENAIR1_DIR}/PHY/TOOLS/log2_approx.c ${OPENAIR1_DIR}/PHY/TOOLS/cmult_sv.c ${OPENAIR1_DIR}/PHY/TOOLS/cmult_vv.c @@ -1585,6 +1588,7 @@ endif () add_library(PHY_COMMON ${PHY_SRC_COMMON}) add_dependencies(PHY_COMMON rrc_flag) +add_dependencies(PHY_COMMON dfts) add_library(PHY ${PHY_SRC}) add_dependencies(PHY rrc_flag) diff --git a/cmake_targets/autotests/test_case_list.xml b/cmake_targets/autotests/test_case_list.xml index b3954db1fd2f3bba8dd14156053eb9909f381f26..0e6435aaf3d2cb3dd05284d72bf8139d1bcfd2c0 100644 --- a/cmake_targets/autotests/test_case_list.xml +++ b/cmake_targets/autotests/test_case_list.xml @@ -1104,9 +1104,8 @@ -n100 -R217 -a80 -s5 -n100 -R217 -a110 -s5 -b100 -n100 -e27 -s30 - -n100 -e16 -s10 - </main_exec_args> - <tags>nr_dlsim.test1 nr_dlsim.test2 nr_dlsim.test3 nr_dlsim.test4 nr_dlsim.test5 nr_dlsim.test6 nr_dlsim.test7 nr_dlsim.test8 nr_dlsim.test9 nr_dlsim.test10 </tags> + -n100 -e16 -s10</main_exec_args> + <tags>nr_dlsim.test1 nr_dlsim.test2 nr_dlsim.test3 nr_dlsim.test4 nr_dlsim.test5 nr_dlsim.test6 nr_dlsim.test7 nr_dlsim.test8 nr_dlsim.test9 nr_dlsim.test10</tags> <search_expr_true>PDSCH test OK</search_expr_true> <search_expr_false>segmentation fault|assertion|exiting|fatal</search_expr_false> <nruns>3</nruns> @@ -1248,11 +1247,11 @@ <pre_exec>$OPENAIR_DIR/cmake_targets/autotests/tools/free_mem.bash</pre_exec> <pre_exec_args></pre_exec_args> <main_exec> $OPENAIR_DIR/targets/bin/nr_ulsim.Rel15</main_exec> - <main_exec_args>-n100 -m9 -r106 -s0 + <main_exec_args>-n100 -m9 -r106 -s5 -n100 -m16 -s10 -n100 -m28 -s20 - -n100 -m9 -R217 -r217 -s0 - -n100 -m9 -R273 -r273 -s0</main_exec_args> + -n100 -m9 -R217 -r217 -s5 + -n100 -m9 -R273 -r273 -s5</main_exec_args> <tags>nr_ulsim.test1 nr_ulsim.test2 nr_ulsim.test3 nr_ulsim.test4 nr_ulsim.test5</tags> <search_expr_true>PUSCH test OK</search_expr_true> <search_expr_false>segmentation fault|assertion|exiting|fatal</search_expr_false> diff --git a/cmake_targets/tools/build_helper b/cmake_targets/tools/build_helper index 818b1fd79c70a486933ab1a1cacc7b0b3492be1e..8e4ae59a7faf90c5c10e70037ff2d52913b27491 100755 --- a/cmake_targets/tools/build_helper +++ b/cmake_targets/tools/build_helper @@ -217,7 +217,7 @@ install_protobuf_from_source(){ #tar -xzvf protobuf-2.6.1.tar.gz --owner $USER --group $USER --no-same-owner #cd protobuf-2.6.1/ rm -rf /tmp/protobuf-cpp-3.3.0.tar.gz* /tmp/protobuf-3.3.0 - wget https://github.com/google/protobuf/releases/download/v3.3.0/protobuf-cpp-3.3.0.tar.gz + wget --tries=3 --retry-connrefused https://github.com/google/protobuf/releases/download/v3.3.0/protobuf-cpp-3.3.0.tar.gz tar -xzvf protobuf-cpp-3.3.0.tar.gz --owner $USER --group $(groups | cut -d" " -f1) --no-same-owner cd protobuf-3.3.0/ ./configure @@ -353,8 +353,8 @@ install_bladerf_driver_from_source(){ $SUDO ldconfig echo "Downloading FPGA and firmware images" cd /tmp/bladeRF - wget https://www.nuand.com/fx3/bladeRF_fw_latest.img - wget https://www.nuand.com/fpga/hostedx40-latest.rbf + wget --tries=3 --retry-connrefused https://www.nuand.com/fx3/bladeRF_fw_latest.img + wget --tries=3 --retry-connrefused https://www.nuand.com/fpga/hostedx40-latest.rbf sudo mkdir -p /usr/share/Nuand/bladeRF sudo mv bladeRF_fw_latest.img /usr/share/Nuand/bladeRF/bladeRF_fw.img sudo mv hostedx40-latest.rbf /usr/share/Nuand/bladeRF/hostedx40.rbf @@ -567,7 +567,7 @@ check_install_additional_tools (){ echo_info "Installing Netinterfaces package. The logfile for installation is in $log_netiface" ( $SUDO rm -fr /tmp/netifaces-0.10.4.tar.gz /tmp/netifaces - wget -P /tmp https://pypi.python.org/packages/18/fa/dd13d4910aea339c0bb87d2b3838d8fd923c11869b1f6e741dbd0ff3bc00/netifaces-0.10.4.tar.gz + wget --tries=3 --retry-connrefused -P /tmp https://pypi.python.org/packages/18/fa/dd13d4910aea339c0bb87d2b3838d8fd923c11869b1f6e741dbd0ff3bc00/netifaces-0.10.4.tar.gz tar -xzvf /tmp/netifaces-0.10.4.tar.gz -C /tmp cd /tmp/netifaces-0.10.4 $SUDO python setup.py install diff --git a/common/utils/telnetsrv/telnetsrv_enb_measurements.c b/common/utils/telnetsrv/telnetsrv_enb_measurements.c index 9c5c5b675bbd3830560e72cff6413da79cd2e6fe..8830173e6d55272e1d42473ebdb84a7f06e45d8b 100644 --- a/common/utils/telnetsrv/telnetsrv_enb_measurements.c +++ b/common/utils/telnetsrv/telnetsrv_enb_measurements.c @@ -110,13 +110,13 @@ void measurcmd_display_pdcpcpu(telnet_printfunc_t prnt) { void measurcmd_display_macstats_ue(telnet_printfunc_t prnt) { - UE_list_t *UE_list = &(RC.mac[eNB_id]->UE_list); + UE_info_t *UE_info = &(RC.mac[eNB_id]->UE_info); - for (int UE_id=UE_list->head; UE_id>=0; UE_id=UE_list->next[UE_id]) { - for (int i=0; i<UE_list->numactiveCCs[UE_id]; i++) { - int CC_id = UE_list->ordered_CCids[i][UE_id]; + for (int UE_id=UE_info->list.head; UE_id>=0; UE_id=UE_info->list.next[UE_id]) { + for (int i=0; i<UE_info->numactiveCCs[UE_id]; i++) { + int CC_id = UE_info->ordered_CCids[i][UE_id]; prnt("%s UE %i Id %i CCid %i %s\n",HDR,i,UE_id,CC_id,HDR); - eNB_UE_STATS *macuestatptr = &(UE_list->eNB_UE_stats[CC_id][UE_id]); + eNB_UE_STATS *macuestatptr = &(UE_info->eNB_UE_stats[CC_id][UE_id]); telnet_ltemeasurdef_t statsptr[]=LTEMAC_UEMEASURE; measurcmd_display_measures(prnt, statsptr, sizeof(statsptr)/sizeof(telnet_ltemeasurdef_t)); } @@ -155,7 +155,7 @@ void measurcmd_display_one_rlcstat(telnet_printfunc_t prnt, int UE_id, telnet_lt void measurcmd_display_rlcstats(telnet_printfunc_t prnt) { protocol_ctxt_t ctxt; - UE_list_t *UE_list = &(RC.mac[eNB_id]->UE_list); + UE_info_t *UE_info = &(RC.mac[eNB_id]->UE_info); telnet_ltemeasurdef_t statsptr[]=LTE_RLCMEASURE; int num_rlcmeasure = sizeof(statsptr)/sizeof(telnet_ltemeasurdef_t ); unsigned int *rlcstats = malloc(num_rlcmeasure*sizeof(unsigned int)); @@ -165,9 +165,9 @@ void measurcmd_display_rlcstats(telnet_printfunc_t prnt) { statsptr[i].vptr = rlcstats + i; } - for (int UE_id=UE_list->head; UE_id>=0; UE_id=UE_list->next[UE_id]) { + for (int UE_id=UE_info->list.head; UE_id>=0; UE_id=UE_info->list.next[UE_id]) { #define NB_eNB_INST 1 - PROTOCOL_CTXT_SET_BY_MODULE_ID(&ctxt,eNB_id, ENB_FLAG_YES,UE_list->eNB_UE_stats[0][UE_id].crnti, + PROTOCOL_CTXT_SET_BY_MODULE_ID(&ctxt,eNB_id, ENB_FLAG_YES,UE_info->eNB_UE_stats[0][UE_id].crnti, eNB->frame,eNB->subframe,eNB_id); measurcmd_display_one_rlcstat(prnt, UE_id, statsptr, num_rlcmeasure, rlcstats, "DCCH", &ctxt, SRB_FLAG_YES, DCCH); measurcmd_display_one_rlcstat(prnt, UE_id, statsptr, num_rlcmeasure, rlcstats, "DTCH", &ctxt, SRB_FLAG_NO, DTCH-2); diff --git a/executables/nr-gnb.c b/executables/nr-gnb.c index 660a2d36553572fe45e40ecb122d7f33d8cbcd58..9003f6835778ce51024d387ac2cfef93f86d7362 100644 --- a/executables/nr-gnb.c +++ b/executables/nr-gnb.c @@ -62,9 +62,7 @@ #include "PHY/phy_extern.h" -#include "LAYER2/MAC/mac.h" #include "LAYER2/NR_MAC_COMMON/nr_mac_extern.h" -#include "LAYER2/MAC/mac_proto.h" #include "RRC/LTE/rrc_extern.h" #include "PHY_INTERFACE/phy_interface.h" #include "common/utils/LOG/log_extern.h" @@ -161,7 +159,7 @@ static inline int rxtx(PHY_VARS_gNB *gNB, int frame_rx, int slot_rx, int frame_t oai_subframe_ind(frame_rx, slot_rx); stop_meas(&nfapi_meas); - if (gNB->UL_INFO.rx_ind.rx_indication_body.number_of_pdus|| + /*if (gNB->UL_INFO.rx_ind.rx_indication_body.number_of_pdus|| gNB->UL_INFO.harq_ind.harq_indication_body.number_of_harqs || gNB->UL_INFO.crc_ind.crc_indication_body.number_of_crcs || gNB->UL_INFO.rach_ind.rach_indication_body.number_of_preambles || @@ -175,7 +173,7 @@ static inline int rxtx(PHY_VARS_gNB *gNB, int frame_rx, int slot_rx, int frame_t gNB->UL_INFO.cqi_ind.number_of_cqis, frame_rx, slot_rx, frame_tx, slot_tx); - } + }*/ } // **************************************** @@ -963,12 +961,12 @@ void init_gNB(int single_thread_flag,int wait_for_sync) { gNB->if_inst->NR_PHY_config_req = nr_phy_config_request; memset((void *)&gNB->UL_INFO,0,sizeof(gNB->UL_INFO)); LOG_I(PHY,"Setting indication lists\n"); - gNB->UL_INFO.rx_ind.rx_indication_body.rx_pdu_list = gNB->rx_pdu_list; - gNB->UL_INFO.crc_ind.crc_indication_body.crc_pdu_list = gNB->crc_pdu_list; - gNB->UL_INFO.sr_ind.sr_indication_body.sr_pdu_list = gNB->sr_pdu_list; + gNB->UL_INFO.rx_ind.pdu_list = gNB->rx_pdu_list; + gNB->UL_INFO.crc_ind.crc_list = gNB->crc_pdu_list; + /*gNB->UL_INFO.sr_ind.sr_indication_body.sr_pdu_list = gNB->sr_pdu_list; gNB->UL_INFO.harq_ind.harq_indication_body.harq_pdu_list = gNB->harq_pdu_list; gNB->UL_INFO.cqi_ind.cqi_pdu_list = gNB->cqi_pdu_list; - gNB->UL_INFO.cqi_ind.cqi_raw_pdu_list = gNB->cqi_raw_pdu_list; + gNB->UL_INFO.cqi_ind.cqi_raw_pdu_list = gNB->cqi_raw_pdu_list;*/ gNB->prach_energy_counter = 0; } diff --git a/executables/nr-ru.c b/executables/nr-ru.c index 30ed266ce4ed0c4d9fec8542dafa01ded485c25b..a6970973a648fd0c368123814f55d10ddd952c3c 100644 --- a/executables/nr-ru.c +++ b/executables/nr-ru.c @@ -72,9 +72,7 @@ #include "SCHED/sched_eNB.h" #include "SCHED_NR/sched_nr.h" -#include "LAYER2/MAC/mac.h" #include "LAYER2/NR_MAC_COMMON/nr_mac_extern.h" -#include "LAYER2/MAC/mac_proto.h" #include "RRC/LTE/rrc_extern.h" #include "PHY_INTERFACE/phy_interface.h" @@ -2298,6 +2296,24 @@ void RCconfig_RU(void) RC.ru[j]->openair0_cfg.clock_source = unset; } + if (config_isparamset(RUParamList.paramarray[j], RU_SDR_TME_SRC)) { + if (strcmp(*(RUParamList.paramarray[j][RU_SDR_TME_SRC].strptr), "internal") == 0) { + RC.ru[j]->openair0_cfg.time_source = internal; + LOG_D(PHY, "RU time source set as internal\n"); + } else if (strcmp(*(RUParamList.paramarray[j][RU_SDR_TME_SRC].strptr), "external") == 0) { + RC.ru[j]->openair0_cfg.time_source = external; + LOG_D(PHY, "RU time source set as external\n"); + } else if (strcmp(*(RUParamList.paramarray[j][RU_SDR_TME_SRC].strptr), "gpsdo") == 0) { + RC.ru[j]->openair0_cfg.time_source = gpsdo; + LOG_D(PHY, "RU time source set as gpsdo\n"); + } else { + LOG_E(PHY, "Erroneous RU time source in the provided configuration file: '%s'\n", *(RUParamList.paramarray[j][RU_SDR_CLK_SRC].strptr)); + } + } + else { + RC.ru[j]->openair0_cfg.time_source = unset; + } + if (strcmp(*(RUParamList.paramarray[j][RU_LOCAL_RF_IDX].strptr), "yes") == 0) { if ( !(config_isparamset(RUParamList.paramarray[j],RU_LOCAL_IF_NAME_IDX)) ) { RC.ru[j]->if_south = LOCAL_RF; diff --git a/executables/nr-softmodem.c b/executables/nr-softmodem.c index cd222ac17685184b622d41fe82e85437ca54b356..6dd3807f3cc1f5a92ff0aee0b30b9e3d80fe4806 100644 --- a/executables/nr-softmodem.c +++ b/executables/nr-softmodem.c @@ -49,8 +49,6 @@ #include "PHY/phy_vars.h" #include "SCHED/sched_common_vars.h" #include "LAYER2/MAC/mac_vars.h" -#include "LAYER2/MAC/mac.h" -#include "LAYER2/MAC/mac_proto.h" #include "RRC/LTE/rrc_vars.h" #include "PHY_INTERFACE/phy_interface_vars.h" #include "gnb_config.h" diff --git a/executables/nr-uesoftmodem.c b/executables/nr-uesoftmodem.c index a269117ed8e1c53206fcb536584e8b07c111aadb..9b2b704833fb878ed5f9796892bb8f9811584f5a 100644 --- a/executables/nr-uesoftmodem.c +++ b/executables/nr-uesoftmodem.c @@ -47,7 +47,6 @@ #include "PHY/NR_REFSIG/nr_mod_table.h" #include "LAYER2/MAC/mac_vars.h" -#include "LAYER2/MAC/mac_proto.h" #include "RRC/LTE/rrc_vars.h" #include "PHY_INTERFACE/phy_interface_vars.h" #include "openair1/SIMULATION/TOOLS/sim.h" @@ -127,7 +126,6 @@ volatile int start_eNB = 0; volatile int start_UE = 0; volatile int oai_exit = 0; -static clock_source_t clock_source = unset; int single_thread_flag=1; static double snr_dB=20; @@ -597,7 +595,8 @@ void init_openair0(void) { PHY_vars_UE_g[0][0]->frame_parms.nb_antennas_rx); openair0_cfg[card].Mod_id = 0; openair0_cfg[card].num_rb_dl=frame_parms[0]->N_RB_DL; - openair0_cfg[card].clock_source = clock_source; + openair0_cfg[card].clock_source = get_softmodem_params()->clock_source; + openair0_cfg[card].time_source = get_softmodem_params()->timing_source; openair0_cfg[card].tx_num_channels=min(2,PHY_vars_UE_g[0][0]->frame_parms.nb_antennas_tx); openair0_cfg[card].rx_num_channels=min(2,PHY_vars_UE_g[0][0]->frame_parms.nb_antennas_rx); diff --git a/executables/nr-uesoftmodem.h b/executables/nr-uesoftmodem.h index 7fad43e897c20ff4ccc3003593974c75ce3da7a4..ba293324e3b275c7caa24d27aea69426790c6974 100644 --- a/executables/nr-uesoftmodem.h +++ b/executables/nr-uesoftmodem.h @@ -59,7 +59,6 @@ /* optname helpstr paramflags XXXptr defXXXval type numelt */ /*----------------------------------------------------------------------------------------------------------------------------------------------------*/ #define CMDLINE_PARAMS_DESC_UE { \ - {"clock-source", CONFIG_HLP_EXCCLK, 0, iptr:&clock_source, defintval:0, TYPE_INT, 0}, \ {"single-thread-disable", CONFIG_HLP_NOSNGLT, PARAMFLAG_BOOL, iptr:&single_thread_flag, defintval:1, TYPE_INT, 0}, \ {"nr-dlsch-demod-shift", CONFIG_HLP_DLSHIFT, 0, iptr:(int32_t *)&nr_dlsch_demod_shift, defintval:0, TYPE_INT, 0}, \ {"A" , CONFIG_HLP_TADV, 0, uptr:&timing_advance, defintval:0, TYPE_UINT, 0}, \ diff --git a/executables/softmodem-common.h b/executables/softmodem-common.h index b16a14fc66e81ed9d8ab2e9f4d2af144250e36ec..0ac7b6449e553ed8fce94dc99ff6d35bed579815 100644 --- a/executables/softmodem-common.h +++ b/executables/softmodem-common.h @@ -58,6 +58,7 @@ extern "C" #define CONFIG_HLP_EXTS "tells hardware to use an external timing reference\n" #define CONFIG_HLP_DMRSSYNC "tells RU to insert DMRS in subframe 1 slot 0" #define CONFIG_HLP_CLK "tells hardware to use a clock reference (0:internal, 1:external, 2:gpsdo)\n" +#define CONFIG_HLP_TME "tells hardware to use a time reference (0:internal, 1:external, 2:gpsdo)\n" #define CONFIG_HLP_USIM "use XOR autentication algo in case of test usim mode\n" #define CONFIG_HLP_NOSNGLT "Disables single-thread mode in lte-softmodem\n" #define CONFIG_HLP_DLF "Set the downlink frequency for all component carriers\n" @@ -114,7 +115,8 @@ extern "C" {"thread-pool", CONFIG_HLP_TPOOL, 0, strptr:(char **)&TP_CONFIG, defstrval:"n", TYPE_STRING, sizeof(TP_CONFIG)}, \ {"phy-test", CONFIG_HLP_PHYTST, PARAMFLAG_BOOL, iptr:&PHY_TEST, defintval:0, TYPE_INT, 0}, \ {"usim-test", CONFIG_HLP_USIM, PARAMFLAG_BOOL, u8ptr:&USIM_TEST, defintval:0, TYPE_UINT8, 0}, \ - {"clock", CONFIG_HLP_CLK, 0, uptr:&CLOCK_SOURCE, defintval:0, TYPE_UINT, 0}, \ + {"clock-source", CONFIG_HLP_CLK, 0, uptr:&CLOCK_SOURCE, defintval:0, TYPE_UINT, 0}, \ + {"time-source", CONFIG_HLP_TME, 0, uptr:&TIMING_SOURCE, defintval:0, TYPE_UINT, 0}, \ {"wait-for-sync", NULL, PARAMFLAG_BOOL, iptr:&WAIT_FOR_SYNC, defintval:0, TYPE_INT, 0}, \ {"single-thread-enable", CONFIG_HLP_NOSNGLT, PARAMFLAG_BOOL, iptr:&SINGLE_THREAD_FLAG, defintval:0, TYPE_INT, 0}, \ {"C" , CONFIG_HLP_DLF, 0, u64ptr:&(downlink_frequency[0][0]), defuintval:0, TYPE_UINT64, 0}, \ diff --git a/nfapi/oai_integration/nfapi_pnf.c b/nfapi/oai_integration/nfapi_pnf.c index 37b57e899de6856c083ad695db3a114e0ccfeeab..59857659c13fe506714210bca0212a4079c5caf0 100644 --- a/nfapi/oai_integration/nfapi_pnf.c +++ b/nfapi/oai_integration/nfapi_pnf.c @@ -49,7 +49,6 @@ extern RAN_CONTEXT_t RC; #include "fapi_stub.h" //#include "fapi_l1.h" #include "common/utils/LOG/log.h" -#include "openair2/LAYER2/MAC/mac_proto.h" #include "PHY/INIT/phy_init.h" #include "PHY/LTE_TRANSPORT/transport_proto.h" diff --git a/nfapi/open-nFAPI/nfapi/public_inc/nfapi_nr_interface_scf.h b/nfapi/open-nFAPI/nfapi/public_inc/nfapi_nr_interface_scf.h index f69c928ed2794ae72321468eb9efc9e726ed3751..8a25a04f7bd2953ddaae0646b474f0c82190bc93 100644 --- a/nfapi/open-nFAPI/nfapi/public_inc/nfapi_nr_interface_scf.h +++ b/nfapi/open-nFAPI/nfapi/public_inc/nfapi_nr_interface_scf.h @@ -1393,7 +1393,7 @@ typedef struct uint16_t timing_advance;//Timing advance ð‘‡ð´ measured for the UE [TS 38.213, Section 4.2] NTA_new = NTA_old + (TA − 31) â‹… 16 â‹… 64â„2μ Value: 0 → 63 0xffff should be set if this field is invalid uint16_t rssi; //variable ! fixme - uint32_t pdu; //MAC PDU + uint8_t *pdu; //MAC PDU } nfapi_nr_rx_data_pdu_t; diff --git a/openair1/PHY/INIT/lte_init_ru.c b/openair1/PHY/INIT/lte_init_ru.c index 207bf249f511902ba0c1e83f78cfa94f48ab22b0..dddd6b1bd50b134456e540dca75a574ee09ed2cf 100644 --- a/openair1/PHY/INIT/lte_init_ru.c +++ b/openair1/PHY/INIT/lte_init_ru.c @@ -38,7 +38,7 @@ int phy_init_RU(RU_t *ru) { LTE_DL_FRAME_PARMS *fp = ru->frame_parms; RU_CALIBRATION *calibration = &ru->calibration; int i,j,p,re; - init_dfts(); + //load_dftslib(); LOG_I(PHY,"Initializing RU signal buffers (if_south %s) nb_tx %d\n",ru_if_types[ru->if_south],ru->nb_tx); if (ru->is_slave == 1) { @@ -76,7 +76,7 @@ int phy_init_RU(RU_t *ru) { } if (ru->function != NGFI_RRU_IF5) { // we need to do RX/TX RU processing - init_dfts(); + load_dftslib(); init_7_5KHz(); LOG_I(PHY,"nb_tx %d\n",ru->nb_tx); ru->common.rxdata_7_5kHz = (int32_t **)malloc16(ru->nb_rx*sizeof(int32_t *) ); diff --git a/openair1/PHY/INIT/lte_init_ue.c b/openair1/PHY/INIT/lte_init_ue.c index 1a6f0081e1ab0fe151b8470ccdbd4b056dd617c0..082db61da94f53302e9a7a94588060f3fa0ed059 100644 --- a/openair1/PHY/INIT/lte_init_ue.c +++ b/openair1/PHY/INIT/lte_init_ue.c @@ -625,7 +625,7 @@ int init_lte_ue_signal(PHY_VARS_UE *ue, int th_id; LOG_D(PHY,"Initializing UE vars (abstraction %"PRIu8") for eNB TXant %"PRIu8", UE RXant %"PRIu8"\n",abstraction_flag,fp->nb_antennas_tx,fp->nb_antennas_rx); crcTableInit(); - init_dfts(); + load_dftslib(); init_frame_parms(&ue->frame_parms,1); lte_sync_time_init(&ue->frame_parms); init_lte_top(&ue->frame_parms); diff --git a/openair1/PHY/INIT/nr_init.c b/openair1/PHY/INIT/nr_init.c index 1c0d5a6acadc6d323f04b99569249f52910f4c0f..af411fc7d776e4a4ac4d0d4308ab4901ac4d59a9 100644 --- a/openair1/PHY/INIT/nr_init.c +++ b/openair1/PHY/INIT/nr_init.c @@ -96,7 +96,7 @@ int phy_init_nr_gNB(PHY_VARS_gNB *gNB, while(gNB->configured == 0) usleep(10000); - init_dfts(); + load_dftslib(); /* LOG_I(PHY,"[gNB %"PRIu8"] Initializing DL_FRAME_PARMS : N_RB_DL %"PRIu8", PHICH Resource %d, PHICH Duration %d nb_antennas_tx:%u nb_antennas_rx:%u PRACH[rootSequenceIndex:%u prach_Config_enabled:%u configIndex:%u highSpeed:%u zeroCorrelationZoneConfig:%u freqOffset:%u]\n", gNB->Mod_id, @@ -112,7 +112,6 @@ int phy_init_nr_gNB(PHY_VARS_gNB *gNB, );*/ LOG_D(PHY,"[MSC_NEW][FRAME 00000][PHY_gNB][MOD %02"PRIu8"][]\n", gNB->Mod_id); crcTableInit(); - init_dfts(); load_nrLDPClib(); // PBCH DMRS gold sequences generation nr_init_pbch_dmrs(gNB); diff --git a/openair1/PHY/INIT/nr_init_ue.c b/openair1/PHY/INIT/nr_init_ue.c index 4ed5be2119e8ca5802923cf44c120ea9cac9302a..5c812e340fa3ca6f24eaa7c739ca0f16722c3025 100644 --- a/openair1/PHY/INIT/nr_init_ue.c +++ b/openair1/PHY/INIT/nr_init_ue.c @@ -988,7 +988,7 @@ void init_nr_ue_transport(PHY_VARS_NR_UE *ue, void phy_init_nr_top(PHY_VARS_NR_UE *ue) { NR_DL_FRAME_PARMS *frame_parms = &ue->frame_parms; crcTableInit(); - init_dfts(); + load_dftslib(); init_context_synchro_nr(frame_parms); generate_ul_reference_signal_sequences(SHRT_MAX); // Polar encoder init for PBCH diff --git a/openair1/PHY/LTE_ESTIMATION/lte_adjust_sync_eNB.c b/openair1/PHY/LTE_ESTIMATION/lte_adjust_sync_eNB.c index 04fe19ecbce878acce9af7830489ff181a5a8573..aaa138fcd9d8ca066a678496c30b015e70c5edde 100644 --- a/openair1/PHY/LTE_ESTIMATION/lte_adjust_sync_eNB.c +++ b/openair1/PHY/LTE_ESTIMATION/lte_adjust_sync_eNB.c @@ -56,22 +56,22 @@ int lte_est_timing_advance(LTE_DL_FRAME_PARMS *frame_parms, // do ifft of channel estimate switch(frame_parms->N_RB_DL) { case 6: - dft128((int16_t*) <e_eNB_srs->srs_ch_estimates[aa][0], + dft(DFT_128,(int16_t*) <e_eNB_srs->srs_ch_estimates[aa][0], (int16_t*) lte_eNB_srs->srs_ch_estimates_time[aa], 1); break; case 25: - dft512((int16_t*) <e_eNB_srs->srs_ch_estimates[aa][0], + dft(DFT_512,(int16_t*) <e_eNB_srs->srs_ch_estimates[aa][0], (int16_t*) lte_eNB_srs->srs_ch_estimates_time[aa], 1); break; case 50: - dft1024((int16_t*) <e_eNB_srs->srs_ch_estimates[aa][0], + dft(DFT_1024,(int16_t*) <e_eNB_srs->srs_ch_estimates[aa][0], (int16_t*) lte_eNB_srs->srs_ch_estimates_time[aa], 1); break; case 100: - dft2048((int16_t*) <e_eNB_srs->srs_ch_estimates[aa][0], + dft(DFT_2048,(int16_t*) <e_eNB_srs->srs_ch_estimates[aa][0], (int16_t*) lte_eNB_srs->srs_ch_estimates_time[aa], 1); break; diff --git a/openair1/PHY/LTE_ESTIMATION/lte_adjust_sync_ue.c b/openair1/PHY/LTE_ESTIMATION/lte_adjust_sync_ue.c index 7414c3a69d13d849f705d0fefaad6b1e208bf6da..23f261149a629606be146997e35c40cc4e10bf0c 100644 --- a/openair1/PHY/LTE_ESTIMATION/lte_adjust_sync_ue.c +++ b/openair1/PHY/LTE_ESTIMATION/lte_adjust_sync_ue.c @@ -23,7 +23,6 @@ #include "PHY/defs_UE.h" #include "PHY/LTE_ESTIMATION/lte_estimation.h" #include "PHY/impl_defs_top.h" -#include "openair2/LAYER2/MAC/mac_proto.h" #include "common/utils/LOG/vcd_signal_dumper.h" diff --git a/openair1/PHY/LTE_ESTIMATION/lte_dl_channel_estimation.c b/openair1/PHY/LTE_ESTIMATION/lte_dl_channel_estimation.c index e50af7cdd8f297a95b8c3eeb440227eb5ec37658..d221348b44f38a9e7f2375a47a3c63db7b3d2a9c 100644 --- a/openair1/PHY/LTE_ESTIMATION/lte_dl_channel_estimation.c +++ b/openair1/PHY/LTE_ESTIMATION/lte_dl_channel_estimation.c @@ -657,35 +657,35 @@ int lte_dl_channel_estimation(PHY_VARS_UE *ue, } } - void (*idft)(int16_t *,int16_t *, int); + idft_size_idx_t idftsizeidx; switch (ue->frame_parms.ofdm_symbol_size) { case 128: - idft = idft128; - break; - - case 256: - idft = idft256; - break; - - case 512: - idft = idft512; - break; - - case 1024: - idft = idft1024; - break; - - case 1536: - idft = idft1536; - break; - - case 2048: - idft = idft2048; - break; - - default: - idft = idft512; + idftsizeidx = IDFT_128; + break; + + case 256: + idftsizeidx = IDFT_256; + break; + + case 512: + idftsizeidx = IDFT_512; + break; + + case 1024: + idftsizeidx = IDFT_1024; + break; + + case 1536: + idftsizeidx = IDFT_1536; + break; + + case 2048: + idftsizeidx = IDFT_2048; + break; + + default: + idftsizeidx = IDFT_512; break; } @@ -695,7 +695,7 @@ int lte_dl_channel_estimation(PHY_VARS_UE *ue, for (p=0; p<ue->frame_parms.nb_antenna_ports_eNB; p++) { if (ue->common_vars.common_vars_rx_data_per_thread[ue->current_thread_id[Ns>>1]].dl_ch_estimates[eNB_offset][(p<<1)+aarx]) { //LOG_I(PHY,"Channel Impulse Computation Slot %d ThreadId %d Symbol %d \n", Ns, ue->current_thread_id[Ns>>1], l); - idft((int16_t *) &ue->common_vars.common_vars_rx_data_per_thread[ue->current_thread_id[Ns>>1]].dl_ch_estimates[eNB_offset][(p<<1)+aarx][8], + idft(idftsizeidx,(int16_t *) &ue->common_vars.common_vars_rx_data_per_thread[ue->current_thread_id[Ns>>1]].dl_ch_estimates[eNB_offset][(p<<1)+aarx][8], (int16_t *) ue->common_vars.common_vars_rx_data_per_thread[ue->current_thread_id[Ns>>1]].dl_ch_estimates_time[eNB_offset][(p<<1)+aarx],1); } } diff --git a/openair1/PHY/LTE_ESTIMATION/lte_dl_mbsfn_channel_estimation.c b/openair1/PHY/LTE_ESTIMATION/lte_dl_mbsfn_channel_estimation.c index 6f917ee49c5cb1b42e1320972f5fc2dfd8155d74..333a6f08665ef8a34dd6c0a4ad480f931264aba8 100644 --- a/openair1/PHY/LTE_ESTIMATION/lte_dl_mbsfn_channel_estimation.c +++ b/openair1/PHY/LTE_ESTIMATION/lte_dl_mbsfn_channel_estimation.c @@ -724,31 +724,31 @@ int lte_dl_mbsfn_channel_estimation(PHY_VARS_UE *ue, if (ue->common_vars.common_vars_rx_data_per_thread[ue->current_thread_id[subframe]].dl_ch_estimates[eNB_offset][aa]) { switch (ue->frame_parms.N_RB_DL) { case 6: - idft128((int16_t *) &ue->common_vars.common_vars_rx_data_per_thread[ue->current_thread_id[subframe]].dl_ch_estimates[eNB_offset][aa][8], + idft(IDFT_128,(int16_t *) &ue->common_vars.common_vars_rx_data_per_thread[ue->current_thread_id[subframe]].dl_ch_estimates[eNB_offset][aa][8], (int16_t *) ue->common_vars.common_vars_rx_data_per_thread[ue->current_thread_id[subframe]].dl_ch_estimates_time[eNB_offset][aa], 1); break; case 25: - idft512((int16_t *) &ue->common_vars.common_vars_rx_data_per_thread[ue->current_thread_id[subframe]].dl_ch_estimates[eNB_offset][aa][8], + idft(IDFT_512,(int16_t *) &ue->common_vars.common_vars_rx_data_per_thread[ue->current_thread_id[subframe]].dl_ch_estimates[eNB_offset][aa][8], (int16_t *) ue->common_vars.common_vars_rx_data_per_thread[ue->current_thread_id[subframe]].dl_ch_estimates_time[eNB_offset][aa], 1); break; case 50: - idft1024((int16_t *) &ue->common_vars.common_vars_rx_data_per_thread[ue->current_thread_id[subframe]].dl_ch_estimates[eNB_offset][aa][8], + idft(IDFT_1024,(int16_t *) &ue->common_vars.common_vars_rx_data_per_thread[ue->current_thread_id[subframe]].dl_ch_estimates[eNB_offset][aa][8], (int16_t *) ue->common_vars.common_vars_rx_data_per_thread[ue->current_thread_id[subframe]].dl_ch_estimates_time[eNB_offset][aa], 1); break; case 75: - idft1536((int16_t *) &ue->common_vars.common_vars_rx_data_per_thread[ue->current_thread_id[subframe]].dl_ch_estimates[eNB_offset][aa][8], + idft(IDFT_1536,(int16_t *) &ue->common_vars.common_vars_rx_data_per_thread[ue->current_thread_id[subframe]].dl_ch_estimates[eNB_offset][aa][8], (int16_t *) ue->common_vars.common_vars_rx_data_per_thread[ue->current_thread_id[subframe]].dl_ch_estimates_time[eNB_offset][aa], 1); break; case 100: - idft2048((int16_t *) &ue->common_vars.common_vars_rx_data_per_thread[ue->current_thread_id[subframe]].dl_ch_estimates[eNB_offset][aa][8], + idft(IDFT_2048,(int16_t *) &ue->common_vars.common_vars_rx_data_per_thread[ue->current_thread_id[subframe]].dl_ch_estimates[eNB_offset][aa][8], (int16_t *) ue->common_vars.common_vars_rx_data_per_thread[ue->current_thread_id[subframe]].dl_ch_estimates_time[eNB_offset][aa], 1); break; diff --git a/openair1/PHY/LTE_ESTIMATION/lte_sync_time.c b/openair1/PHY/LTE_ESTIMATION/lte_sync_time.c index 0c98bdc5a563295f73f2801bfdbbe25c2d5da2f5..0d765a18b339c6fe92109207cb7067cbd50ea3cc 100644 --- a/openair1/PHY/LTE_ESTIMATION/lte_sync_time.c +++ b/openair1/PHY/LTE_ESTIMATION/lte_sync_time.c @@ -141,28 +141,28 @@ int lte_sync_time_init(LTE_DL_FRAME_PARMS *frame_parms ) // LTE_UE_COMMON *com switch (frame_parms->N_RB_DL) { case 6: - idft128((short*)syncF_tmp, /// complex input + idft(IDFT_128,(short*)syncF_tmp, /// complex input (short*)sync_tmp, /// complex output 1); break; case 25: - idft512((short*)syncF_tmp, /// complex input + idft(IDFT_512,(short*)syncF_tmp, /// complex input (short*)sync_tmp, /// complex output 1); break; case 50: - idft1024((short*)syncF_tmp, /// complex input + idft(IDFT_1024,(short*)syncF_tmp, /// complex input (short*)sync_tmp, /// complex output 1); break; case 75: - idft1536((short*)syncF_tmp, /// complex input + idft(IDFT_1536,(short*)syncF_tmp, /// complex input (short*)sync_tmp, 1); /// complex output break; case 100: - idft2048((short*)syncF_tmp, /// complex input + idft(IDFT_2048,(short*)syncF_tmp, /// complex input (short*)sync_tmp, /// complex output 1); break; @@ -189,28 +189,28 @@ int lte_sync_time_init(LTE_DL_FRAME_PARMS *frame_parms ) // LTE_UE_COMMON *com switch (frame_parms->N_RB_DL) { case 6: - idft128((short*)syncF_tmp, /// complex input + idft(IDFT_128,(short*)syncF_tmp, /// complex input (short*)sync_tmp, /// complex output 1); break; case 25: - idft512((short*)syncF_tmp, /// complex input + idft(IDFT_512,(short*)syncF_tmp, /// complex input (short*)sync_tmp, /// complex output 1); break; case 50: - idft1024((short*)syncF_tmp, /// complex input + idft(IDFT_1024,(short*)syncF_tmp, /// complex input (short*)sync_tmp, /// complex output 1); break; case 75: - idft1536((short*)syncF_tmp, /// complex input + idft(IDFT_1536,(short*)syncF_tmp, /// complex input (short*)sync_tmp, /// complex output 1); break; case 100: - idft2048((short*)syncF_tmp, /// complex input + idft(IDFT_2048,(short*)syncF_tmp, /// complex input (short*)sync_tmp, /// complex output 1); break; @@ -237,28 +237,28 @@ int lte_sync_time_init(LTE_DL_FRAME_PARMS *frame_parms ) // LTE_UE_COMMON *com switch (frame_parms->N_RB_DL) { case 6: - idft128((short*)syncF_tmp, /// complex input + idft(IDFT_128,(short*)syncF_tmp, /// complex input (short*)sync_tmp, /// complex output 1); break; case 25: - idft512((short*)syncF_tmp, /// complex input + idft(IDFT_512,(short*)syncF_tmp, /// complex input (short*)sync_tmp, /// complex output 1); break; case 50: - idft1024((short*)syncF_tmp, /// complex input + idft(IDFT_1024,(short*)syncF_tmp, /// complex input (short*)sync_tmp, /// complex output 1); break; case 75: - idft1536((short*)syncF_tmp, /// complex input + idft(IDFT_1536,(short*)syncF_tmp, /// complex input (short*)sync_tmp, /// complex output 1); break; case 100: - idft2048((short*)syncF_tmp, /// complex input + idft(IDFT_2048,(short*)syncF_tmp, /// complex input (short*)sync_tmp, /// complex output 1); break; @@ -492,28 +492,28 @@ int ru_sync_time_init(RU_t *ru) // LTE_UE_COMMON *common_vars switch (ru->frame_parms->N_RB_DL) { case 6: - idft128((int16_t*)(&dmrsp[0][3*ru->frame_parms->ofdm_symbol_size]), + idft(IDFT_128,(int16_t*)(&dmrsp[0][3*ru->frame_parms->ofdm_symbol_size]), ru->dmrssync, /// complex output 1); break; case 25: - idft512((int16_t*)(&dmrsp[0][3*ru->frame_parms->ofdm_symbol_size]), + idft(IDFT_512,(int16_t*)(&dmrsp[0][3*ru->frame_parms->ofdm_symbol_size]), ru->dmrssync, /// complex output 1); break; case 50: - idft1024((int16_t*)(&dmrsp[0][3*ru->frame_parms->ofdm_symbol_size]), + idft(IDFT_1024,(int16_t*)(&dmrsp[0][3*ru->frame_parms->ofdm_symbol_size]), ru->dmrssync, /// complex output 1); break; case 75: - idft1536((int16_t*)(&dmrsp[0][3*ru->frame_parms->ofdm_symbol_size]), + idft(IDFT_1536,(int16_t*)(&dmrsp[0][3*ru->frame_parms->ofdm_symbol_size]), ru->dmrssync, 1); /// complex output break; case 100: - idft2048((int16_t*)(&dmrsp[0][3*ru->frame_parms->ofdm_symbol_size]), + idft(IDFT_2048,(int16_t*)(&dmrsp[0][3*ru->frame_parms->ofdm_symbol_size]), ru->dmrssync, /// complex output 1); break; diff --git a/openair1/PHY/LTE_ESTIMATION/lte_sync_timefreq.c b/openair1/PHY/LTE_ESTIMATION/lte_sync_timefreq.c index de48a855df6b5814b569cc3d5fcc15f24e28e434..524b200e1a1883d4cc1748f8b420e2d78ffc5dd8 100644 --- a/openair1/PHY/LTE_ESTIMATION/lte_sync_timefreq.c +++ b/openair1/PHY/LTE_ESTIMATION/lte_sync_timefreq.c @@ -80,7 +80,7 @@ void lte_sync_timefreq(PHY_VARS_UE *ue,int band,unsigned int DL_freq) while (1) { //compute frequency-domain representation of 6144-sample chunk - dft6144((int16_t *)rxp, + dft(DFT_6144,(int16_t *)rxp, sp,1); @@ -267,7 +267,7 @@ void lte_sync_timefreq(PHY_VARS_UE *ue,int band,unsigned int DL_freq) } // ifft, accumulate energy over two half-frames - idft256((int16_t*)autocorr0,(int16_t*)tmp_t,1); + idft(IDFT_256,(int16_t*)autocorr0,(int16_t*)tmp_t,1); /* if (i==12288) { sprintf(fname,"corr256F_%d.m",abs(f)); @@ -285,12 +285,12 @@ void lte_sync_timefreq(PHY_VARS_UE *ue,int band,unsigned int DL_freq) for (re=0; re<(256/4); re++) autocorr0_t[re] = _mm_add_epi32(autocorr0_t[re],_mm_madd_epi16(tmp_t[re],tmp_t[re])); - idft256((int16_t*)autocorr1,(int16_t*)tmp_t,1); + idft(IDFT_256,(int16_t*)autocorr1,(int16_t*)tmp_t,1); for (re=0; re<(256/4); re++) autocorr1_t[re] = _mm_add_epi32(autocorr1_t[re],_mm_madd_epi16(tmp_t[re],tmp_t[re])); - idft256((int16_t*)autocorr2,(int16_t*)tmp_t,1); + idft(IDFT_256,(int16_t*)autocorr2,(int16_t*)tmp_t,1); for (re=0; re<(256/4); re++) autocorr2_t[re] = _mm_add_epi32(autocorr2_t[re],_mm_madd_epi16(tmp_t[re],tmp_t[re])); diff --git a/openair1/PHY/LTE_ESTIMATION/lte_ul_channel_estimation.c b/openair1/PHY/LTE_ESTIMATION/lte_ul_channel_estimation.c index 5a0751c5ef92c15af3ac5d50df51f1a5d153a4df..7caaf07406b0355d970165fd8a1eb793f9710197 100644 --- a/openair1/PHY/LTE_ESTIMATION/lte_ul_channel_estimation.c +++ b/openair1/PHY/LTE_ESTIMATION/lte_ul_channel_estimation.c @@ -249,25 +249,25 @@ int32_t lte_ul_channel_estimation(PHY_VARS_eNB *eNB, switch(frame_parms->N_RB_DL) { case 6: - idft128((int16_t *) temp_in_ifft_0, + idft(IDFT_128,(int16_t *) temp_in_ifft_0, (int16_t *) ul_ch_estimates_time[aa], 1); break; case 25: - idft512((int16_t *) temp_in_ifft_0, + idft(IDFT_512,(int16_t *) temp_in_ifft_0, (int16_t *) ul_ch_estimates_time[aa], 1); break; case 50: - idft1024((int16_t *) temp_in_ifft_0, + idft(IDFT_1024,(int16_t *) temp_in_ifft_0, (int16_t *) ul_ch_estimates_time[aa], 1); break; case 100: - idft2048((int16_t *) temp_in_ifft_0, + idft(IDFT_2048,(int16_t *) temp_in_ifft_0, (int16_t *) ul_ch_estimates_time[aa], 1); break; @@ -578,25 +578,25 @@ int32_t lte_ul_channel_estimation_RRU(LTE_DL_FRAME_PARMS *frame_parms, switch(frame_parms->N_RB_DL) { case 6: - idft128((int16_t *) temp_in_ifft_0, + idft(IDFT_128,(int16_t *) temp_in_ifft_0, (int16_t *) ul_ch_estimates_time[aa], 1); break; case 25: - idft512((int16_t *) temp_in_ifft_0, + idft(IDFT_512,(int16_t *) temp_in_ifft_0, (int16_t *) ul_ch_estimates_time[aa], 1); break; case 50: - idft1024((int16_t *) temp_in_ifft_0, + idft(IDFT_1024,(int16_t *) temp_in_ifft_0, (int16_t *) ul_ch_estimates_time[aa], 1); break; case 100: - idft2048((int16_t *) temp_in_ifft_0, + idft(IDFT_2048,(int16_t *) temp_in_ifft_0, (int16_t *) ul_ch_estimates_time[aa], 1); break; diff --git a/openair1/PHY/LTE_TRANSPORT/lte_mcs.c b/openair1/PHY/LTE_TRANSPORT/lte_mcs.c index c13876f29a3ae81ad14cd56b2efcb76f071a225d..6144b978bf432bf20ddb5d2c2be98ead053c1d90 100644 --- a/openair1/PHY/LTE_TRANSPORT/lte_mcs.c +++ b/openair1/PHY/LTE_TRANSPORT/lte_mcs.c @@ -94,6 +94,35 @@ unsigned char I_TBS2I_MCS(unsigned char I_TBS) { return I_MCS; } +uint16_t find_nb_rb_DL(uint8_t mcs, uint32_t bytes, uint16_t nb_rb_max, uint16_t rb_gran) { + if (bytes == 0 || mcs > 28 || nb_rb_max == 0) + return 0; + const uint32_t bits = bytes << 3; + const unsigned char I_TBS = get_I_TBS(mcs); + + uint32_t TBS = TBStable[I_TBS][nb_rb_max - 1]; + if (bits >= TBS) // is nb_rb_max too small? + return nb_rb_max; + + TBS = TBStable[I_TBS][rb_gran - 1]; + if (bits <= TBS) // is rb_gran RB enough? + return rb_gran; + + nb_rb_max += nb_rb_max % rb_gran; // round up to full RBG + uint16_t hi = nb_rb_max/rb_gran - 1; + uint16_t lo = 0; + uint16_t p = (hi + lo) / 2; + for (; lo + 1 != hi; p = (hi + lo) / 2) { + const uint16_t rbi = (p + 1) * rb_gran - 1; // convert "RBG" -> RB + TBS = TBStable[I_TBS][rbi]; + if (bits <= TBS) // need less RBs + hi = p; + else // need more RBs + lo = p; + } + return (hi + 1) * rb_gran; +} + uint32_t get_TBS_DL(uint8_t mcs, uint16_t nb_rb) { uint32_t TBS; diff --git a/openair1/PHY/LTE_TRANSPORT/prach.c b/openair1/PHY/LTE_TRANSPORT/prach.c index 99d8aa1bbccb3feda1d8634324b3f93c98227af5..24faf584d3ae2e2048e3ee4a412c3c33637d8a0d 100644 --- a/openair1/PHY/LTE_TRANSPORT/prach.c +++ b/openair1/PHY/LTE_TRANSPORT/prach.c @@ -297,24 +297,24 @@ void rx_prach0(PHY_VARS_eNB *eNB, switch (fp->N_RB_UL) { case 6: if (prach_fmt == 4) { - dft256(prach2,rxsigF[aa],1); + dft(DFT_256,prach2,rxsigF[aa],1); } else { - dft1536(prach2,rxsigF[aa],1); + dft(DFT_1536,prach2,rxsigF[aa],1); if (prach_fmt>1) - dft1536(prach2+3072,rxsigF[aa]+3072,1); + dft(DFT_1536,prach2+3072,rxsigF[aa]+3072,1); } break; case 15: if (prach_fmt == 4) { - dft256(prach2,rxsigF[aa],1); + dft(DFT_256,prach2,rxsigF[aa],1); } else { - dft3072(prach2,rxsigF[aa],1); + dft(DFT_3072,prach2,rxsigF[aa],1); if (prach_fmt>1) - dft3072(prach2+6144,rxsigF[aa]+6144,1); + dft(DFT_3072,prach2+6144,rxsigF[aa]+6144,1); } break; @@ -322,13 +322,13 @@ void rx_prach0(PHY_VARS_eNB *eNB, case 25: default: if (prach_fmt == 4) { - dft1024(prach2,rxsigF[aa],1); + dft(DFT_1024,prach2,rxsigF[aa],1); fft_size = 1024; } else { - dft6144(prach2,rxsigF[aa],1); + dft(DFT_6144,prach2,rxsigF[aa],1); if (prach_fmt>1) - dft6144(prach2+12288,rxsigF[aa]+12288,1); + dft(DFT_6144,prach2+12288,rxsigF[aa]+12288,1); fft_size = 6144; } @@ -337,24 +337,24 @@ void rx_prach0(PHY_VARS_eNB *eNB, case 50: if (prach_fmt == 4) { - dft2048(prach2,rxsigF[aa],1); + dft(DFT_2048,prach2,rxsigF[aa],1); } else { - dft12288(prach2,rxsigF[aa],1); + dft(DFT_12288,prach2,rxsigF[aa],1); if (prach_fmt>1) - dft12288(prach2+24576,rxsigF[aa]+24576,1); + dft(DFT_12288,prach2+24576,rxsigF[aa]+24576,1); } break; case 75: if (prach_fmt == 4) { - dft3072(prach2,rxsigF[aa],1); + dft(DFT_3072,prach2,rxsigF[aa],1); } else { - dft18432(prach2,rxsigF[aa],1); + dft(DFT_18432,prach2,rxsigF[aa],1); if (prach_fmt>1) - dft18432(prach2+36864,rxsigF[aa]+36864,1); + dft(DFT_18432,prach2+36864,rxsigF[aa]+36864,1); } break; @@ -362,21 +362,21 @@ void rx_prach0(PHY_VARS_eNB *eNB, case 100: if (fp->threequarter_fs==0) { if (prach_fmt == 4) { - dft4096(prach2,rxsigF[aa],1); + dft(DFT_4096,prach2,rxsigF[aa],1); } else { - dft24576(prach2,rxsigF[aa],1); + dft(DFT_24576,prach2,rxsigF[aa],1); if (prach_fmt>1) - dft24576(prach2+49152,rxsigF[aa]+49152,1); + dft(DFT_24576,prach2+49152,rxsigF[aa]+49152,1); } } else { if (prach_fmt == 4) { - dft3072(prach2,rxsigF[aa],1); + dft(DFT_3072,prach2,rxsigF[aa],1); } else { - dft18432(prach2,rxsigF[aa],1); + dft(DFT_18432,prach2,rxsigF[aa],1); if (prach_fmt>1) - dft18432(prach2+36864,rxsigF[aa]+36864,1); + dft(DFT_18432,prach2+36864,rxsigF[aa]+36864,1); } } @@ -588,13 +588,13 @@ void rx_prach0(PHY_VARS_eNB *eNB, // Now do IFFT of size 1024 (N_ZC=839) or 256 (N_ZC=139) if (N_ZC == 839) { log2_ifft_size = 10; - idft1024(prachF,prach_ifft_tmp,1); + idft(IDFT_1024,prachF,prach_ifft_tmp,1); // compute energy and accumulate over receive antennas and repetitions for BR for (i=0; i<2048; i++) prach_ifft[i] += (prach_ifft_tmp[i<<1]*prach_ifft_tmp[i<<1] + prach_ifft_tmp[1+(i<<1)]*prach_ifft_tmp[1+(i<<1)])>>9; } else { - idft256(prachF,prach_ifft_tmp,1); + idft(IDFT_256,prachF,prach_ifft_tmp,1); log2_ifft_size = 8; // compute energy and accumulate over receive antennas and repetitions for BR diff --git a/openair1/PHY/LTE_TRANSPORT/transport_common_proto.h b/openair1/PHY/LTE_TRANSPORT/transport_common_proto.h index 1d7aa598afd652b59432a919c061461996419c2d..e4f5d9a17f10b3d3090a53df586229751a568267 100644 --- a/openair1/PHY/LTE_TRANSPORT/transport_common_proto.h +++ b/openair1/PHY/LTE_TRANSPORT/transport_common_proto.h @@ -60,6 +60,8 @@ unsigned char get_I_TBS_UL(unsigned char I_MCS); @return Transport block size */ uint32_t get_TBS_DL(uint8_t mcs, uint16_t nb_rb); +uint16_t find_nb_rb_DL(uint8_t mcs, uint32_t bytes, uint16_t nb_rb_max, uint16_t rb_gran); + /** \brief Compute Q (modulation order) based on uplink I_MCS. Implements table 7.1.7.1-1 from 36.213. @param I_MCS @param nb_rb diff --git a/openair1/PHY/LTE_TRANSPORT/ulsch_demodulation.c b/openair1/PHY/LTE_TRANSPORT/ulsch_demodulation.c index 1b0d7feaf51cd647d6e199c08016df49c9e057b3..0e7bdd2ae46af2fe9075fa58e443f0d7676f433b 100644 --- a/openair1/PHY/LTE_TRANSPORT/ulsch_demodulation.c +++ b/openair1/PHY/LTE_TRANSPORT/ulsch_demodulation.c @@ -154,9 +154,9 @@ void lte_idft(LTE_DL_FRAME_PARMS *frame_parms,uint32_t *z, uint16_t Msc_PUSCH) { switch (Msc_PUSCH) { case 12: - dft12((int16_t *)idft_in0,(int16_t *)idft_out0); - dft12((int16_t *)idft_in1,(int16_t *)idft_out1); - dft12((int16_t *)idft_in2,(int16_t *)idft_out2); + dft(DFT_12,(int16_t *)idft_in0,(int16_t *)idft_out0,0); + dft(DFT_12,(int16_t *)idft_in1,(int16_t *)idft_out1,0); + dft(DFT_12,(int16_t *)idft_in2,(int16_t *)idft_out2,0); #if defined(__x86_64__)||defined(__i386__) norm128 = _mm_set1_epi16(9459); #elif defined(__arm__) @@ -178,201 +178,201 @@ void lte_idft(LTE_DL_FRAME_PARMS *frame_parms,uint32_t *z, uint16_t Msc_PUSCH) { break; case 24: - dft24(idft_in0,idft_out0,1); - dft24(idft_in1,idft_out1,1); - dft24(idft_in2,idft_out2,1); + dft(DFT_24,idft_in0,idft_out0,1); + dft(DFT_24,idft_in1,idft_out1,1); + dft(DFT_24,idft_in2,idft_out2,1); break; case 36: - dft36(idft_in0,idft_out0,1); - dft36(idft_in1,idft_out1,1); - dft36(idft_in2,idft_out2,1); + dft(DFT_36,idft_in0,idft_out0,1); + dft(DFT_36,idft_in1,idft_out1,1); + dft(DFT_36,idft_in2,idft_out2,1); break; case 48: - dft48(idft_in0,idft_out0,1); - dft48(idft_in1,idft_out1,1); - dft48(idft_in2,idft_out2,1); + dft(DFT_48,idft_in0,idft_out0,1); + dft(DFT_48,idft_in1,idft_out1,1); + dft(DFT_48,idft_in2,idft_out2,1); break; case 60: - dft60(idft_in0,idft_out0,1); - dft60(idft_in1,idft_out1,1); - dft60(idft_in2,idft_out2,1); + dft(DFT_60,idft_in0,idft_out0,1); + dft(DFT_60,idft_in1,idft_out1,1); + dft(DFT_60,idft_in2,idft_out2,1); break; case 72: - dft72(idft_in0,idft_out0,1); - dft72(idft_in1,idft_out1,1); - dft72(idft_in2,idft_out2,1); + dft(DFT_72,idft_in0,idft_out0,1); + dft(DFT_72,idft_in1,idft_out1,1); + dft(DFT_72,idft_in2,idft_out2,1); break; case 96: - dft96(idft_in0,idft_out0,1); - dft96(idft_in1,idft_out1,1); - dft96(idft_in2,idft_out2,1); + dft(DFT_96,idft_in0,idft_out0,1); + dft(DFT_96,idft_in1,idft_out1,1); + dft(DFT_96,idft_in2,idft_out2,1); break; case 108: - dft108(idft_in0,idft_out0,1); - dft108(idft_in1,idft_out1,1); - dft108(idft_in2,idft_out2,1); + dft(DFT_108,idft_in0,idft_out0,1); + dft(DFT_108,idft_in1,idft_out1,1); + dft(DFT_108,idft_in2,idft_out2,1); break; case 120: - dft120(idft_in0,idft_out0,1); - dft120(idft_in1,idft_out1,1); - dft120(idft_in2,idft_out2,1); + dft(DFT_120,idft_in0,idft_out0,1); + dft(DFT_120,idft_in1,idft_out1,1); + dft(DFT_120,idft_in2,idft_out2,1); break; case 144: - dft144(idft_in0,idft_out0,1); - dft144(idft_in1,idft_out1,1); - dft144(idft_in2,idft_out2,1); + dft(DFT_144,idft_in0,idft_out0,1); + dft(DFT_144,idft_in1,idft_out1,1); + dft(DFT_144,idft_in2,idft_out2,1); break; case 180: - dft180(idft_in0,idft_out0,1); - dft180(idft_in1,idft_out1,1); - dft180(idft_in2,idft_out2,1); + dft(DFT_180,idft_in0,idft_out0,1); + dft(DFT_180,idft_in1,idft_out1,1); + dft(DFT_180,idft_in2,idft_out2,1); break; case 192: - dft192(idft_in0,idft_out0,1); - dft192(idft_in1,idft_out1,1); - dft192(idft_in2,idft_out2,1); + dft(DFT_192,idft_in0,idft_out0,1); + dft(DFT_192,idft_in1,idft_out1,1); + dft(DFT_192,idft_in2,idft_out2,1); break; case 216: - dft216(idft_in0,idft_out0,1); - dft216(idft_in1,idft_out1,1); - dft216(idft_in2,idft_out2,1); + dft(DFT_216,idft_in0,idft_out0,1); + dft(DFT_216,idft_in1,idft_out1,1); + dft(DFT_216,idft_in2,idft_out2,1); break; case 240: - dft240(idft_in0,idft_out0,1); - dft240(idft_in1,idft_out1,1); - dft240(idft_in2,idft_out2,1); + dft(DFT_240,idft_in0,idft_out0,1); + dft(DFT_240,idft_in1,idft_out1,1); + dft(DFT_240,idft_in2,idft_out2,1); break; case 288: - dft288(idft_in0,idft_out0,1); - dft288(idft_in1,idft_out1,1); - dft288(idft_in2,idft_out2,1); + dft(DFT_288,idft_in0,idft_out0,1); + dft(DFT_288,idft_in1,idft_out1,1); + dft(DFT_288,idft_in2,idft_out2,1); break; case 300: - dft300(idft_in0,idft_out0,1); - dft300(idft_in1,idft_out1,1); - dft300(idft_in2,idft_out2,1); + dft(DFT_300,idft_in0,idft_out0,1); + dft(DFT_300,idft_in1,idft_out1,1); + dft(DFT_300,idft_in2,idft_out2,1); break; case 324: - dft324((int16_t *)idft_in0,(int16_t *)idft_out0,1); - dft324((int16_t *)idft_in1,(int16_t *)idft_out1,1); - dft324((int16_t *)idft_in2,(int16_t *)idft_out2,1); + dft(DFT_324,(int16_t *)idft_in0,(int16_t *)idft_out0,1); + dft(DFT_324,(int16_t *)idft_in1,(int16_t *)idft_out1,1); + dft(DFT_324,(int16_t *)idft_in2,(int16_t *)idft_out2,1); break; case 360: - dft360((int16_t *)idft_in0,(int16_t *)idft_out0,1); - dft360((int16_t *)idft_in1,(int16_t *)idft_out1,1); - dft360((int16_t *)idft_in2,(int16_t *)idft_out2,1); + dft(DFT_360,(int16_t *)idft_in0,(int16_t *)idft_out0,1); + dft(DFT_360,(int16_t *)idft_in1,(int16_t *)idft_out1,1); + dft(DFT_360,(int16_t *)idft_in2,(int16_t *)idft_out2,1); break; case 384: - dft384((int16_t *)idft_in0,(int16_t *)idft_out0,1); - dft384((int16_t *)idft_in1,(int16_t *)idft_out1,1); - dft384((int16_t *)idft_in2,(int16_t *)idft_out2,1); + dft(DFT_384,(int16_t *)idft_in0,(int16_t *)idft_out0,1); + dft(DFT_384,(int16_t *)idft_in1,(int16_t *)idft_out1,1); + dft(DFT_384,(int16_t *)idft_in2,(int16_t *)idft_out2,1); break; case 432: - dft432((int16_t *)idft_in0,(int16_t *)idft_out0,1); - dft432((int16_t *)idft_in1,(int16_t *)idft_out1,1); - dft432((int16_t *)idft_in2,(int16_t *)idft_out2,1); + dft(DFT_432,(int16_t *)idft_in0,(int16_t *)idft_out0,1); + dft(DFT_432,(int16_t *)idft_in1,(int16_t *)idft_out1,1); + dft(DFT_432,(int16_t *)idft_in2,(int16_t *)idft_out2,1); break; case 480: - dft480((int16_t *)idft_in0,(int16_t *)idft_out0,1); - dft480((int16_t *)idft_in1,(int16_t *)idft_out1,1); - dft480((int16_t *)idft_in2,(int16_t *)idft_out2,1); + dft(DFT_480,(int16_t *)idft_in0,(int16_t *)idft_out0,1); + dft(DFT_480,(int16_t *)idft_in1,(int16_t *)idft_out1,1); + dft(DFT_480,(int16_t *)idft_in2,(int16_t *)idft_out2,1); break; case 540: - dft540((int16_t *)idft_in0,(int16_t *)idft_out0,1); - dft540((int16_t *)idft_in1,(int16_t *)idft_out1,1); - dft540((int16_t *)idft_in2,(int16_t *)idft_out2,1); + dft(DFT_540,(int16_t *)idft_in0,(int16_t *)idft_out0,1); + dft(DFT_540,(int16_t *)idft_in1,(int16_t *)idft_out1,1); + dft(DFT_540,(int16_t *)idft_in2,(int16_t *)idft_out2,1); break; case 576: - dft576((int16_t *)idft_in0,(int16_t *)idft_out0,1); - dft576((int16_t *)idft_in1,(int16_t *)idft_out1,1); - dft576((int16_t *)idft_in2,(int16_t *)idft_out2,1); + dft(DFT_576,(int16_t *)idft_in0,(int16_t *)idft_out0,1); + dft(DFT_576,(int16_t *)idft_in1,(int16_t *)idft_out1,1); + dft(DFT_576,(int16_t *)idft_in2,(int16_t *)idft_out2,1); break; case 600: - dft600((int16_t *)idft_in0,(int16_t *)idft_out0,1); - dft600((int16_t *)idft_in1,(int16_t *)idft_out1,1); - dft600((int16_t *)idft_in2,(int16_t *)idft_out2,1); + dft(DFT_600,(int16_t *)idft_in0,(int16_t *)idft_out0,1); + dft(DFT_600,(int16_t *)idft_in1,(int16_t *)idft_out1,1); + dft(DFT_600,(int16_t *)idft_in2,(int16_t *)idft_out2,1); break; case 648: - dft648((int16_t *)idft_in0,(int16_t *)idft_out0,1); - dft648((int16_t *)idft_in1,(int16_t *)idft_out1,1); - dft648((int16_t *)idft_in2,(int16_t *)idft_out2,1); + dft(DFT_648,(int16_t *)idft_in0,(int16_t *)idft_out0,1); + dft(DFT_648,(int16_t *)idft_in1,(int16_t *)idft_out1,1); + dft(DFT_648,(int16_t *)idft_in2,(int16_t *)idft_out2,1); break; case 720: - dft720((int16_t *)idft_in0,(int16_t *)idft_out0,1); - dft720((int16_t *)idft_in1,(int16_t *)idft_out1,1); - dft720((int16_t *)idft_in2,(int16_t *)idft_out2,1); + dft(DFT_720,(int16_t *)idft_in0,(int16_t *)idft_out0,1); + dft(DFT_720,(int16_t *)idft_in1,(int16_t *)idft_out1,1); + dft(DFT_720,(int16_t *)idft_in2,(int16_t *)idft_out2,1); break; case 768: - dft768((int16_t *)idft_in0,(int16_t *)idft_out0,1); - dft768((int16_t *)idft_in1,(int16_t *)idft_out1,1); - dft768((int16_t *)idft_in2,(int16_t *)idft_out2,1); + dft(DFT_768,(int16_t *)idft_in0,(int16_t *)idft_out0,1); + dft(DFT_768,(int16_t *)idft_in1,(int16_t *)idft_out1,1); + dft(DFT_768,(int16_t *)idft_in2,(int16_t *)idft_out2,1); break; case 864: - dft864((int16_t *)idft_in0,(int16_t *)idft_out0,1); - dft864((int16_t *)idft_in1,(int16_t *)idft_out1,1); - dft864((int16_t *)idft_in2,(int16_t *)idft_out2,1); + dft(DFT_864,(int16_t *)idft_in0,(int16_t *)idft_out0,1); + dft(DFT_864,(int16_t *)idft_in1,(int16_t *)idft_out1,1); + dft(DFT_864,(int16_t *)idft_in2,(int16_t *)idft_out2,1); break; case 900: - dft900((int16_t *)idft_in0,(int16_t *)idft_out0,1); - dft900((int16_t *)idft_in1,(int16_t *)idft_out1,1); - dft900((int16_t *)idft_in2,(int16_t *)idft_out2,1); + dft(DFT_900,(int16_t *)idft_in0,(int16_t *)idft_out0,1); + dft(DFT_900,(int16_t *)idft_in1,(int16_t *)idft_out1,1); + dft(DFT_900,(int16_t *)idft_in2,(int16_t *)idft_out2,1); break; case 960: - dft960((int16_t *)idft_in0,(int16_t *)idft_out0,1); - dft960((int16_t *)idft_in1,(int16_t *)idft_out1,1); - dft960((int16_t *)idft_in2,(int16_t *)idft_out2,1); + dft(DFT_960,(int16_t *)idft_in0,(int16_t *)idft_out0,1); + dft(DFT_960,(int16_t *)idft_in1,(int16_t *)idft_out1,1); + dft(DFT_960,(int16_t *)idft_in2,(int16_t *)idft_out2,1); break; case 972: - dft972((int16_t *)idft_in0,(int16_t *)idft_out0,1); - dft972((int16_t *)idft_in1,(int16_t *)idft_out1,1); - dft972((int16_t *)idft_in2,(int16_t *)idft_out2,1); + dft(DFT_972,(int16_t *)idft_in0,(int16_t *)idft_out0,1); + dft(DFT_972,(int16_t *)idft_in1,(int16_t *)idft_out1,1); + dft(DFT_972,(int16_t *)idft_in2,(int16_t *)idft_out2,1); break; case 1080: - dft1080((int16_t *)idft_in0,(int16_t *)idft_out0,1); - dft1080((int16_t *)idft_in1,(int16_t *)idft_out1,1); - dft1080((int16_t *)idft_in2,(int16_t *)idft_out2,1); + dft(DFT_1080,(int16_t *)idft_in0,(int16_t *)idft_out0,1); + dft(DFT_1080,(int16_t *)idft_in1,(int16_t *)idft_out1,1); + dft(DFT_1080,(int16_t *)idft_in2,(int16_t *)idft_out2,1); break; case 1152: - dft1152((int16_t *)idft_in0,(int16_t *)idft_out0,1); - dft1152((int16_t *)idft_in1,(int16_t *)idft_out1,1); - dft1152((int16_t *)idft_in2,(int16_t *)idft_out2,1); + dft(DFT_1152,(int16_t *)idft_in0,(int16_t *)idft_out0,1); + dft(DFT_1152,(int16_t *)idft_in1,(int16_t *)idft_out1,1); + dft(DFT_1152,(int16_t *)idft_in2,(int16_t *)idft_out2,1); break; case 1200: - dft1200(idft_in0,idft_out0,1); - dft1200(idft_in1,idft_out1,1); - dft1200(idft_in2,idft_out2,1); + dft(DFT_1200,idft_in0,idft_out0,1); + dft(DFT_1200,idft_in1,idft_out1,1); + dft(DFT_1200,idft_in2,idft_out2,1); break; default: diff --git a/openair1/PHY/LTE_UE_TRANSPORT/initial_sync.c b/openair1/PHY/LTE_UE_TRANSPORT/initial_sync.c index afa46de820f17c12fcaecf99cc5050a75c4469b8..ba904629a1ccd34cc46c012b30d1bdf8b61370d0 100644 --- a/openair1/PHY/LTE_UE_TRANSPORT/initial_sync.c +++ b/openair1/PHY/LTE_UE_TRANSPORT/initial_sync.c @@ -38,7 +38,6 @@ #include "PHY/MODULATION/modulation_UE.h" #include "PHY/LTE_ESTIMATION/lte_estimation.h" #include "PHY/LTE_REFSIG/lte_refsig.h" -#include "openair2/LAYER2/MAC/mac_proto.h" #include "common_lib.h" #include "PHY/INIT/phy_init.h" diff --git a/openair1/PHY/LTE_UE_TRANSPORT/prach_ue.c b/openair1/PHY/LTE_UE_TRANSPORT/prach_ue.c index a1b7898a2dcb1c3b8a8f3e3d83904bffbf878a79..e4083863f0da352bfd5c74998414cbd768526601 100644 --- a/openair1/PHY/LTE_UE_TRANSPORT/prach_ue.c +++ b/openair1/PHY/LTE_UE_TRANSPORT/prach_ue.c @@ -338,11 +338,11 @@ int32_t generate_prach( PHY_VARS_UE *ue, uint8_t eNB_id, uint8_t subframe, uint1 switch (ue->frame_parms.N_RB_UL) { case 6: if (prach_fmt == 4) { - idft256(prachF,prach2,1); + idft(IDFT_256,prachF,prach2,1); memmove( prach, prach+512, Ncp<<2 ); prach_len = 256+Ncp; } else { - idft1536(prachF,prach2,1); + idft(IDFT_1536,prachF,prach2,1); memmove( prach, prach+3072, Ncp<<2 ); prach_len = 1536+Ncp; @@ -356,12 +356,12 @@ int32_t generate_prach( PHY_VARS_UE *ue, uint8_t eNB_id, uint8_t subframe, uint1 case 15: if (prach_fmt == 4) { - idft512(prachF,prach2,1); + idft(IDFT_512,prachF,prach2,1); //TODO: account for repeated format in dft output memmove( prach, prach+1024, Ncp<<2 ); prach_len = 512+Ncp; } else { - idft3072(prachF,prach2,1); + idft(IDFT_3072,prachF,prach2,1); memmove( prach, prach+6144, Ncp<<2 ); prach_len = 3072+Ncp; @@ -376,11 +376,11 @@ int32_t generate_prach( PHY_VARS_UE *ue, uint8_t eNB_id, uint8_t subframe, uint1 case 25: default: if (prach_fmt == 4) { - idft1024(prachF,prach2,1); + idft(IDFT_1024,prachF,prach2,1); memmove( prach, prach+2048, Ncp<<2 ); prach_len = 1024+Ncp; } else { - idft6144(prachF,prach2,1); + idft(IDFT_6144,prachF,prach2,1); /*for (i=0;i<6144*2;i++) prach2[i]<<=1;*/ memmove( prach, prach+12288, Ncp<<2 ); @@ -396,11 +396,11 @@ int32_t generate_prach( PHY_VARS_UE *ue, uint8_t eNB_id, uint8_t subframe, uint1 case 50: if (prach_fmt == 4) { - idft2048(prachF,prach2,1); + idft(IDFT_2048,prachF,prach2,1); memmove( prach, prach+4096, Ncp<<2 ); prach_len = 2048+Ncp; } else { - idft12288(prachF,prach2,1); + idft(IDFT_12288,prachF,prach2,1); memmove( prach, prach+24576, Ncp<<2 ); prach_len = 12288+Ncp; @@ -414,12 +414,12 @@ int32_t generate_prach( PHY_VARS_UE *ue, uint8_t eNB_id, uint8_t subframe, uint1 case 75: if (prach_fmt == 4) { - idft3072(prachF,prach2,1); + idft(IDFT_3072,prachF,prach2,1); //TODO: account for repeated format in dft output memmove( prach, prach+6144, Ncp<<2 ); prach_len = 3072+Ncp; } else { - idft18432(prachF,prach2,1); + idft(IDFT_18432,prachF,prach2,1); memmove( prach, prach+36864, Ncp<<2 ); prach_len = 18432+Ncp; @@ -434,11 +434,11 @@ int32_t generate_prach( PHY_VARS_UE *ue, uint8_t eNB_id, uint8_t subframe, uint1 case 100: if (ue->frame_parms.threequarter_fs == 0) { if (prach_fmt == 4) { - idft4096(prachF,prach2,1); + idft(IDFT_4096,prachF,prach2,1); memmove( prach, prach+8192, Ncp<<2 ); prach_len = 4096+Ncp; } else { - idft24576(prachF,prach2,1); + idft(IDFT_24576,prachF,prach2,1); memmove( prach, prach+49152, Ncp<<2 ); prach_len = 24576+Ncp; @@ -449,12 +449,12 @@ int32_t generate_prach( PHY_VARS_UE *ue, uint8_t eNB_id, uint8_t subframe, uint1 } } else { if (prach_fmt == 4) { - idft3072(prachF,prach2,1); + idft(IDFT_3072,prachF,prach2,1); //TODO: account for repeated format in dft output memmove( prach, prach+6144, Ncp<<2 ); prach_len = 3072+Ncp; } else { - idft18432(prachF,prach2,1); + idft(IDFT_18432,prachF,prach2,1); memmove( prach, prach+36864, Ncp<<2 ); prach_len = 18432+Ncp; printf("Generated prach for 100 PRB, 3/4 sampling\n"); diff --git a/openair1/PHY/LTE_UE_TRANSPORT/ulsch_modulation.c b/openair1/PHY/LTE_UE_TRANSPORT/ulsch_modulation.c index a9878b4eae49019a7a4d17063d60561f4bc16a3f..b08fe30248299c18f3dc4d96a986acfee1af1aee 100644 --- a/openair1/PHY/LTE_UE_TRANSPORT/ulsch_modulation.c +++ b/openair1/PHY/LTE_UE_TRANSPORT/ulsch_modulation.c @@ -104,9 +104,9 @@ void dft_lte(int32_t *z,int32_t *d, int32_t Msc_PUSCH, uint8_t Nsymb) switch (Msc_PUSCH) { case 12: - dft12((int16_t *)dft_in0,(int16_t *)dft_out0); - dft12((int16_t *)dft_in1,(int16_t *)dft_out1); - dft12((int16_t *)dft_in2,(int16_t *)dft_out2); + dft(DFT_12,(int16_t *)dft_in0,(int16_t *)dft_out0,0); + dft(DFT_12,(int16_t *)dft_in1,(int16_t *)dft_out1,0); + dft(DFT_12,(int16_t *)dft_in2,(int16_t *)dft_out2,0); /* dft12f(&((__m128i *)dft_in0)[0],&((__m128i *)dft_in0)[1],&((__m128i *)dft_in0)[2],&((__m128i *)dft_in0)[3],&((__m128i *)dft_in0)[4],&((__m128i *)dft_in0)[5],&((__m128i *)dft_in0)[6],&((__m128i *)dft_in0)[7],&((__m128i *)dft_in0)[8],&((__m128i *)dft_in0)[9],&((__m128i *)dft_in0)[10],&((__m128i *)dft_in0)[11], @@ -138,201 +138,201 @@ void dft_lte(int32_t *z,int32_t *d, int32_t Msc_PUSCH, uint8_t Nsymb) break; case 24: - dft24((int16_t*)dft_in0,(int16_t*)dft_out0,1); - dft24((int16_t*)dft_in1,(int16_t*)dft_out1,1); - dft24((int16_t*)dft_in2,(int16_t*)dft_out2,1); + dft(DFT_24,(int16_t*)dft_in0,(int16_t*)dft_out0,1); + dft(DFT_24,(int16_t*)dft_in1,(int16_t*)dft_out1,1); + dft(DFT_24,(int16_t*)dft_in2,(int16_t*)dft_out2,1); break; case 36: - dft36((int16_t*)dft_in0,(int16_t*)dft_out0,1); - dft36((int16_t*)dft_in1,(int16_t*)dft_out1,1); - dft36((int16_t*)dft_in2,(int16_t*)dft_out2,1); + dft(DFT_36,(int16_t*)dft_in0,(int16_t*)dft_out0,1); + dft(DFT_36,(int16_t*)dft_in1,(int16_t*)dft_out1,1); + dft(DFT_36,(int16_t*)dft_in2,(int16_t*)dft_out2,1); break; case 48: - dft48((int16_t*)dft_in0,(int16_t*)dft_out0,1); - dft48((int16_t*)dft_in1,(int16_t*)dft_out1,1); - dft48((int16_t*)dft_in2,(int16_t*)dft_out2,1); + dft(DFT_48,(int16_t*)dft_in0,(int16_t*)dft_out0,1); + dft(DFT_48,(int16_t*)dft_in1,(int16_t*)dft_out1,1); + dft(DFT_48,(int16_t*)dft_in2,(int16_t*)dft_out2,1); break; case 60: - dft60((int16_t*)dft_in0,(int16_t*)dft_out0,1); - dft60((int16_t*)dft_in1,(int16_t*)dft_out1,1); - dft60((int16_t*)dft_in2,(int16_t*)dft_out2,1); + dft(DFT_60,(int16_t*)dft_in0,(int16_t*)dft_out0,1); + dft(DFT_60,(int16_t*)dft_in1,(int16_t*)dft_out1,1); + dft(DFT_60,(int16_t*)dft_in2,(int16_t*)dft_out2,1); break; case 72: - dft72((int16_t*)dft_in0,(int16_t*)dft_out0,1); - dft72((int16_t*)dft_in1,(int16_t*)dft_out1,1); - dft72((int16_t*)dft_in2,(int16_t*)dft_out2,1); + dft(DFT_72,(int16_t*)dft_in0,(int16_t*)dft_out0,1); + dft(DFT_72,(int16_t*)dft_in1,(int16_t*)dft_out1,1); + dft(DFT_72,(int16_t*)dft_in2,(int16_t*)dft_out2,1); break; case 96: - dft96((int16_t*)dft_in0,(int16_t*)dft_out0,1); - dft96((int16_t*)dft_in1,(int16_t*)dft_out1,1); - dft96((int16_t*)dft_in2,(int16_t*)dft_out2,1); + dft(DFT_96,(int16_t*)dft_in0,(int16_t*)dft_out0,1); + dft(DFT_96,(int16_t*)dft_in1,(int16_t*)dft_out1,1); + dft(DFT_96,(int16_t*)dft_in2,(int16_t*)dft_out2,1); break; case 108: - dft108((int16_t*)dft_in0,(int16_t*)dft_out0,1); - dft108((int16_t*)dft_in1,(int16_t*)dft_out1,1); - dft108((int16_t*)dft_in2,(int16_t*)dft_out2,1); + dft(DFT_108,(int16_t*)dft_in0,(int16_t*)dft_out0,1); + dft(DFT_108,(int16_t*)dft_in1,(int16_t*)dft_out1,1); + dft(DFT_108,(int16_t*)dft_in2,(int16_t*)dft_out2,1); break; case 120: - dft120((int16_t*)dft_in0,(int16_t*)dft_out0,1); - dft120((int16_t*)dft_in1,(int16_t*)dft_out1,1); - dft120((int16_t*)dft_in2,(int16_t*)dft_out2,1); + dft(DFT_120,(int16_t*)dft_in0,(int16_t*)dft_out0,1); + dft(DFT_120,(int16_t*)dft_in1,(int16_t*)dft_out1,1); + dft(DFT_120,(int16_t*)dft_in2,(int16_t*)dft_out2,1); break; case 144: - dft144((int16_t*)dft_in0,(int16_t*)dft_out0,1); - dft144((int16_t*)dft_in1,(int16_t*)dft_out1,1); - dft144((int16_t*)dft_in2,(int16_t*)dft_out2,1); + dft(DFT_144,(int16_t*)dft_in0,(int16_t*)dft_out0,1); + dft(DFT_144,(int16_t*)dft_in1,(int16_t*)dft_out1,1); + dft(DFT_144,(int16_t*)dft_in2,(int16_t*)dft_out2,1); break; case 180: - dft180((int16_t*)dft_in0,(int16_t*)dft_out0,1); - dft180((int16_t*)dft_in1,(int16_t*)dft_out1,1); - dft180((int16_t*)dft_in2,(int16_t*)dft_out2,1); + dft(DFT_180,(int16_t*)dft_in0,(int16_t*)dft_out0,1); + dft(DFT_180,(int16_t*)dft_in1,(int16_t*)dft_out1,1); + dft(DFT_180,(int16_t*)dft_in2,(int16_t*)dft_out2,1); break; case 192: - dft192((int16_t*)dft_in0,(int16_t*)dft_out0,1); - dft192((int16_t*)dft_in1,(int16_t*)dft_out1,1); - dft192((int16_t*)dft_in2,(int16_t*)dft_out2,1); + dft(DFT_192,(int16_t*)dft_in0,(int16_t*)dft_out0,1); + dft(DFT_192,(int16_t*)dft_in1,(int16_t*)dft_out1,1); + dft(DFT_192,(int16_t*)dft_in2,(int16_t*)dft_out2,1); break; case 216: - dft216((int16_t*)dft_in0,(int16_t*)dft_out0,1); - dft216((int16_t*)dft_in1,(int16_t*)dft_out1,1); - dft216((int16_t*)dft_in2,(int16_t*)dft_out2,1); + dft(DFT_216,(int16_t*)dft_in0,(int16_t*)dft_out0,1); + dft(DFT_216,(int16_t*)dft_in1,(int16_t*)dft_out1,1); + dft(DFT_216,(int16_t*)dft_in2,(int16_t*)dft_out2,1); break; case 240: - dft240((int16_t*)dft_in0,(int16_t*)dft_out0,1); - dft240((int16_t*)dft_in1,(int16_t*)dft_out1,1); - dft240((int16_t*)dft_in2,(int16_t*)dft_out2,1); + dft(DFT_240,(int16_t*)dft_in0,(int16_t*)dft_out0,1); + dft(DFT_240,(int16_t*)dft_in1,(int16_t*)dft_out1,1); + dft(DFT_240,(int16_t*)dft_in2,(int16_t*)dft_out2,1); break; case 288: - dft288((int16_t*)dft_in0,(int16_t*)dft_out0,1); - dft288((int16_t*)dft_in1,(int16_t*)dft_out1,1); - dft288((int16_t*)dft_in2,(int16_t*)dft_out2,1); + dft(DFT_288,(int16_t*)dft_in0,(int16_t*)dft_out0,1); + dft(DFT_288,(int16_t*)dft_in1,(int16_t*)dft_out1,1); + dft(DFT_288,(int16_t*)dft_in2,(int16_t*)dft_out2,1); break; case 300: - dft300((int16_t*)dft_in0,(int16_t*)dft_out0,1); - dft300((int16_t*)dft_in1,(int16_t*)dft_out1,1); - dft300((int16_t*)dft_in2,(int16_t*)dft_out2,1); + dft(DFT_300,(int16_t*)dft_in0,(int16_t*)dft_out0,1); + dft(DFT_300,(int16_t*)dft_in1,(int16_t*)dft_out1,1); + dft(DFT_300,(int16_t*)dft_in2,(int16_t*)dft_out2,1); break; case 324: - dft324((int16_t*)dft_in0,(int16_t*)dft_out0,1); - dft324((int16_t*)dft_in1,(int16_t*)dft_out1,1); - dft324((int16_t*)dft_in2,(int16_t*)dft_out2,1); + dft(DFT_324,(int16_t*)dft_in0,(int16_t*)dft_out0,1); + dft(DFT_324,(int16_t*)dft_in1,(int16_t*)dft_out1,1); + dft(DFT_324,(int16_t*)dft_in2,(int16_t*)dft_out2,1); break; case 360: - dft360((int16_t*)dft_in0,(int16_t*)dft_out0,1); - dft360((int16_t*)dft_in1,(int16_t*)dft_out1,1); - dft360((int16_t*)dft_in2,(int16_t*)dft_out2,1); + dft(DFT_360,(int16_t*)dft_in0,(int16_t*)dft_out0,1); + dft(DFT_360,(int16_t*)dft_in1,(int16_t*)dft_out1,1); + dft(DFT_360,(int16_t*)dft_in2,(int16_t*)dft_out2,1); break; case 384: - dft384((int16_t*)dft_in0,(int16_t*)dft_out0,1); - dft384((int16_t*)dft_in1,(int16_t*)dft_out1,1); - dft384((int16_t*)dft_in2,(int16_t*)dft_out2,1); + dft(DFT_384,(int16_t*)dft_in0,(int16_t*)dft_out0,1); + dft(DFT_384,(int16_t*)dft_in1,(int16_t*)dft_out1,1); + dft(DFT_384,(int16_t*)dft_in2,(int16_t*)dft_out2,1); break; case 432: - dft432((int16_t*)dft_in0,(int16_t*)dft_out0,1); - dft432((int16_t*)dft_in1,(int16_t*)dft_out1,1); - dft432((int16_t*)dft_in2,(int16_t*)dft_out2,1); + dft(DFT_432,(int16_t*)dft_in0,(int16_t*)dft_out0,1); + dft(DFT_432,(int16_t*)dft_in1,(int16_t*)dft_out1,1); + dft(DFT_432,(int16_t*)dft_in2,(int16_t*)dft_out2,1); break; case 480: - dft480((int16_t*)dft_in0,(int16_t*)dft_out0,1); - dft480((int16_t*)dft_in1,(int16_t*)dft_out1,1); - dft480((int16_t*)dft_in2,(int16_t*)dft_out2,1); + dft(DFT_480,(int16_t*)dft_in0,(int16_t*)dft_out0,1); + dft(DFT_480,(int16_t*)dft_in1,(int16_t*)dft_out1,1); + dft(DFT_480,(int16_t*)dft_in2,(int16_t*)dft_out2,1); break; case 540: - dft540((int16_t*)dft_in0,(int16_t*)dft_out0,1); - dft540((int16_t*)dft_in1,(int16_t*)dft_out1,1); - dft540((int16_t*)dft_in2,(int16_t*)dft_out2,1); + dft(DFT_540,(int16_t*)dft_in0,(int16_t*)dft_out0,1); + dft(DFT_540,(int16_t*)dft_in1,(int16_t*)dft_out1,1); + dft(DFT_540,(int16_t*)dft_in2,(int16_t*)dft_out2,1); break; case 576: - dft576((int16_t*)dft_in0,(int16_t*)dft_out0,1); - dft576((int16_t*)dft_in1,(int16_t*)dft_out1,1); - dft576((int16_t*)dft_in2,(int16_t*)dft_out2,1); + dft(DFT_576,(int16_t*)dft_in0,(int16_t*)dft_out0,1); + dft(DFT_576,(int16_t*)dft_in1,(int16_t*)dft_out1,1); + dft(DFT_576,(int16_t*)dft_in2,(int16_t*)dft_out2,1); break; case 600: - dft600((int16_t*)dft_in0,(int16_t*)dft_out0,1); - dft600((int16_t*)dft_in1,(int16_t*)dft_out1,1); - dft600((int16_t*)dft_in2,(int16_t*)dft_out2,1); + dft(DFT_600,(int16_t*)dft_in0,(int16_t*)dft_out0,1); + dft(DFT_600,(int16_t*)dft_in1,(int16_t*)dft_out1,1); + dft(DFT_600,(int16_t*)dft_in2,(int16_t*)dft_out2,1); break; case 648: - dft648((int16_t*)dft_in0,(int16_t*)dft_out0,1); - dft648((int16_t*)dft_in1,(int16_t*)dft_out1,1); - dft648((int16_t*)dft_in2,(int16_t*)dft_out2,1); + dft(DFT_648,(int16_t*)dft_in0,(int16_t*)dft_out0,1); + dft(DFT_648,(int16_t*)dft_in1,(int16_t*)dft_out1,1); + dft(DFT_648,(int16_t*)dft_in2,(int16_t*)dft_out2,1); break; case 720: - dft720((int16_t*)dft_in0,(int16_t*)dft_out0,1); - dft720((int16_t*)dft_in1,(int16_t*)dft_out1,1); - dft720((int16_t*)dft_in2,(int16_t*)dft_out2,1); + dft(DFT_720,(int16_t*)dft_in0,(int16_t*)dft_out0,1); + dft(DFT_720,(int16_t*)dft_in1,(int16_t*)dft_out1,1); + dft(DFT_720,(int16_t*)dft_in2,(int16_t*)dft_out2,1); break; case 768: - dft768((int16_t*)dft_in0,(int16_t*)dft_out0,1); - dft768((int16_t*)dft_in1,(int16_t*)dft_out1,1); - dft768((int16_t*)dft_in2,(int16_t*)dft_out2,1); + dft(DFT_768,(int16_t*)dft_in0,(int16_t*)dft_out0,1); + dft(DFT_768,(int16_t*)dft_in1,(int16_t*)dft_out1,1); + dft(DFT_768,(int16_t*)dft_in2,(int16_t*)dft_out2,1); break; case 864: - dft864((int16_t*)dft_in0,(int16_t*)dft_out0,1); - dft864((int16_t*)dft_in1,(int16_t*)dft_out1,1); - dft864((int16_t*)dft_in2,(int16_t*)dft_out2,1); + dft(DFT_864,(int16_t*)dft_in0,(int16_t*)dft_out0,1); + dft(DFT_864,(int16_t*)dft_in1,(int16_t*)dft_out1,1); + dft(DFT_864,(int16_t*)dft_in2,(int16_t*)dft_out2,1); break; case 900: - dft900((int16_t*)dft_in0,(int16_t*)dft_out0,1); - dft900((int16_t*)dft_in1,(int16_t*)dft_out1,1); - dft900((int16_t*)dft_in2,(int16_t*)dft_out2,1); + dft(DFT_900,(int16_t*)dft_in0,(int16_t*)dft_out0,1); + dft(DFT_900,(int16_t*)dft_in1,(int16_t*)dft_out1,1); + dft(DFT_900,(int16_t*)dft_in2,(int16_t*)dft_out2,1); break; case 960: - dft960((int16_t*)dft_in0,(int16_t*)dft_out0,1); - dft960((int16_t*)dft_in1,(int16_t*)dft_out1,1); - dft960((int16_t*)dft_in2,(int16_t*)dft_out2,1); + dft(DFT_960,(int16_t*)dft_in0,(int16_t*)dft_out0,1); + dft(DFT_960,(int16_t*)dft_in1,(int16_t*)dft_out1,1); + dft(DFT_960,(int16_t*)dft_in2,(int16_t*)dft_out2,1); break; case 972: - dft972((int16_t*)dft_in0,(int16_t*)dft_out0,1); - dft972((int16_t*)dft_in1,(int16_t*)dft_out1,1); - dft972((int16_t*)dft_in2,(int16_t*)dft_out2,1); + dft(DFT_972,(int16_t*)dft_in0,(int16_t*)dft_out0,1); + dft(DFT_972,(int16_t*)dft_in1,(int16_t*)dft_out1,1); + dft(DFT_972,(int16_t*)dft_in2,(int16_t*)dft_out2,1); break; case 1080: - dft1080((int16_t*)dft_in0,(int16_t*)dft_out0,1); - dft1080((int16_t*)dft_in1,(int16_t*)dft_out1,1); - dft1080((int16_t*)dft_in2,(int16_t*)dft_out2,1); + dft(DFT_1080,(int16_t*)dft_in0,(int16_t*)dft_out0,1); + dft(DFT_1080,(int16_t*)dft_in1,(int16_t*)dft_out1,1); + dft(DFT_1080,(int16_t*)dft_in2,(int16_t*)dft_out2,1); break; case 1152: - dft1152((int16_t*)dft_in0,(int16_t*)dft_out0,1); - dft1152((int16_t*)dft_in1,(int16_t*)dft_out1,1); - dft1152((int16_t*)dft_in2,(int16_t*)dft_out2,1); + dft(DFT_1152,(int16_t*)dft_in0,(int16_t*)dft_out0,1); + dft(DFT_1152,(int16_t*)dft_in1,(int16_t*)dft_out1,1); + dft(DFT_1152,(int16_t*)dft_in2,(int16_t*)dft_out2,1); break; case 1200: - dft1200((int16_t*)dft_in0,(int16_t*)dft_out0,1); - dft1200((int16_t*)dft_in1,(int16_t*)dft_out1,1); - dft1200((int16_t*)dft_in2,(int16_t*)dft_out2,1); + dft(DFT_1200,(int16_t*)dft_in0,(int16_t*)dft_out0,1); + dft(DFT_1200,(int16_t*)dft_in1,(int16_t*)dft_out1,1); + dft(DFT_1200,(int16_t*)dft_in2,(int16_t*)dft_out2,1); break; } diff --git a/openair1/PHY/MODULATION/nr_modulation.c b/openair1/PHY/MODULATION/nr_modulation.c index 5c8fce3c3862641ecdd4dc39315e5cd542e0e984..b27b692e66122244cba89b409b0bc9343d235a88 100644 --- a/openair1/PHY/MODULATION/nr_modulation.c +++ b/openair1/PHY/MODULATION/nr_modulation.c @@ -242,7 +242,7 @@ void nr_dft(int32_t *z, int32_t *d, uint32_t Msc_PUSCH) switch (Msc_PUSCH) { case 12: - dft12((int16_t *)dft_in0, (int16_t *)dft_out0); + dft(DFT_12,(int16_t *)dft_in0, (int16_t *)dft_out0,0); #if defined(__x86_64__) || defined(__i386__) norm128 = _mm_set1_epi16(9459); @@ -260,135 +260,135 @@ void nr_dft(int32_t *z, int32_t *d, uint32_t Msc_PUSCH) break; case 24: - dft24((int16_t*)dft_in0, (int16_t*)dft_out0, 1); + dft(DFT_24,(int16_t*)dft_in0, (int16_t*)dft_out0, 1); break; case 36: - dft36((int16_t*)dft_in0, (int16_t*)dft_out0, 1); + dft(DFT_36,(int16_t*)dft_in0, (int16_t*)dft_out0, 1); break; case 48: - dft48((int16_t*)dft_in0, (int16_t*)dft_out0, 1); + dft(DFT_48,(int16_t*)dft_in0, (int16_t*)dft_out0, 1); break; case 60: - dft60((int16_t*)dft_in0, (int16_t*)dft_out0, 1); + dft(DFT_60,(int16_t*)dft_in0, (int16_t*)dft_out0, 1); break; case 72: - dft72((int16_t*)dft_in0, (int16_t*)dft_out0, 1); + dft(DFT_72,(int16_t*)dft_in0, (int16_t*)dft_out0, 1); break; case 96: - dft96((int16_t*)dft_in0, (int16_t*)dft_out0, 1); + dft(DFT_96,(int16_t*)dft_in0, (int16_t*)dft_out0, 1); break; case 108: - dft108((int16_t*)dft_in0, (int16_t*)dft_out0, 1); + dft(DFT_108,(int16_t*)dft_in0, (int16_t*)dft_out0, 1); break; case 120: - dft120((int16_t*)dft_in0, (int16_t*)dft_out0, 1); + dft(DFT_120,(int16_t*)dft_in0, (int16_t*)dft_out0, 1); break; case 144: - dft144((int16_t*)dft_in0, (int16_t*)dft_out0, 1); + dft(DFT_144,(int16_t*)dft_in0, (int16_t*)dft_out0, 1); break; case 180: - dft180((int16_t*)dft_in0, (int16_t*)dft_out0, 1); + dft(DFT_180,(int16_t*)dft_in0, (int16_t*)dft_out0, 1); break; case 192: - dft192((int16_t*)dft_in0, (int16_t*)dft_out0, 1); + dft(DFT_192,(int16_t*)dft_in0, (int16_t*)dft_out0, 1); break; case 216: - dft216((int16_t*)dft_in0, (int16_t*)dft_out0, 1); + dft(DFT_216,(int16_t*)dft_in0, (int16_t*)dft_out0, 1); break; case 240: - dft240((int16_t*)dft_in0, (int16_t*)dft_out0, 1); + dft(DFT_240,(int16_t*)dft_in0, (int16_t*)dft_out0, 1); break; case 288: - dft288((int16_t*)dft_in0, (int16_t*)dft_out0, 1); + dft(DFT_288,(int16_t*)dft_in0, (int16_t*)dft_out0, 1); break; case 300: - dft300((int16_t*)dft_in0, (int16_t*)dft_out0, 1); + dft(DFT_300,(int16_t*)dft_in0, (int16_t*)dft_out0, 1); break; case 324: - dft324((int16_t*)dft_in0, (int16_t*)dft_out0, 1); + dft(DFT_324,(int16_t*)dft_in0, (int16_t*)dft_out0, 1); break; case 360: - dft360((int16_t*)dft_in0, (int16_t*)dft_out0, 1); + dft(DFT_360,(int16_t*)dft_in0, (int16_t*)dft_out0, 1); break; case 384: - dft384((int16_t*)dft_in0, (int16_t*)dft_out0, 1); + dft(DFT_384,(int16_t*)dft_in0, (int16_t*)dft_out0, 1); break; case 432: - dft432((int16_t*)dft_in0, (int16_t*)dft_out0, 1); + dft(DFT_432,(int16_t*)dft_in0, (int16_t*)dft_out0, 1); break; case 480: - dft480((int16_t*)dft_in0, (int16_t*)dft_out0, 1); + dft(DFT_480,(int16_t*)dft_in0, (int16_t*)dft_out0, 1); break; case 540: - dft540((int16_t*)dft_in0, (int16_t*)dft_out0, 1); + dft(DFT_540,(int16_t*)dft_in0, (int16_t*)dft_out0, 1); break; case 576: - dft576((int16_t*)dft_in0, (int16_t*)dft_out0, 1); + dft(DFT_576,(int16_t*)dft_in0, (int16_t*)dft_out0, 1); break; case 600: - dft600((int16_t*)dft_in0, (int16_t*)dft_out0, 1); + dft(DFT_600,(int16_t*)dft_in0, (int16_t*)dft_out0, 1); break; case 648: - dft648((int16_t*)dft_in0, (int16_t*)dft_out0, 1); + dft(DFT_648,(int16_t*)dft_in0, (int16_t*)dft_out0, 1); break; case 720: - dft720((int16_t*)dft_in0, (int16_t*)dft_out0, 1); + dft(DFT_720,(int16_t*)dft_in0, (int16_t*)dft_out0, 1); break; case 768: - dft768((int16_t*)dft_in0, (int16_t*)dft_out0, 1); + dft(DFT_768,(int16_t*)dft_in0, (int16_t*)dft_out0, 1); break; case 864: - dft864((int16_t*)dft_in0, (int16_t*)dft_out0, 1); + dft(DFT_864,(int16_t*)dft_in0, (int16_t*)dft_out0, 1); break; case 900: - dft900((int16_t*)dft_in0, (int16_t*)dft_out0, 1); + dft(DFT_900,(int16_t*)dft_in0, (int16_t*)dft_out0, 1); break; case 960: - dft960((int16_t*)dft_in0, (int16_t*)dft_out0, 1); + dft(DFT_960,(int16_t*)dft_in0, (int16_t*)dft_out0, 1); break; case 972: - dft972((int16_t*)dft_in0, (int16_t*)dft_out0, 1); + dft(DFT_960,(int16_t*)dft_in0, (int16_t*)dft_out0, 1); break; case 1080: - dft1080((int16_t*)dft_in0, (int16_t*)dft_out0, 1); + dft(DFT_1080,(int16_t*)dft_in0, (int16_t*)dft_out0, 1); break; case 1152: - dft1152((int16_t*)dft_in0, (int16_t*)dft_out0, 1); + dft(DFT_1152,(int16_t*)dft_in0, (int16_t*)dft_out0, 1); break; case 1200: - dft1200((int16_t*)dft_in0, (int16_t*)dft_out0, 1); + dft(DFT_1200,(int16_t*)dft_in0, (int16_t*)dft_out0, 1); break; } diff --git a/openair1/PHY/MODULATION/ofdm_mod.c b/openair1/PHY/MODULATION/ofdm_mod.c index cbeeca13278f6147c0ce2657f95da5faef7e490d..855e649cc5e629a128ba9ffcc680f07c6525956d 100644 --- a/openair1/PHY/MODULATION/ofdm_mod.c +++ b/openair1/PHY/MODULATION/ofdm_mod.c @@ -95,41 +95,41 @@ void PHY_ofdm_mod(int *input, /// pointer to complex input volatile int *output_ptr=(int*)0; int *temp_ptr=(int*)0; - void (*idft)(int16_t *,int16_t *, int); + idft_size_idx_t idftsize; switch (fftsize) { case 128: - idft = idft128; + idftsize = IDFT_128; break; case 256: - idft = idft256; + idftsize = IDFT_256; break; case 512: - idft = idft512; + idftsize = IDFT_512; break; case 1024: - idft = idft1024; + idftsize = IDFT_1024; break; case 1536: - idft = idft1536; + idftsize = IDFT_1536; break; case 2048: - idft = idft2048; + idftsize = IDFT_2048; break; case 3072: - idft = idft3072; + idftsize = IDFT_3072; break; case 4096: - idft = idft4096; + idftsize = IDFT_4096; break; default: - idft = idft512; + idftsize = IDFT_512; break; } @@ -148,12 +148,12 @@ void PHY_ofdm_mod(int *input, /// pointer to complex input #ifndef __AVX2__ // handle 128-bit alignment for 128-bit SIMD (SSE4,NEON,AltiVEC) - idft((int16_t *)&input[i*fftsize], + idft(idftsize,(int16_t *)&input[i*fftsize], (fftsize==128) ? (int16_t *)temp : (int16_t *)&output[(i*fftsize) + ((1+i)*nb_prefix_samples)], 1); #else // on AVX2 need 256-bit alignment - idft((int16_t *)&input[i*fftsize], + idft(idftsize,(int16_t *)&input[i*fftsize], (int16_t *)temp, 1); diff --git a/openair1/PHY/MODULATION/slot_fep.c b/openair1/PHY/MODULATION/slot_fep.c index 163ebac65f7a81938b7dd97b743f2846945c9b33..8f41735f10cfa5fd4a915a7d8cb825b2305c03ba 100644 --- a/openair1/PHY/MODULATION/slot_fep.c +++ b/openair1/PHY/MODULATION/slot_fep.c @@ -49,36 +49,36 @@ int slot_fep(PHY_VARS_UE *ue, unsigned char harq_pid = dlsch_ue[0]->current_harq_pid; LTE_DL_UE_HARQ_t *dlsch0_harq = dlsch_ue[0]->harq_processes[harq_pid]; int uespec_pilot[9][1200];*/ - void (*dft)(int16_t *,int16_t *, int); + dft_size_idx_t dftsizeidx; int tmp_dft_in[2048] __attribute__ ((aligned (32))); // This is for misalignment issues for 6 and 15 PRBs switch (frame_parms->ofdm_symbol_size) { case 128: - dft = dft128; - break; - - case 256: - dft = dft256; - break; - - case 512: - dft = dft512; - break; - - case 1024: - dft = dft1024; - break; - - case 1536: - dft = dft1536; - break; - - case 2048: - dft = dft2048; + dftsizeidx = DFT_128; + break; + + case 256: + dftsizeidx = DFT_256; + break; + + case 512: + dftsizeidx = DFT_512; + break; + + case 1024: + dftsizeidx = DFT_1024; + break; + + case 1536: + dftsizeidx = DFT_1536; + break; + + case 2048: + dftsizeidx = DFT_2048; break; default: - dft = dft512; + dftsizeidx = DFT_512; break; } @@ -118,13 +118,13 @@ int slot_fep(PHY_VARS_UE *ue, memcpy((void *)tmp_dft_in, (void *)&common_vars->rxdata[aa][rx_offset % frame_length_samples], frame_parms->ofdm_symbol_size*sizeof(int)); - dft((int16_t *)tmp_dft_in, + dft(dftsizeidx,(int16_t *)tmp_dft_in, (int16_t *)&common_vars->common_vars_rx_data_per_thread[ue->current_thread_id[Ns>>1]].rxdataF[aa][frame_parms->ofdm_symbol_size*symbol],1); } else { // use dft input from RX buffer directly #if UE_TIMING_TRACE start_meas(&ue->rx_dft_stats); #endif - dft((int16_t *)&common_vars->rxdata[aa][(rx_offset) % frame_length_samples], + dft(dftsizeidx,(int16_t *)&common_vars->rxdata[aa][(rx_offset) % frame_length_samples], (int16_t *)&common_vars->common_vars_rx_data_per_thread[ue->current_thread_id[Ns>>1]].rxdataF[aa][frame_parms->ofdm_symbol_size*symbol],1); #if UE_TIMING_TRACE stop_meas(&ue->rx_dft_stats); @@ -153,10 +153,10 @@ int slot_fep(PHY_VARS_UE *ue, memcpy((void *)tmp_dft_in, (void *)&common_vars->rxdata[aa][(rx_offset) % frame_length_samples], frame_parms->ofdm_symbol_size*sizeof(int)); - dft((int16_t *)tmp_dft_in, + dft(dftsizeidx,(int16_t *)tmp_dft_in, (int16_t *)&common_vars->common_vars_rx_data_per_thread[ue->current_thread_id[Ns>>1]].rxdataF[aa][frame_parms->ofdm_symbol_size*symbol],1); } else { // use dft input from RX buffer directly - dft((int16_t *)&common_vars->rxdata[aa][(rx_offset) % frame_length_samples], + dft(dftsizeidx,(int16_t *)&common_vars->rxdata[aa][(rx_offset) % frame_length_samples], (int16_t *)&common_vars->common_vars_rx_data_per_thread[ue->current_thread_id[Ns>>1]].rxdataF[aa][frame_parms->ofdm_symbol_size*symbol],1); } @@ -247,36 +247,36 @@ int front_end_fft(PHY_VARS_UE *ue, unsigned char harq_pid = dlsch_ue[0]->current_harq_pid; LTE_DL_UE_HARQ_t *dlsch0_harq = dlsch_ue[0]->harq_processes[harq_pid]; int uespec_pilot[9][1200];*/ - void (*dft)(int16_t *,int16_t *, int); + dft_size_idx_t dftsizeidx; int tmp_dft_in[2048] __attribute__ ((aligned (32))); // This is for misalignment issues for 6 and 15 PRBs switch (frame_parms->ofdm_symbol_size) { case 128: - dft = dft128; - break; - - case 256: - dft = dft256; - break; - - case 512: - dft = dft512; - break; - - case 1024: - dft = dft1024; - break; - - case 1536: - dft = dft1536; - break; - - case 2048: - dft = dft2048; - break; - - default: - dft = dft512; + dftsizeidx = DFT_128; + break; + + case 256: + dftsizeidx = DFT_256; + break; + + case 512: + dftsizeidx = DFT_512; + break; + + case 1024: + dftsizeidx = DFT_1024; + break; + + case 1536: + dftsizeidx = DFT_1536; + break; + + case 2048: + dftsizeidx = DFT_2048; + break; + + default: + dftsizeidx = DFT_512; break; } @@ -319,11 +319,11 @@ int front_end_fft(PHY_VARS_UE *ue, memcpy((void *)tmp_dft_in, (void *)&common_vars->rxdata[aa][rx_offset % frame_length_samples], frame_parms->ofdm_symbol_size*sizeof(int)); - dft((int16_t *)tmp_dft_in, + dft(dftsizeidx,(int16_t *)tmp_dft_in, (int16_t *)&common_vars->common_vars_rx_data_per_thread[threadId].rxdataF[aa][frame_parms->ofdm_symbol_size*symbol],1); } else { // use dft input from RX buffer directly start_meas(&ue->rx_dft_stats); - dft((int16_t *)&common_vars->rxdata[aa][(rx_offset) % frame_length_samples], + dft(dftsizeidx,(int16_t *)&common_vars->rxdata[aa][(rx_offset) % frame_length_samples], (int16_t *)&common_vars->common_vars_rx_data_per_thread[threadId].rxdataF[aa][frame_parms->ofdm_symbol_size*symbol],1); stop_meas(&ue->rx_dft_stats); } @@ -349,10 +349,10 @@ int front_end_fft(PHY_VARS_UE *ue, memcpy((void *)tmp_dft_in, (void *)&common_vars->rxdata[aa][(rx_offset) % frame_length_samples], frame_parms->ofdm_symbol_size*sizeof(int)); - dft((int16_t *)tmp_dft_in, + dft(dftsizeidx,(int16_t *)tmp_dft_in, (int16_t *)&common_vars->common_vars_rx_data_per_thread[threadId].rxdataF[aa][frame_parms->ofdm_symbol_size*symbol],1); } else { // use dft input from RX buffer directly - dft((int16_t *)&common_vars->rxdata[aa][(rx_offset) % frame_length_samples], + dft(dftsizeidx,(int16_t *)&common_vars->rxdata[aa][(rx_offset) % frame_length_samples], (int16_t *)&common_vars->common_vars_rx_data_per_thread[threadId].rxdataF[aa][frame_parms->ofdm_symbol_size*symbol],1); } diff --git a/openair1/PHY/MODULATION/slot_fep_mbsfn.c b/openair1/PHY/MODULATION/slot_fep_mbsfn.c index 38d78119e3fefe839bd34a3e270dc4a73247b163..603674502973f973275dd913480a1c4645963205 100644 --- a/openair1/PHY/MODULATION/slot_fep_mbsfn.c +++ b/openair1/PHY/MODULATION/slot_fep_mbsfn.c @@ -42,35 +42,35 @@ int slot_fep_mbsfn(PHY_VARS_UE *ue, unsigned int subframe_offset; // int i; unsigned int frame_length_samples = frame_parms->samples_per_tti * 10; - void (*dft)(int16_t *,int16_t *, int); + dft_size_idx_t dftsizeidx; switch (frame_parms->ofdm_symbol_size) { case 128: - dft = dft128; - break; - - case 256: - dft = dft256; - break; - - case 512: - dft = dft512; - break; - - case 1024: - dft = dft1024; - break; - - case 1536: - dft = dft1536; - break; - - case 2048: - dft = dft2048; - break; - - default: - dft = dft512; + dftsizeidx = DFT_128; + break; + + case 256: + dftsizeidx = DFT_256; + break; + + case 512: + dftsizeidx = DFT_512; + break; + + case 1024: + dftsizeidx = DFT_1024; + break; + + case 1536: + dftsizeidx = DFT_1536; + break; + + case 2048: + dftsizeidx = DFT_2048; + break; + + default: + dftsizeidx = DFT_512; break; } @@ -110,7 +110,7 @@ int slot_fep_mbsfn(PHY_VARS_UE *ue, #if UE_TIMING_TRACE start_meas(&ue->rx_dft_stats); #endif - dft((int16_t *)&common_vars->rxdata[aa][(sample_offset + + dft(dftsizeidx,(int16_t *)&common_vars->rxdata[aa][(sample_offset + nb_prefix_samples0 + subframe_offset - SOFFSET) % frame_length_samples], @@ -131,7 +131,7 @@ int slot_fep_mbsfn(PHY_VARS_UE *ue, #if UE_TIMING_TRACE start_meas(&ue->rx_dft_stats); #endif - dft((int16_t *)&common_vars->rxdata[aa][(sample_offset + + dft(dftsizeidx,(int16_t *)&common_vars->rxdata[aa][(sample_offset + (frame_parms->ofdm_symbol_size+nb_prefix_samples0+nb_prefix_samples) + (frame_parms->ofdm_symbol_size+nb_prefix_samples)*(l-1) + subframe_offset- @@ -208,43 +208,43 @@ int slot_fep_mbsfn_khz_1dot25(PHY_VARS_UE *ue, int ofdm_symbol_size; unsigned int subframe_offset; unsigned int frame_length_samples = frame_parms->samples_per_tti * 10; - void (*dft)(int16_t *,int16_t *, int); + dft_size_idx_t dftsizeidx; AssertFatal(frame_parms->frame_type == FDD, "Frame is TDD!\n"); switch (frame_parms->ofdm_symbol_size) { case 128: - dft = dft1536; + dftsizeidx = DFT_1536; ofdm_symbol_size=1536; nb_prefix_samples=384; break; case 256: AssertFatal(1==0,"FeMBMS dft3072 not implemented\n"); - dft = dft3072; + dftsizeidx = DFT_3072; ofdm_symbol_size=3072; nb_prefix_samples=768; break; case 512: - dft = dft6144; + dftsizeidx = DFT_6144; nb_prefix_samples=1536; ofdm_symbol_size=6144; break; case 1024: - dft = dft12288; + dftsizeidx = DFT_12288; nb_prefix_samples=3072; ofdm_symbol_size=12288; break; case 1536: - dft = dft18432; + dftsizeidx = DFT_18432; nb_prefix_samples=4608; ofdm_symbol_size=18432; break; case 2048: - dft = dft24576; + dftsizeidx = DFT_24576; nb_prefix_samples=6144; ofdm_symbol_size=24576; break; @@ -265,7 +265,7 @@ int slot_fep_mbsfn_khz_1dot25(PHY_VARS_UE *ue, #if UE_TIMING_TRACE start_meas(&ue->rx_dft_stats); #endif - dft((int16_t *)&common_vars->rxdata[aa][(sample_offset + + dft(dftsizeidx,(int16_t *)&common_vars->rxdata[aa][(sample_offset + nb_prefix_samples + subframe_offset - SOFFSET) % frame_length_samples], diff --git a/openair1/PHY/MODULATION/slot_fep_nr.c b/openair1/PHY/MODULATION/slot_fep_nr.c index f2e5d24badb305acd0c912e99120220a45ad5b29..c5c4d0b63821ac78cbb6d43a382f0c65be4cfcb2 100644 --- a/openair1/PHY/MODULATION/slot_fep_nr.c +++ b/openair1/PHY/MODULATION/slot_fep_nr.c @@ -62,44 +62,44 @@ int nr_slot_fep(PHY_VARS_NR_UE *ue, unsigned int rx_offset; - void (*dft)(int16_t *,int16_t *, int); + dft_size_idx_t dftsize; int tmp_dft_in[8192] __attribute__ ((aligned (32))); // This is for misalignment issues for 6 and 15 PRBs switch (frame_parms->ofdm_symbol_size) { case 128: - dft = dft128; + dftsize = DFT_128; break; case 256: - dft = dft256; + dftsize = DFT_256; break; case 512: - dft = dft512; + dftsize = DFT_512; break; case 1024: - dft = dft1024; + dftsize = DFT_1024; break; case 1536: - dft = dft1536; + dftsize = DFT_1536; break; case 2048: - dft = dft2048; + dftsize = DFT_2048; break; case 3072: - dft = dft3072; + dftsize = DFT_3072; break; case 4096: - dft = dft4096; + dftsize = DFT_4096; break; case 8192: - dft = dft8192; + dftsize = DFT_8192; break; default: @@ -155,14 +155,14 @@ int nr_slot_fep(PHY_VARS_NR_UE *ue, memcpy((void *)tmp_dft_in, (void *) &common_vars->rxdata[aa][rx_offset % frame_length_samples], frame_parms->ofdm_symbol_size*sizeof(int)); - dft((int16_t *)tmp_dft_in, + dft(dftsize,(int16_t *)tmp_dft_in, (int16_t *)&common_vars->common_vars_rx_data_per_thread[ue->current_thread_id[Ns]].rxdataF[aa][frame_parms->ofdm_symbol_size*symbol],1); } else { // use dft input from RX buffer directly #if UE_TIMING_TRACE start_meas(&ue->rx_dft_stats); #endif - dft((int16_t *) &common_vars->rxdata[aa][(rx_offset) % frame_length_samples], + dft(dftsize,(int16_t *) &common_vars->rxdata[aa][(rx_offset) % frame_length_samples], (int16_t *)&common_vars->common_vars_rx_data_per_thread[ue->current_thread_id[Ns]].rxdataF[aa][frame_parms->ofdm_symbol_size*symbol],1); #if UE_TIMING_TRACE stop_meas(&ue->rx_dft_stats); @@ -183,11 +183,11 @@ int nr_slot_fep(PHY_VARS_NR_UE *ue, memcpy((void *)tmp_dft_in, (void *) &common_vars->rxdata[aa][(rx_offset) % frame_length_samples], frame_parms->ofdm_symbol_size*sizeof(int)); - dft((int16_t *)tmp_dft_in, + dft(dftsize,(int16_t *)tmp_dft_in, (int16_t *)&common_vars->common_vars_rx_data_per_thread[ue->current_thread_id[Ns]].rxdataF[aa][frame_parms->ofdm_symbol_size*symbol],1); } else { // use dft input from RX buffer directly - dft((int16_t *) &common_vars->rxdata[aa][(rx_offset) % frame_length_samples], + dft(dftsize,(int16_t *) &common_vars->rxdata[aa][(rx_offset) % frame_length_samples], (int16_t *)&common_vars->common_vars_rx_data_per_thread[ue->current_thread_id[Ns]].rxdataF[aa][frame_parms->ofdm_symbol_size*symbol],1); } #if UE_TIMING_TRACE @@ -237,44 +237,44 @@ int nr_slot_fep_init_sync(PHY_VARS_NR_UE *ue, unsigned int rx_offset; - void (*dft)(int16_t *,int16_t *, int); + dft_size_idx_t dftsize; int tmp_dft_in[8192] __attribute__ ((aligned (32))); // This is for misalignment issues for 6 and 15 PRBs switch (frame_parms->ofdm_symbol_size) { case 128: - dft = dft128; + dftsize = DFT_128; break; case 256: - dft = dft256; + dftsize = DFT_256; break; case 512: - dft = dft512; + dftsize = DFT_512; break; case 1024: - dft = dft1024; + dftsize = DFT_1024; break; case 1536: - dft = dft1536; + dftsize = DFT_1536; break; case 2048: - dft = dft2048; + dftsize = DFT_2048; break; case 3072: - dft = dft3072; + dftsize = DFT_3072; break; case 4096: - dft = dft4096; + dftsize = DFT_4096; break; case 8192: - dft = dft8192; + dftsize = DFT_8192; break; default: @@ -330,14 +330,15 @@ int nr_slot_fep_init_sync(PHY_VARS_NR_UE *ue, memcpy((void *)tmp_dft_in, (void *) &common_vars->rxdata[aa][rx_offset], frame_parms->ofdm_symbol_size*sizeof(int)); - dft((int16_t *)tmp_dft_in, + dft(dftsize,(int16_t *)tmp_dft_in, (int16_t *)&common_vars->common_vars_rx_data_per_thread[ue->current_thread_id[Ns]].rxdataF[aa][frame_parms->ofdm_symbol_size*symbol],1); } else { // use dft input from RX buffer directly #if UE_TIMING_TRACE start_meas(&ue->rx_dft_stats); #endif - dft((int16_t *) &common_vars->rxdata[aa][rx_offset], + + dft(dftsize,(int16_t *) &common_vars->rxdata[aa][(rx_offset) % frame_length_samples], (int16_t *)&common_vars->common_vars_rx_data_per_thread[ue->current_thread_id[Ns]].rxdataF[aa][frame_parms->ofdm_symbol_size*symbol],1); #if UE_TIMING_TRACE stop_meas(&ue->rx_dft_stats); @@ -358,11 +359,10 @@ int nr_slot_fep_init_sync(PHY_VARS_NR_UE *ue, memcpy((void *)tmp_dft_in, (void *) &common_vars->rxdata[aa][rx_offset], frame_parms->ofdm_symbol_size*sizeof(int)); - dft((int16_t *)tmp_dft_in, + dft(dftsize,(int16_t *)tmp_dft_in, (int16_t *)&common_vars->common_vars_rx_data_per_thread[ue->current_thread_id[Ns]].rxdataF[aa][frame_parms->ofdm_symbol_size*symbol],1); } else { // use dft input from RX buffer directly - - dft((int16_t *) &common_vars->rxdata[aa][rx_offset], + dft(dftsize,(int16_t *) &common_vars->rxdata[aa][(rx_offset) % frame_length_samples], (int16_t *)&common_vars->common_vars_rx_data_per_thread[ue->current_thread_id[Ns]].rxdataF[aa][frame_parms->ofdm_symbol_size*symbol],1); } #if UE_TIMING_TRACE @@ -400,43 +400,43 @@ int nr_slot_fep_ul(NR_DL_FRAME_PARMS *frame_parms, unsigned int nb_prefix_samples = (no_prefix ? 0 : frame_parms->nb_prefix_samples); unsigned int nb_prefix_samples0 = (no_prefix ? 0 : frame_parms->nb_prefix_samples0); - void (*dft)(int16_t *,int16_t *, int); + dft_size_idx_t dftsize; switch (frame_parms->ofdm_symbol_size) { case 128: - dft = dft128; + dftsize = DFT_128; break; case 256: - dft = dft256; + dftsize = DFT_256; break; case 512: - dft = dft512; + dftsize = DFT_512; break; case 1024: - dft = dft1024; + dftsize = DFT_1024; break; case 1536: - dft = dft1536; + dftsize = DFT_1536; break; case 2048: - dft = dft2048; + dftsize = DFT_2048; break; case 4096: - dft = dft4096; + dftsize = DFT_4096; break; case 8192: - dft = dft8192; + dftsize = DFT_8192; break; default: - dft = dft512; + dftsize = DFT_512; break; } @@ -448,7 +448,7 @@ int nr_slot_fep_ul(NR_DL_FRAME_PARMS *frame_parms, else rxdata_offset = slot_offset + nb_prefix_samples0 + (symbol * (frame_parms->ofdm_symbol_size + nb_prefix_samples)) - SOFFSET; - dft((int16_t *)&rxdata[rxdata_offset], + dft(dftsize,(int16_t *)&rxdata[rxdata_offset], (int16_t *)&rxdataF[symbol * frame_parms->ofdm_symbol_size], 1); return(0); diff --git a/openair1/PHY/MODULATION/slot_fep_ul.c b/openair1/PHY/MODULATION/slot_fep_ul.c index 3ac8537c696ff2df692e98ad0967c1c296253ac8..746f8dbc0e1535dcca3bcdded7a83b6edee24a91 100644 --- a/openair1/PHY/MODULATION/slot_fep_ul.c +++ b/openair1/PHY/MODULATION/slot_fep_ul.c @@ -44,7 +44,7 @@ int slot_fep_ul(RU_t *ru, unsigned int slot_offset; - void (*dft)(int16_t *,int16_t *, int); + dft_size_idx_t dftsize; int tmp_dft_in[2048] __attribute__ ((aligned (32))); // This is for misalignment issues for 6 and 15 PRBs unsigned int frame_length_samples = fp->samples_per_tti * 10; @@ -52,31 +52,31 @@ int slot_fep_ul(RU_t *ru, switch (fp->ofdm_symbol_size) { case 128: - dft = dft128; + dftsize = DFT_128; break; case 256: - dft = dft256; + dftsize = DFT_256; break; case 512: - dft = dft512; + dftsize = DFT_512; break; case 1024: - dft = dft1024; + dftsize = DFT_1024; break; case 1536: - dft = dft1536; + dftsize = DFT_1536; break; case 2048: - dft = dft2048; + dftsize = DFT_2048; break; default: - dft = dft512; + dftsize = DFT_512; break; } @@ -109,7 +109,7 @@ int slot_fep_ul(RU_t *ru, LOG_D(PHY,"slot_fep: symbol 0 %d dB\n", dB_fixed(signal_energy(&common->rxdata_7_5kHz[aa][rx_offset],fp->ofdm_symbol_size))); #endif - dft( (int16_t *)&common->rxdata_7_5kHz[aa][rx_offset], + dft( dftsize,(int16_t *)&common->rxdata_7_5kHz[aa][rx_offset], (int16_t *)&common->rxdataF[aa][fp->ofdm_symbol_size*symbol], 1 ); @@ -121,13 +121,13 @@ int slot_fep_ul(RU_t *ru, memcpy((void *)&tmp_dft_in, (void *)&common->rxdata_7_5kHz[aa][(rx_offset % frame_length_samples)], fp->ofdm_symbol_size*sizeof(int)); - dft( (short *) tmp_dft_in, + dft( dftsize,(short *) tmp_dft_in, (short*) &common->rxdataF[aa][fp->ofdm_symbol_size*symbol], 1 ); } else{ - dft( (short *)&common->rxdata_7_5kHz[aa][rx_offset], + dft( dftsize,(short *)&common->rxdata_7_5kHz[aa][rx_offset], (short*)&common->rxdataF[aa][fp->ofdm_symbol_size*symbol], 1 ); diff --git a/openair1/PHY/NR_ESTIMATION/nr_ul_channel_estimation.c b/openair1/PHY/NR_ESTIMATION/nr_ul_channel_estimation.c index 0d7732599fc21fbe942734d36fdccebf400fb4ce..f94a82c111820ba61af2d9bf5eb9e3173dfd9c6e 100644 --- a/openair1/PHY/NR_ESTIMATION/nr_ul_channel_estimation.c +++ b/openair1/PHY/NR_ESTIMATION/nr_ul_channel_estimation.c @@ -430,55 +430,55 @@ int nr_pusch_channel_estimation(PHY_VARS_gNB *gNB, switch (gNB->frame_parms.ofdm_symbol_size) { case 128: - idft128((int16_t*) &ul_ch_estimates[aarx][symbol_offset], + idft(IDFT_128,(int16_t*) &ul_ch_estimates[aarx][symbol_offset], (int16_t*) ul_ch_estimates_time[aarx], 1); break; case 256: - idft256((int16_t*) &ul_ch_estimates[aarx][symbol_offset], + idft(IDFT_256,(int16_t*) &ul_ch_estimates[aarx][symbol_offset], (int16_t*) ul_ch_estimates_time[aarx], 1); break; case 512: - idft512((int16_t*) &ul_ch_estimates[aarx][symbol_offset], + idft(IDFT_512,(int16_t*) &ul_ch_estimates[aarx][symbol_offset], (int16_t*) ul_ch_estimates_time[aarx], 1); break; case 1024: - idft1024((int16_t*) &ul_ch_estimates[aarx][symbol_offset], + idft(IDFT_1024,(int16_t*) &ul_ch_estimates[aarx][symbol_offset], (int16_t*) ul_ch_estimates_time[aarx], 1); break; case 1536: - idft1536((int16_t*) &ul_ch_estimates[aarx][symbol_offset], + idft(IDFT_1536,(int16_t*) &ul_ch_estimates[aarx][symbol_offset], (int16_t*) ul_ch_estimates_time[aarx], 1); break; case 2048: - idft2048((int16_t*) &ul_ch_estimates[aarx][symbol_offset], + idft(IDFT_2048,(int16_t*) &ul_ch_estimates[aarx][symbol_offset], (int16_t*) ul_ch_estimates_time[aarx], 1); break; case 4096: - idft4096((int16_t*) &ul_ch_estimates[aarx][symbol_offset], + idft(IDFT_4096,(int16_t*) &ul_ch_estimates[aarx][symbol_offset], (int16_t*) ul_ch_estimates_time[aarx], 1); break; case 8192: - idft8192((int16_t*) &ul_ch_estimates[aarx][symbol_offset], + idft(IDFT_8192,(int16_t*) &ul_ch_estimates[aarx][symbol_offset], (int16_t*) ul_ch_estimates_time[aarx], 1); break; default: - idft512((int16_t*) &ul_ch_estimates[aarx][symbol_offset], + idft(IDFT_512,(int16_t*) &ul_ch_estimates[aarx][symbol_offset], (int16_t*) ul_ch_estimates_time[aarx], 1); break; diff --git a/openair1/PHY/NR_REFSIG/pss_nr.h b/openair1/PHY/NR_REFSIG/pss_nr.h index a2e66d4e110dce4263b22a42e9c4c513bc3a6a00..19b9736bcbeab0f10a5df838659df74ca911d939 100644 --- a/openair1/PHY/NR_REFSIG/pss_nr.h +++ b/openair1/PHY/NR_REFSIG/pss_nr.h @@ -127,8 +127,8 @@ time_stats_t generic_time[TIME_LAST]; /************** FUNCTION ******************************************/ -void *get_idft(int ofdm_symbol_size); -void *get_dft(int ofdm_symbol_size); +idft_size_idx_t get_idft(int ofdm_symbol_size); +dft_size_idx_t get_dft(int ofdm_symbol_size); void init_context_synchro_nr(NR_DL_FRAME_PARMS *frame_parms_ue); void free_context_synchro_nr(void); void init_context_pss_nr(NR_DL_FRAME_PARMS *frame_parms_ue); diff --git a/openair1/PHY/NR_TRANSPORT/nr_prach.c b/openair1/PHY/NR_TRANSPORT/nr_prach.c index 5710499e1aed5c7c61b640aa0ca93682728b38e8..7ab553fe6bcdff35a0cc326e2ee64de2f4951e7e 100644 --- a/openair1/PHY/NR_TRANSPORT/nr_prach.c +++ b/openair1/PHY/NR_TRANSPORT/nr_prach.c @@ -175,39 +175,39 @@ void rx_nr_prach_ru(RU_t *ru, //50 MHz @ 61.44 Ms/s prach2 = prach[aa] + (Ncp<<2); if (prach_fmt == 0 || prach_fmt == 1 || prach_fmt == 2) - dft49152(prach2,rxsigF[aa],1); + dft(DFT_49152,prach2,rxsigF[aa],1); if (prach_fmt == 1 || prach_fmt == 2) { - dft49152(prach2+98304,rxsigF[aa]+98304,1); + dft(DFT_49152,prach2+98304,rxsigF[aa]+98304,1); reps++; } if (prach_fmt == 2) { - dft49152(prach2+(98304*2),rxsigF[aa]+(98304*2),1); - dft49152(prach2+(98304*3),rxsigF[aa]+(98304*3),1); + dft(DFT_49152,prach2+(98304*2),rxsigF[aa]+(98304*2),1); + dft(DFT_49152,prach2+(98304*3),rxsigF[aa]+(98304*3),1); reps+=2; } if (prach_fmt == 3) { - for (int i=0;i<4;i++) dft12288(prach2+(i*12288*2),rxsigF[aa]+(i*12288*2),1); + for (int i=0;i<4;i++) dft(DFT_12288,prach2+(i*12288*2),rxsigF[aa]+(i*12288*2),1); reps=4; } if (prach_fmt >3) { - dft2048(prach2,rxsigF[aa],1); + dft(DFT_2048,prach2,rxsigF[aa],1); if (prach_fmt != 0xc0) { - dft2048(prach2+4096,rxsigF[aa]+4096,1); + dft(DFT_2048,prach2+4096,rxsigF[aa]+4096,1); reps++; } } if (prach_fmt == 0xa2 || prach_fmt == 0xa3 || prach_fmt == 0xb2 || prach_fmt == 0xb3 || prach_fmt == 0xb4 || prach_fmt == 0xc2) { - dft2048(prach2+4096*2,rxsigF[aa]+4096*2,1); - dft2048(prach2+4096*3,rxsigF[aa]+4096*3,1); + dft(DFT_2048,prach2+4096*2,rxsigF[aa]+4096*2,1); + dft(DFT_2048,prach2+4096*3,rxsigF[aa]+4096*3,1); reps+=2; } if (prach_fmt == 0xa3 || prach_fmt == 0xb3 || prach_fmt == 0xc2) { - dft2048(prach2+4096*4,rxsigF[aa]+4096*4,1); - dft2048(prach2+4096*5,rxsigF[aa]+4096*5,1); + dft(DFT_2048,prach2+4096*4,rxsigF[aa]+4096*4,1); + dft(DFT_2048,prach2+4096*5,rxsigF[aa]+4096*5,1); reps+=2; } if (prach_fmt == 0xc2) { - for (int i=6;i<11;i++) dft2048(prach2+(3072*i),rxsigF[aa]+(3072*i),1); + for (int i=6;i<11;i++) dft(DFT_2048,prach2+(3072*i),rxsigF[aa]+(3072*i),1); reps+=6; } } else { @@ -215,41 +215,41 @@ void rx_nr_prach_ru(RU_t *ru, prach2 = prach[aa] + (3*Ncp); AssertFatal(fp->N_RB_UL <= 107,"cannot do 108..136 PRBs with 3/4 sampling\n"); if (prach_fmt == 0 || prach_fmt == 1 || prach_fmt == 2) { - dft36864(prach2,rxsigF[aa],1); + dft(DFT_36864,prach2,rxsigF[aa],1); reps++; } if (prach_fmt == 1 || prach_fmt == 2) { - dft36864(prach2+73728,rxsigF[aa]+73728,1); + dft(DFT_36864,prach2+73728,rxsigF[aa]+73728,1); reps++; } if (prach_fmt == 2) { - dft36864(prach2+(98304*2),rxsigF[aa]+(98304*2),1); - dft36864(prach2+(98304*3),rxsigF[aa]+(98304*3),1); + dft(DFT_36864,prach2+(98304*2),rxsigF[aa]+(98304*2),1); + dft(DFT_36864,prach2+(98304*3),rxsigF[aa]+(98304*3),1); reps+=2; } if (prach_fmt == 3) { - for (int i=0;i<4;i++) dft9216(prach2+(i*9216*2),rxsigF[aa]+(i*9216*2),1); + for (int i=0;i<4;i++) dft(DFT_9216,prach2+(i*9216*2),rxsigF[aa]+(i*9216*2),1); reps=4; } if (prach_fmt >3) { - dft1536(prach2,rxsigF[aa],1); + dft(DFT_1536,prach2,rxsigF[aa],1); if (prach_fmt != 0xc0) { - dft1536(prach2+3072,rxsigF[aa]+3072,1); + dft(DFT_1536,prach2+3072,rxsigF[aa]+3072,1); reps++; } } if (prach_fmt == 0xa2 || prach_fmt == 0xa3 || prach_fmt == 0xb2 || prach_fmt == 0xb3 || prach_fmt == 0xb4 || prach_fmt == 0xc2) { - dft1536(prach2+3072*2,rxsigF[aa]+3072*2,1); - dft1536(prach2+3072*3,rxsigF[aa]+3072*3,1); + dft(DFT_1536,prach2+3072*2,rxsigF[aa]+3072*2,1); + dft(DFT_1536,prach2+3072*3,rxsigF[aa]+3072*3,1); reps+=2; } if (prach_fmt == 0xa3 || prach_fmt == 0xb3 || prach_fmt == 0xc2) { - dft1536(prach2+3072*4,rxsigF[aa]+3072*4,1); - dft1536(prach2+3072*5,rxsigF[aa]+3072*5,1); + dft(DFT_1536,prach2+3072*4,rxsigF[aa]+3072*4,1); + dft(DFT_1536,prach2+3072*5,rxsigF[aa]+3072*5,1); reps+=2; } if (prach_fmt == 0xc2) { - for (int i=6;i<11;i++) dft1536(prach2+(3072*i),rxsigF[aa]+(3072*i),1); + for (int i=6;i<11;i++) dft(DFT_1536,prach2+(3072*i),rxsigF[aa]+(3072*i),1); reps+=6; } } @@ -260,41 +260,41 @@ void rx_nr_prach_ru(RU_t *ru, dftlen=98304; //80,90,100 MHz @ 61.44 Ms/s if (prach_fmt == 0 || prach_fmt == 1 || prach_fmt == 2) - dft98304(prach2,rxsigF[aa],1); + dft(DFT_98304,prach2,rxsigF[aa],1); if (prach_fmt == 1 || prach_fmt == 2) { - dft98304(prach2+196608,rxsigF[aa]+196608,1); + dft(DFT_98304,prach2+196608,rxsigF[aa]+196608,1); reps++; } if (prach_fmt == 1 || prach_fmt == 2) { - dft98304(prach2+196608,rxsigF[aa]+196608,1); - dft98304(prach2+(196608*2),rxsigF[aa]+(196608*2),1); + dft(DFT_98304,prach2+196608,rxsigF[aa]+196608,1); + dft(DFT_98304,prach2+(196608*2),rxsigF[aa]+(196608*2),1); reps+=2; } if (prach_fmt == 3) { - dft24576(prach2+(2*49152),rxsigF[aa]+(2*49152),1); + dft(DFT_24576,prach2+(2*49152),rxsigF[aa]+(2*49152),1); reps=4; dftlen=24576; } if (prach_fmt >3) { dftlen=4096; - dft4096(prach2,rxsigF[aa],1); + dft(DFT_4096,prach2,rxsigF[aa],1); if (prach_fmt != 0xc0) { - dft4096(prach2+8192,rxsigF[aa]+8192,1); + dft(DFT_4096,prach2+8192,rxsigF[aa]+8192,1); reps++; } } if (prach_fmt == 0xa2 || prach_fmt == 0xa3 || prach_fmt == 0xb2 || prach_fmt == 0xb3 || prach_fmt == 0xb4 || prach_fmt == 0xc2) { - dft4096(prach2+8192*2,rxsigF[aa]+8192*2,1); - dft4096(prach2+8192*3,rxsigF[aa]+8192*3,1); + dft(DFT_4096,prach2+8192*2,rxsigF[aa]+8192*2,1); + dft(DFT_4096,prach2+8192*3,rxsigF[aa]+8192*3,1); reps+=2; } if (prach_fmt == 0xa3 || prach_fmt == 0xb3 || prach_fmt == 0xc2) { - dft4096(prach2+8192*4,rxsigF[aa]+8192*4,1); - dft4096(prach2+8192*5,rxsigF[aa]+8192*5,1); + dft(DFT_4096,prach2+8192*4,rxsigF[aa]+8192*4,1); + dft(DFT_4096,prach2+8192*5,rxsigF[aa]+8192*5,1); reps+=2; } if (prach_fmt == 0xc2) { - for (int i=6;i<11;i++) dft4096(prach2+(8192*i),rxsigF[aa]+(8192*i),1); + for (int i=6;i<11;i++) dft(DFT_4096,prach2+(8192*i),rxsigF[aa]+(8192*i),1); reps+=6; } } else { @@ -303,39 +303,39 @@ void rx_nr_prach_ru(RU_t *ru, // 80 MHz @ 46.08 Ms/s dftlen=73728; if (prach_fmt == 0 || prach_fmt == 1 || prach_fmt == 2) { - dft73728(prach2,rxsigF[aa],1); + dft(DFT_73728,prach2,rxsigF[aa],1); reps++; } if (prach_fmt == 1 || prach_fmt == 2) { - dft73728(prach2+(2*73728),rxsigF[aa]+(2*73728),1); + dft(DFT_73728,prach2+(2*73728),rxsigF[aa]+(2*73728),1); reps++; } if (prach_fmt == 3) { - dft73728(prach2+(4*73728),rxsigF[aa]+(4*73728),1); + dft(DFT_73728,prach2+(4*73728),rxsigF[aa]+(4*73728),1); reps=4; dftlen=18432; } if (prach_fmt >3) { dftlen=3072; - dft3072(prach2,rxsigF[aa],1); + dft(DFT_3072,prach2,rxsigF[aa],1); if (prach_fmt != 0xc0) { - dft3072(prach2+6144,rxsigF[aa]+6144,1); + dft(DFT_3072,prach2+6144,rxsigF[aa]+6144,1); reps++; } } if (prach_fmt == 0xa2 || prach_fmt == 0xa3 || prach_fmt == 0xb2 || prach_fmt == 0xb3 || prach_fmt == 0xb4 || prach_fmt == 0xc2) { - dft3072(prach2+6144*2,rxsigF[aa]+6144*2,1); - dft3072(prach2+6144*3,rxsigF[aa]+6144*3,1); + dft(DFT_3072,prach2+6144*2,rxsigF[aa]+6144*2,1); + dft(DFT_3072,prach2+6144*3,rxsigF[aa]+6144*3,1); reps+=2; } if (prach_fmt == 0xa3 || prach_fmt == 0xb3 || prach_fmt == 0xc2) { - dft3072(prach2+6144*4,rxsigF[aa]+6144*4,1); - dft3072(prach2+6144*5,rxsigF[aa]+6144*5,1); + dft(DFT_3072,prach2+6144*4,rxsigF[aa]+6144*4,1); + dft(DFT_3072,prach2+6144*5,rxsigF[aa]+6144*5,1); reps+=2; } if (prach_fmt == 0xc2) { - for (int i=6;i<11;i++) dft3072(prach2+(6144*i),rxsigF[aa]+(6144*i),1); + for (int i=6;i<11;i++) dft(DFT_3072,prach2+(6144*i),rxsigF[aa]+(6144*i),1); reps+=6; } } @@ -590,12 +590,12 @@ void rx_nr_prach(PHY_VARS_gNB *gNB, // Now do IFFT of size 1024 (N_ZC=839) or 256 (N_ZC=139) if (N_ZC == 839) { log2_ifft_size = 10; - idft1024(prachF,prach_ifft_tmp,1); + idft(IDFT_1024,prachF,prach_ifft_tmp,1); // compute energy and accumulate over receive antennas for (i=0;i<2048;i++) prach_ifft[i] += (prach_ifft_tmp[i<<1]*prach_ifft_tmp[i<<1] + prach_ifft_tmp[1+(i<<1)]*prach_ifft_tmp[1+(i<<1)])>>10; } else { - idft256(prachF,prach_ifft_tmp,1); + idft(IDFT_256,prachF,prach_ifft_tmp,1); log2_ifft_size = 8; // compute energy and accumulate over receive antennas and repetitions for BR for (i=0;i<256;i++) diff --git a/openair1/PHY/NR_TRANSPORT/nr_ulsch_decoding.c b/openair1/PHY/NR_TRANSPORT/nr_ulsch_decoding.c index e8a961360f45f237140d8efd64a5a28b542d7fad..050c2302128fd5965fd78df090e1daf4342fd356 100644 --- a/openair1/PHY/NR_TRANSPORT/nr_ulsch_decoding.c +++ b/openair1/PHY/NR_TRANSPORT/nr_ulsch_decoding.c @@ -458,9 +458,8 @@ uint32_t nr_ulsch_decoding(PHY_VARS_gNB *phy_vars_gNB, for (r=0; r<harq_process->C; r++) { E = nr_get_E(G, harq_process->C, Qm, n_layers, r); -#if gNB_TIMING_TRACE - start_meas(ulsch_deinterleaving_stats); -#endif + + start_meas(&phy_vars_gNB->ulsch_deinterleaving_stats); //////////////////////////////////////////////////////////////////////////////////////////// ///////////////////////////////// nr_deinterleaving_ldpc /////////////////////////////////// @@ -476,13 +475,8 @@ uint32_t nr_ulsch_decoding(PHY_VARS_gNB *phy_vars_gNB, //for (int i =0; i<16; i++) // printf("rx output deinterleaving w[%d]= %d r_offset %d\n", i,harq_process->w[r][i], r_offset); -#if gNB_TIMING_TRACE - stop_meas(ulsch_deinterleaving_stats); -#endif + stop_meas(&phy_vars_gNB->ulsch_deinterleaving_stats); -#if gNB_TIMING_TRACE - start_meas(ulsch_rate_unmatching_stats); -#endif #ifdef DEBUG_ULSCH_DECODING LOG_D(PHY,"HARQ_PID %d Rate Matching Segment %d (coded bits %d,unpunctured/repeated bits %d, TBS %d, mod_order %d, nb_rb %d, Nl %d, rv %d, round %d)...\n", @@ -504,6 +498,8 @@ uint32_t nr_ulsch_decoding(PHY_VARS_gNB *phy_vars_gNB, ///////////////////////// harq_process->e =====> harq_process->d ///////////////////////// + start_meas(&phy_vars_gNB->ulsch_rate_unmatching_stats); + Tbslbrm = nr_compute_tbslbrm(0,nb_rb,n_layers,harq_process->C); if (nr_rate_matching_ldpc_rx(Ilbrm, @@ -518,15 +514,13 @@ uint32_t nr_ulsch_decoding(PHY_VARS_gNB *phy_vars_gNB, E, harq_process->F, Kr-harq_process->F-2*(p_decParams->Z))==-1) { -#if gNB_TIMING_TRACE - stop_meas(ulsch_rate_unmatching_stats); -#endif + + stop_meas(&phy_vars_gNB->ulsch_rate_unmatching_stats); + LOG_E(PHY,"ulsch_decoding.c: Problem in rate_matching\n"); return (ulsch->max_ldpc_iterations + 1); } else { -#if gNB_TIMING_TRACE - stop_meas(ulsch_rate_unmatching_stats); -#endif + stop_meas(&phy_vars_gNB->ulsch_rate_unmatching_stats); } r_offset += E; @@ -564,9 +558,7 @@ uint32_t nr_ulsch_decoding(PHY_VARS_gNB *phy_vars_gNB, if (err_flag == 0) { -#if gNB_TIMING_TRACE - start_meas(ulsch_turbo_decoding_stats); -#endif + start_meas(&phy_vars_gNB->ulsch_ldpc_decoding_stats); //LOG_E(PHY,"AbsSubframe %d.%d Start LDPC segment %d/%d A %d ",frame%1024,nr_tti_rx,r,harq_process->C-1, A); @@ -636,9 +628,7 @@ uint32_t nr_ulsch_decoding(PHY_VARS_gNB *phy_vars_gNB, //write_output("dec_output.m","dec0",harq_process->c[0],Kr_bytes,1,4); #endif -#if gNB_TIMING_TRACE - stop_meas(ulsch_turbo_decoding_stats); -#endif + stop_meas(&phy_vars_gNB->ulsch_ldpc_decoding_stats); } if ((err_flag == 0) && (ret >= (ulsch->max_ldpc_iterations + 1))) { diff --git a/openair1/PHY/NR_TRANSPORT/nr_ulsch_demodulation.c b/openair1/PHY/NR_TRANSPORT/nr_ulsch_demodulation.c index bce8ddcc29190f362574f154098ed63c8436908d..d22a013c049cf346a7cb9f09c49aec6ccc102a38 100644 --- a/openair1/PHY/NR_TRANSPORT/nr_ulsch_demodulation.c +++ b/openair1/PHY/NR_TRANSPORT/nr_ulsch_demodulation.c @@ -44,7 +44,7 @@ void nr_idft(uint32_t *z, uint32_t Msc_PUSCH) switch (Msc_PUSCH) { case 12: - dft12((int16_t *)idft_in0, (int16_t *)idft_out0); + dft(DFT_12,(int16_t *)idft_in0, (int16_t *)idft_out0,0); #if defined(__x86_64__)||defined(__i386__) norm128 = _mm_set1_epi16(9459); @@ -63,135 +63,135 @@ void nr_idft(uint32_t *z, uint32_t Msc_PUSCH) break; case 24: - dft24(idft_in0, idft_out0, 1); + dft(DFT_24,idft_in0, idft_out0, 1); break; case 36: - dft36(idft_in0, idft_out0, 1); + dft(DFT_36,idft_in0, idft_out0, 1); break; case 48: - dft48(idft_in0, idft_out0, 1); + dft(DFT_48,idft_in0, idft_out0, 1); break; case 60: - dft60(idft_in0, idft_out0, 1); + dft(DFT_60,idft_in0, idft_out0, 1); break; case 72: - dft72(idft_in0, idft_out0, 1); + dft(DFT_72,idft_in0, idft_out0, 1); break; case 96: - dft96(idft_in0, idft_out0, 1); + dft(DFT_96,idft_in0, idft_out0, 1); break; case 108: - dft108(idft_in0, idft_out0, 1); + dft(DFT_108,idft_in0, idft_out0, 1); break; case 120: - dft120(idft_in0, idft_out0, 1); + dft(DFT_120,idft_in0, idft_out0, 1); break; case 144: - dft144(idft_in0, idft_out0, 1); + dft(DFT_144,idft_in0, idft_out0, 1); break; case 180: - dft180(idft_in0, idft_out0, 1); + dft(DFT_180,idft_in0, idft_out0, 1); break; case 192: - dft192(idft_in0, idft_out0, 1); + dft(DFT_192,idft_in0, idft_out0, 1); break; case 216: - dft216(idft_in0, idft_out0, 1); + dft(DFT_216,idft_in0, idft_out0, 1); break; case 240: - dft240(idft_in0, idft_out0, 1); + dft(DFT_240,idft_in0, idft_out0, 1); break; case 288: - dft288(idft_in0, idft_out0, 1); + dft(DFT_288,idft_in0, idft_out0, 1); break; case 300: - dft300(idft_in0, idft_out0, 1); + dft(DFT_300,idft_in0, idft_out0, 1); break; case 324: - dft324((int16_t*)idft_in0, (int16_t*)idft_out0, 1); + dft(DFT_324,(int16_t*)idft_in0, (int16_t*)idft_out0, 1); break; case 360: - dft360((int16_t*)idft_in0, (int16_t*)idft_out0, 1); + dft(DFT_360,(int16_t*)idft_in0, (int16_t*)idft_out0, 1); break; case 384: - dft384((int16_t*)idft_in0, (int16_t*)idft_out0, 1); + dft(DFT_384,(int16_t*)idft_in0, (int16_t*)idft_out0, 1); break; case 432: - dft432((int16_t*)idft_in0, (int16_t*)idft_out0, 1); + dft(DFT_432,(int16_t*)idft_in0, (int16_t*)idft_out0, 1); break; case 480: - dft480((int16_t*)idft_in0, (int16_t*)idft_out0, 1); + dft(DFT_480,(int16_t*)idft_in0, (int16_t*)idft_out0, 1); break; case 540: - dft540((int16_t*)idft_in0, (int16_t*)idft_out0, 1); + dft(DFT_540,(int16_t*)idft_in0, (int16_t*)idft_out0, 1); break; case 576: - dft576((int16_t*)idft_in0, (int16_t*)idft_out0, 1); + dft(DFT_576,(int16_t*)idft_in0, (int16_t*)idft_out0, 1); break; case 600: - dft600((int16_t*)idft_in0, (int16_t*)idft_out0, 1); + dft(DFT_600,(int16_t*)idft_in0, (int16_t*)idft_out0, 1); break; case 648: - dft648((int16_t*)idft_in0, (int16_t*)idft_out0, 1); + dft(DFT_648,(int16_t*)idft_in0, (int16_t*)idft_out0, 1); break; case 720: - dft720((int16_t*)idft_in0, (int16_t*)idft_out0, 1); + dft(DFT_720,(int16_t*)idft_in0, (int16_t*)idft_out0, 1); break; case 768: - dft768((int16_t*)idft_in0, (int16_t*)idft_out0, 1); + dft(DFT_768,(int16_t*)idft_in0, (int16_t*)idft_out0, 1); break; case 864: - dft864((int16_t*)idft_in0, (int16_t*)idft_out0, 1); + dft(DFT_864,(int16_t*)idft_in0, (int16_t*)idft_out0, 1); break; case 900: - dft900((int16_t*)idft_in0, (int16_t*)idft_out0, 1); + dft(DFT_900,(int16_t*)idft_in0, (int16_t*)idft_out0, 1); break; case 960: - dft960((int16_t*)idft_in0, (int16_t*)idft_out0, 1); + dft(DFT_960,(int16_t*)idft_in0, (int16_t*)idft_out0, 1); break; case 972: - dft972((int16_t*)idft_in0, (int16_t*)idft_out0, 1); + dft(DFT_972,(int16_t*)idft_in0, (int16_t*)idft_out0, 1); break; case 1080: - dft1080((int16_t*)idft_in0, (int16_t*)idft_out0, 1); + dft(DFT_1080,(int16_t*)idft_in0, (int16_t*)idft_out0, 1); break; case 1152: - dft1152((int16_t*)idft_in0, (int16_t*)idft_out0, 1); + dft(DFT_1152,(int16_t*)idft_in0, (int16_t*)idft_out0, 1); break; case 1200: - dft1200(idft_in0, idft_out0, 1); + dft(DFT_1200,idft_in0, idft_out0, 1); break; default: @@ -1093,7 +1093,7 @@ void nr_rx_pusch(PHY_VARS_gNB *gNB, //---------------------------------------------------------- //--------------------- Channel estimation --------------------- //---------------------------------------------------------- - + start_meas(&gNB->ulsch_channel_estimation_stats); if (dmrs_symbol_flag == 1) nr_pusch_channel_estimation(gNB, nr_tti_rx, @@ -1101,17 +1101,19 @@ void nr_rx_pusch(PHY_VARS_gNB *gNB, symbol, bwp_start_subcarrier, rel15_ul); - + stop_meas(&gNB->ulsch_channel_estimation_stats); //---------------------------------------------------------- //--------------------- RBs extraction --------------------- //---------------------------------------------------------- + start_meas(&gNB->ulsch_rbs_extraction_stats); nr_ulsch_extract_rbs_single(gNB->common_vars.rxdataF, gNB->pusch_vars[UE_id], symbol, dmrs_symbol_flag, rel15_ul, frame_parms); + stop_meas(&gNB->ulsch_rbs_extraction_stats); nr_ulsch_scale_channel(gNB->pusch_vars[UE_id]->ul_ch_estimates_ext, frame_parms, @@ -1140,6 +1142,7 @@ void nr_rx_pusch(PHY_VARS_gNB *gNB, } + start_meas(&gNB->ulsch_channel_compensation_stats); nr_ulsch_channel_compensation(gNB->pusch_vars[UE_id]->rxdataF_ext, gNB->pusch_vars[UE_id]->ul_ch_estimates_ext, gNB->pusch_vars[UE_id]->ul_ch_mag0, @@ -1152,6 +1155,7 @@ void nr_rx_pusch(PHY_VARS_gNB *gNB, rel15_ul->qam_mod_order, rel15_ul->rb_size, gNB->pusch_vars[UE_id]->log2_maxh); + stop_meas(&gNB->ulsch_channel_compensation_stats); #ifdef NR_SC_FDMA nr_idft(&((uint32_t*)gNB->pusch_vars[UE_id]->rxdataF_ext[0])[symbol * rel15_ul->rb_size * NR_NB_SC_PER_RB], nb_re_pusch); @@ -1160,7 +1164,7 @@ void nr_rx_pusch(PHY_VARS_gNB *gNB, //---------------------------------------------------------- //-------------------- LLRs computation -------------------- //---------------------------------------------------------- - + start_meas(&gNB->ulsch_llr_stats); nr_ulsch_compute_llr(&gNB->pusch_vars[UE_id]->rxdataF_comp[0][symbol * rel15_ul->rb_size * NR_NB_SC_PER_RB], gNB->pusch_vars[UE_id]->ul_ch_mag0, gNB->pusch_vars[UE_id]->ul_ch_magb0, @@ -1169,6 +1173,7 @@ void nr_rx_pusch(PHY_VARS_gNB *gNB, nb_re_pusch, symbol, rel15_ul->qam_mod_order); + stop_meas(&gNB->ulsch_llr_stats); gNB->pusch_vars[UE_id]->rxdataF_ext_offset = gNB->pusch_vars[UE_id]->rxdataF_ext_offset + nb_re_pusch - gNB->pusch_vars[UE_id]->ptrs_sc_per_ofdm_symbol; diff --git a/openair1/PHY/NR_UE_ESTIMATION/nr_adjust_synch_ue.c b/openair1/PHY/NR_UE_ESTIMATION/nr_adjust_synch_ue.c index cc22e5f7d789ceed43bf5cf5ccee99c416c59889..7f5872e8858fa69c873c220757415c4bb6597c01 100644 --- a/openair1/PHY/NR_UE_ESTIMATION/nr_adjust_synch_ue.c +++ b/openair1/PHY/NR_UE_ESTIMATION/nr_adjust_synch_ue.c @@ -23,7 +23,6 @@ #include "PHY/defs_nr_UE.h" #include "PHY/NR_UE_ESTIMATION/nr_estimation.h" #include "PHY/impl_defs_top.h" -//#include "openair2/LAYER2/MAC/mac_proto.h" #include "common/utils/LOG/vcd_signal_dumper.h" diff --git a/openair1/PHY/NR_UE_ESTIMATION/nr_dl_channel_estimation.c b/openair1/PHY/NR_UE_ESTIMATION/nr_dl_channel_estimation.c index be5c754bebfb0df750e3c7662deb7c5b09b5a5e3..19564bd8d08394d52cb417cb31ae3dee2fff2fde 100644 --- a/openair1/PHY/NR_UE_ESTIMATION/nr_dl_channel_estimation.c +++ b/openair1/PHY/NR_UE_ESTIMATION/nr_dl_channel_estimation.c @@ -405,39 +405,39 @@ int nr_pbch_channel_estimation(PHY_VARS_NR_UE *ue, } - void (*idft)(int16_t *,int16_t *, int); + idft_size_idx_t idftsizeidx; switch (ue->frame_parms.ofdm_symbol_size) { case 128: - idft = idft128; + idftsizeidx = IDFT_128; break; case 256: - idft = idft256; + idftsizeidx = IDFT_256; break; case 512: - idft = idft512; + idftsizeidx = IDFT_512; break; case 1024: - idft = idft1024; + idftsizeidx = IDFT_1024; break; case 1536: - idft = idft1536; + idftsizeidx = IDFT_1536; break; case 2048: - idft = idft2048; + idftsizeidx = IDFT_2048; break; case 3072: - idft = idft3072; + idftsizeidx = IDFT_3072; break; case 4096: - idft = idft4096; + idftsizeidx = IDFT_4096; break; default: @@ -453,7 +453,8 @@ int nr_pbch_channel_estimation(PHY_VARS_NR_UE *ue, if (ue->pbch_vars[eNB_offset]->dl_ch_estimates[(p<<1)+aarx]) { LOG_D(PHY,"Channel Impulse Computation Slot %d ThreadId %d Symbol %d ch_offset %d\n", Ns, ue->current_thread_id[Ns], symbol, ch_offset); - idft((int16_t*) &ue->pbch_vars[eNB_offset]->dl_ch_estimates[(p<<1)+aarx][ch_offset], + idft(idftsizeidx, + (int16_t*) &ue->pbch_vars[eNB_offset]->dl_ch_estimates[(p<<1)+aarx][ch_offset], (int16_t*) ue->pbch_vars[eNB_offset]->dl_ch_estimates_time[(p<<1)+aarx],1); } } diff --git a/openair1/PHY/NR_UE_TRANSPORT/nr_prach.c b/openair1/PHY/NR_UE_TRANSPORT/nr_prach.c index f7d5201a8231004025dbd3b0720ec898a77b03a9..adef4a759277c8371e089239310394e79ad8640d 100644 --- a/openair1/PHY/NR_UE_TRANSPORT/nr_prach.c +++ b/openair1/PHY/NR_UE_TRANSPORT/nr_prach.c @@ -398,7 +398,7 @@ int32_t generate_nr_prach( PHY_VARS_NR_UE *ue, uint8_t eNB_id, uint8_t subframe, // This is after cyclic prefix (Ncp<<1 samples for 30.72 Ms/s, Ncp<<2 samples for 61.44 Ms/s prach2 = prach+(Ncp<<1); if (prach_fmt == 0) { //24576 samples @ 30.72 Ms/s, 49152 samples @ 61.44 Ms/s - idft49152(prachF,prach2,1); + idft(IDFT_49152,prachF,prach2,1); // here we have |empty | Prach49152| memmove(prach,prach+(49152<<1),(Ncp<<3)); // here we have |Prefix | Prach49152| @@ -406,7 +406,7 @@ int32_t generate_nr_prach( PHY_VARS_NR_UE *ue, uint8_t eNB_id, uint8_t subframe, dftlen=49152; } else if (prach_fmt == 1) { //24576 samples @ 30.72 Ms/s, 49152 samples @ 61.44 Ms/s - idft49152(prachF,prach2,1); + idft(IDFT_49152,prachF,prach2,1); memmove(prach2+(49152<<1),prach2,(49152<<2)); // here we have |empty | Prach49152 | Prach49152| memmove(prach,prach+(49152<<2),(Ncp<<3)); @@ -415,7 +415,7 @@ int32_t generate_nr_prach( PHY_VARS_NR_UE *ue, uint8_t eNB_id, uint8_t subframe, dftlen=49152; } else if (prach_fmt == 2) { //24576 samples @ 30.72 Ms/s, 49152 samples @ 61.44 Ms/s - idft49152(prachF,prach2,1); + idft(IDFT_49152,prachF,prach2,1); memmove(prach2+(49152<<1),prach2,(49152<<2)); // here we have |empty | Prach49152 | Prach49152| empty49152 | empty49152 memmove(prach2+(49152<<2),prach2,(49152<<3)); @@ -426,7 +426,7 @@ int32_t generate_nr_prach( PHY_VARS_NR_UE *ue, uint8_t eNB_id, uint8_t subframe, dftlen=49152; } else if (prach_fmt == 3) { // //6144 samples @ 30.72 Ms/s, 12288 samples @ 61.44 Ms/s - idft12288(prachF,prach2,1); + idft(IDFT_12288,prachF,prach2,1); memmove(prach2+(12288<<1),prach2,(12288<<2)); // here we have |empty | Prach12288 | Prach12288| empty12288 | empty12288 memmove(prach2+(12288<<2),prach2,(12288<<3)); @@ -438,7 +438,7 @@ int32_t generate_nr_prach( PHY_VARS_NR_UE *ue, uint8_t eNB_id, uint8_t subframe, } else if (prach_fmt == 0xa1 || prach_fmt == 0xb1 || prach_fmt == 0xc0) { prach2 = prach+(Ncp<<1); - idft2048(prachF,prach2,1); + idft(IDFT_2048,prachF,prach2,1); dftlen=2048; // here we have |empty | Prach2048 | if (prach_fmt != 0xc0) { @@ -450,7 +450,7 @@ int32_t generate_nr_prach( PHY_VARS_NR_UE *ue, uint8_t eNB_id, uint8_t subframe, // here we have |Prefix | Prach2048 | Prach2048 (if ! 0xc0) | } else if (prach_fmt == 0xa2 || prach_fmt == 0xb2) { // 6x2048 - idft2048(prachF,prach2,1); + idft(IDFT_2048,prachF,prach2,1); dftlen=2048; // here we have |empty | Prach2048 | memmove(prach2+(2048<<1),prach2,(2048<<2)); @@ -463,7 +463,7 @@ int32_t generate_nr_prach( PHY_VARS_NR_UE *ue, uint8_t eNB_id, uint8_t subframe, } else if (prach_fmt == 0xa3 || prach_fmt == 0xb3) { // 6x2048 prach2 = prach+(Ncp<<1); - idft2048(prachF,prach2,1); + idft(IDFT_2048,prachF,prach2,1); dftlen=2048; // here we have |empty | Prach2048 | memmove(prach2+(2048<<1),prach2,(2048<<2)); @@ -477,7 +477,7 @@ int32_t generate_nr_prach( PHY_VARS_NR_UE *ue, uint8_t eNB_id, uint8_t subframe, prach_len = (2048*6)+Ncp; } else if (prach_fmt == 0xb4) { // 12x2048 - idft2048(prachF,prach2,1); + idft(IDFT_2048,prachF,prach2,1); dftlen=2048; // here we have |empty | Prach2048 | memmove(prach2+(2048<<1),prach2,(2048<<2)); @@ -498,7 +498,7 @@ int32_t generate_nr_prach( PHY_VARS_NR_UE *ue, uint8_t eNB_id, uint8_t subframe, Ncp = (Ncp*3)/2; prach2 = prach+(Ncp<<1); if (prach_fmt == 0) { - idft36864(prachF,prach2,1); + idft(IDFT_36864,prachF,prach2,1); dftlen=36864; // here we have |empty | Prach73728| memmove(prach,prach+(36864<<1),(Ncp<<2)); @@ -506,7 +506,7 @@ int32_t generate_nr_prach( PHY_VARS_NR_UE *ue, uint8_t eNB_id, uint8_t subframe, prach_len = (36864*1)+Ncp; } else if (prach_fmt == 1) { - idft36864(prachF,prach2,1); + idft(IDFT_36864,prachF,prach2,1); dftlen=36864; memmove(prach2+(36864<<1),prach2,(36864<<2)); // here we have |empty | Prach73728 | Prach73728| @@ -515,7 +515,7 @@ int32_t generate_nr_prach( PHY_VARS_NR_UE *ue, uint8_t eNB_id, uint8_t subframe, prach_len = (36864*2)+Ncp; } if (prach_fmt == 2) { - idft36864(prachF,prach2,1); + idft(IDFT_36864,prachF,prach2,1); dftlen=36864; memmove(prach2+(36864<<1),prach2,(36864<<2)); // here we have |empty | Prach73728 | Prach73728| empty73728 | empty73728 @@ -526,7 +526,7 @@ int32_t generate_nr_prach( PHY_VARS_NR_UE *ue, uint8_t eNB_id, uint8_t subframe, prach_len = (36864*4)+Ncp; } else if (prach_fmt == 3) { - idft9216(prachF,prach2,1); + idft(IDFT_9216,prachF,prach2,1); dftlen=36864; memmove(prach2+(9216<<1),prach2,(9216<<2)); // here we have |empty | Prach9216 | Prach9216| empty9216 | empty9216 @@ -537,7 +537,7 @@ int32_t generate_nr_prach( PHY_VARS_NR_UE *ue, uint8_t eNB_id, uint8_t subframe, prach_len = (9216*4)+Ncp; } else if (prach_fmt == 0xa1 || prach_fmt == 0xb1 || prach_fmt == 0xc0) { - idft1536(prachF,prach2,1); + idft(IDFT_1536,prachF,prach2,1); dftlen=1536; // here we have |empty | Prach1536 | if (prach_fmt != 0xc0) @@ -547,7 +547,7 @@ int32_t generate_nr_prach( PHY_VARS_NR_UE *ue, uint8_t eNB_id, uint8_t subframe, prach_len = (1536*2)+Ncp; } else if (prach_fmt == 0xa2 || prach_fmt == 0xb2) { // 6x1536 - idft1536(prachF,prach2,1); + idft(IDFT_1536,prachF,prach2,1); dftlen=1536; // here we have |empty | Prach1536 | memmove(prach2+(1536<<1),prach2,(1536<<2)); @@ -559,7 +559,7 @@ int32_t generate_nr_prach( PHY_VARS_NR_UE *ue, uint8_t eNB_id, uint8_t subframe, prach_len = (1536*4)+Ncp; } else if (prach_fmt == 0xa3 || prach_fmt == 0xb3) { // 6x1536 - idft1536(prachF,prach2,1); + idft(IDFT_1536,prachF,prach2,1); dftlen=1536; // here we have |empty | Prach1536 | memmove(prach2+(1536<<1),prach2,(1536<<2)); @@ -573,7 +573,7 @@ int32_t generate_nr_prach( PHY_VARS_NR_UE *ue, uint8_t eNB_id, uint8_t subframe, prach_len = (1536*6)+Ncp; } else if (prach_fmt == 0xb4) { // 12x1536 - idft1536(prachF,prach2,1); + idft(IDFT_1536,prachF,prach2,1); dftlen=1536; // here we have |empty | Prach1536 | memmove(prach2+(1536<<1),prach2,(1536<<2)); @@ -595,7 +595,7 @@ int32_t generate_nr_prach( PHY_VARS_NR_UE *ue, uint8_t eNB_id, uint8_t subframe, Ncp<<=2; prach2 = prach+(Ncp<<1); if (prach_fmt == 0) { //24576 samples @ 30.72 Ms/s, 98304 samples @ 122.88 Ms/s - idft98304(prachF,prach2,1); + idft(IDFT_98304,prachF,prach2,1); dftlen=98304; // here we have |empty | Prach98304| memmove(prach,prach+(98304<<1),(Ncp<<2)); @@ -603,7 +603,7 @@ int32_t generate_nr_prach( PHY_VARS_NR_UE *ue, uint8_t eNB_id, uint8_t subframe, prach_len = (98304*1)+Ncp; } else if (prach_fmt == 1) { - idft98304(prachF,prach2,1); + idft(IDFT_98304,prachF,prach2,1); dftlen=98304; memmove(prach2+(98304<<1),prach2,(98304<<2)); // here we have |empty | Prach98304 | Prach98304| @@ -612,7 +612,7 @@ int32_t generate_nr_prach( PHY_VARS_NR_UE *ue, uint8_t eNB_id, uint8_t subframe, prach_len = (98304*2)+Ncp; } else if (prach_fmt == 2) { - idft98304(prachF,prach2,1); + idft(IDFT_98304,prachF,prach2,1); dftlen=98304; memmove(prach2+(98304<<1),prach2,(98304<<2)); // here we have |empty | Prach98304 | Prach98304| empty98304 | empty98304 @@ -623,7 +623,7 @@ int32_t generate_nr_prach( PHY_VARS_NR_UE *ue, uint8_t eNB_id, uint8_t subframe, prach_len = (98304*4)+Ncp; } else if (prach_fmt == 3) { // 4x6144, Ncp 3168 - idft24576(prachF,prach2,1); + idft(IDFT_24576,prachF,prach2,1); dftlen=24576; memmove(prach2+(24576<<1),prach2,(24576<<2)); // here we have |empty | Prach24576 | Prach24576| empty24576 | empty24576 @@ -634,7 +634,7 @@ int32_t generate_nr_prach( PHY_VARS_NR_UE *ue, uint8_t eNB_id, uint8_t subframe, prach_len = (24576*4)+(Ncp<<1); } else if (prach_fmt == 0xa1 || prach_fmt == 0xb1 || prach_fmt == 0xc0) { - idft4096(prachF,prach2,1); + idft(IDFT_4096,prachF,prach2,1); dftlen=4096; // here we have |empty | Prach4096 | if (prach_fmt != 0xc0) { @@ -647,7 +647,7 @@ int32_t generate_nr_prach( PHY_VARS_NR_UE *ue, uint8_t eNB_id, uint8_t subframe, } else if (prach_fmt == 0xa2 || prach_fmt == 0xb2) { // 4x4096 - idft4096(prachF,prach2,1); + idft(IDFT_4096,prachF,prach2,1); dftlen=4096; // here we have |empty | Prach4096 | memmove(prach2+(4096<<1),prach2,(4096<<2)); @@ -659,7 +659,7 @@ int32_t generate_nr_prach( PHY_VARS_NR_UE *ue, uint8_t eNB_id, uint8_t subframe, prach_len = (4096*4)+Ncp; } else if (prach_fmt == 0xa3 || prach_fmt == 0xb3) { // 6x4096 - idft4096(prachF,prach2,1); + idft(IDFT_4096,prachF,prach2,1); dftlen=4096; // here we have |empty | Prach4096 | memmove(prach2+(4096<<1),prach2,(4096<<2)); @@ -673,7 +673,7 @@ int32_t generate_nr_prach( PHY_VARS_NR_UE *ue, uint8_t eNB_id, uint8_t subframe, prach_len = (4096*6)+Ncp; } else if (prach_fmt == 0xb4) { // 12x4096 - idft4096(prachF,prach2,1); + idft(IDFT_4096,prachF,prach2,1); dftlen=4096; // here we have |empty | Prach4096 | memmove(prach2+(4096<<1),prach2,(4096<<2)); @@ -693,7 +693,7 @@ int32_t generate_nr_prach( PHY_VARS_NR_UE *ue, uint8_t eNB_id, uint8_t subframe, Ncp = (Ncp*3); prach2 = prach+(Ncp<<1); if (prach_fmt == 0) { - idft73728(prachF,prach2,1); + idft(IDFT_73728,prachF,prach2,1); dftlen=73728; // here we have |empty | Prach73728| memmove(prach,prach+(73728<<1),(Ncp<<4)); @@ -701,7 +701,7 @@ int32_t generate_nr_prach( PHY_VARS_NR_UE *ue, uint8_t eNB_id, uint8_t subframe, prach_len = (73728*1)+Ncp; } else if (prach_fmt == 1) { - idft73728(prachF,prach2,1); + idft(IDFT_73728,prachF,prach2,1); dftlen=73728; memmove(prach2+(73728<<1),prach2,(73728<<2)); // here we have |empty | Prach73728 | Prach73728| @@ -710,7 +710,7 @@ int32_t generate_nr_prach( PHY_VARS_NR_UE *ue, uint8_t eNB_id, uint8_t subframe, prach_len = (73728*2)+Ncp; } if (prach_fmt == 2) { - idft73728(prachF,prach2,1); + idft(IDFT_73728,prachF,prach2,1); dftlen=73728; memmove(prach2+(73728<<1),prach2,(73728<<2)); // here we have |empty | Prach73728 | Prach73728| empty73728 | empty73728 @@ -721,7 +721,7 @@ int32_t generate_nr_prach( PHY_VARS_NR_UE *ue, uint8_t eNB_id, uint8_t subframe, prach_len = (73728*4)+Ncp; } else if (prach_fmt == 3) { - idft18432(prachF,prach2,1); + idft(IDFT_18432,prachF,prach2,1); dftlen=18432; memmove(prach2+(18432<<1),prach2,(18432<<2)); // here we have |empty | Prach18432 | Prach18432| empty18432 | empty18432 @@ -732,7 +732,7 @@ int32_t generate_nr_prach( PHY_VARS_NR_UE *ue, uint8_t eNB_id, uint8_t subframe, prach_len = (18432*4)+Ncp; } else if (prach_fmt == 0xa1 || prach_fmt == 0xb1 || prach_fmt == 0xc0) { - idft3072(prachF,prach2,1); + idft(IDFT_3072,prachF,prach2,1); dftlen=3072; // here we have |empty | Prach3072 | if (prach_fmt != 0xc0) { @@ -744,7 +744,7 @@ int32_t generate_nr_prach( PHY_VARS_NR_UE *ue, uint8_t eNB_id, uint8_t subframe, // here we have |Prefix | Prach3072 | Prach3072 (if ! 0xc0) | } else if (prach_fmt == 0xa3 || prach_fmt == 0xb3) { // 6x3072 - idft3072(prachF,prach2,1); + idft(IDFT_3072,prachF,prach2,1); dftlen=3072; // here we have |empty | Prach3072 | memmove(prach2+(3072<<1),prach2,(3072<<2)); @@ -758,7 +758,7 @@ int32_t generate_nr_prach( PHY_VARS_NR_UE *ue, uint8_t eNB_id, uint8_t subframe, prach_len = (3072*6)+Ncp; } else if (prach_fmt == 0xa2 || prach_fmt == 0xb2) { // 4x3072 - idft3072(prachF,prach2,1); + idft(IDFT_3072,prachF,prach2,1); dftlen=3072; // here we have |empty | Prach3072 | memmove(prach2+(3072<<1),prach2,(3072<<2)); @@ -770,7 +770,7 @@ int32_t generate_nr_prach( PHY_VARS_NR_UE *ue, uint8_t eNB_id, uint8_t subframe, prach_len = (3072*4)+Ncp; } else if (prach_fmt == 0xb4) { // 12x3072 - idft3072(prachF,prach2,1); + idft(IDFT_3072,prachF,prach2,1); dftlen=3072; // here we have |empty | Prach3072 | memmove(prach2+(3072<<1),prach2,(3072<<2)); diff --git a/openair1/PHY/NR_UE_TRANSPORT/nr_ulsch_coding.c b/openair1/PHY/NR_UE_TRANSPORT/nr_ulsch_coding.c index 55bac9052082e0f29c412af194a98498f572cb1c..00627ac3ae33559b40acf8736de42104a4b9f2f5 100644 --- a/openair1/PHY/NR_UE_TRANSPORT/nr_ulsch_coding.c +++ b/openair1/PHY/NR_UE_TRANSPORT/nr_ulsch_coding.c @@ -356,11 +356,6 @@ int nr_ulsch_encoding(NR_UE_ULSCH_t *ulsch, Kr_bytes = Kr>>3; #endif -/////////// -///////////////////////////////////////////////////////////////////////////////////// - -opp_enabled=0; - ///////////////////////// c---->| LDCP coding |---->d ///////////////////////// /////////// @@ -386,6 +381,12 @@ opp_enabled=0; //for (int i=0;i<68*384;i++) // printf("channel_input[%d]=%d\n",i,channel_input[i]); + int temp_opp = 0; + + if (opp_enabled) { + opp_enabled = 0; + temp_opp = 1; + } /*printf("output %d %d %d %d %d \n", harq_process->d[0][0], harq_process->d[0][1], harq_process->d[r][2],harq_process->d[0][3], harq_process->d[0][4]); @@ -402,10 +403,12 @@ opp_enabled=0; //stop_meas(te_stats); //printf("end ldpc encoder -- output\n"); #ifdef DEBUG_DLSCH_CODING - write_output("ulsch_enc_input0.m","enc_in0",&harq_process->c[0][0],Kr_bytes,1,4); - write_output("ulsch_enc_output0.m","enc0",&harq_process->d[0][0],(3*8*Kr_bytes)+12,1,4); + write_output("ulsch_enc_input0.m","enc_in0",&harq_process->c[0][0],Kr_bytes,1,4); + write_output("ulsch_enc_output0.m","enc0",&harq_process->d[0][0],(3*8*Kr_bytes)+12,1,4); #endif + if (temp_opp) opp_enabled = 1; + /////////// /////////////////////////////////////////////////////////////////////////////// diff --git a/openair1/PHY/NR_UE_TRANSPORT/pss_nr.c b/openair1/PHY/NR_UE_TRANSPORT/pss_nr.c index e8eceb77a6d881c9a80d85e3154b0a6abce3353e..baf34ade92a2a67fe51aae93498af971993c674f 100644 --- a/openair1/PHY/NR_UE_TRANSPORT/pss_nr.c +++ b/openair1/PHY/NR_UE_TRANSPORT/pss_nr.c @@ -52,7 +52,7 @@ * * PARAMETERS : size of ofdm symbol * -* RETURN : function idft +* RETURN : index pointing to the dft func in the dft library * * DESCRIPTION : get idft function depending of ofdm size * @@ -60,45 +60,45 @@ //#define DBG_PSS_NR -void *get_idft(int ofdm_symbol_size) +idft_size_idx_t get_idft(int ofdm_symbol_size) { - void (*idft)(int16_t *,int16_t *, int); - + + switch (ofdm_symbol_size) { case 128: - idft = idft128; + return IDFT_128; break; case 256: - idft = idft256; + return IDFT_256; break; case 512: - idft = idft512; + return IDFT_512; break; case 1024: - idft = idft1024; + return IDFT_1024; break; case 1536: - idft = idft1536; + return IDFT_1536; break; case 2048: - idft = idft2048; + return IDFT_2048; break; case 3072: - idft = idft3072; + return IDFT_3072; break; case 4096: - idft = idft4096; + return IDFT_4096; break; case 8192: - idft = idft8192; + return IDFT_8192; break; default: @@ -106,7 +106,7 @@ void *get_idft(int ofdm_symbol_size) assert(0); break; } - return idft; + return IDFT_SIZE_IDXTABLESIZE; // never reached and will trigger assertion in idft function } /******************************************************************* @@ -121,41 +121,41 @@ void *get_idft(int ofdm_symbol_size) * *********************************************************************/ -void *get_dft(int ofdm_symbol_size) +dft_size_idx_t get_dft(int ofdm_symbol_size) { - void (*dft)(int16_t *,int16_t *, int); + switch (ofdm_symbol_size) { case 128: - dft = dft128; + return DFT_128; break; case 256: - dft = dft256; + return DFT_256; break; case 512: - dft = dft512; + return DFT_512; break; case 1024: - dft = dft1024; + return DFT_1024; break; case 1536: - dft = dft1536; + return DFT_1536; break; case 2048: - dft = dft2048; + return DFT_2048; break; case 4096: - dft = dft4096; + return DFT_4096; break; case 8192: - dft = dft8192; + return DFT_8192; break; default: @@ -163,7 +163,7 @@ void *get_dft(int ofdm_symbol_size) assert(0); break; } - return dft; + return DFT_SIZE_IDXTABLESIZE; // never reached and will trigger assertion in idft function; } /******************************************************************* @@ -191,7 +191,7 @@ void generate_pss_nr(NR_DL_FRAME_PARMS *fp,int N_ID_2) unsigned int size = length * IQ_SIZE; /* i & q */ int16_t *primary_synchro = primary_synchro_nr[N_ID_2]; /* pss in complex with alternatively i then q */ int16_t *primary_synchro2 = primary_synchro_nr2[N_ID_2]; /* pss in complex with alternatively i then q */ - void (*idft)(int16_t *,int16_t *, int); + #define INITIAL_PSS_NR (7) const int x_initial[INITIAL_PSS_NR] = {0, 1, 1 , 0, 1, 1, 1}; @@ -282,9 +282,10 @@ void generate_pss_nr(NR_DL_FRAME_PARMS *fp,int N_ID_2) /* IFFT will give temporal signal of Pss */ - idft = get_idft(length); - - idft(synchroF_tmp, /* complex input */ + + + idft((int16_t)get_idft(length), + synchroF_tmp, /* complex input */ synchro_tmp, /* complex output */ 1); /* scaling factor */ @@ -312,6 +313,7 @@ void generate_pss_nr(NR_DL_FRAME_PARMS *fp,int N_ID_2) #endif + #if 0 /* it allows checking that process of idft on a signal and then dft gives same signal with limited errors */ @@ -323,10 +325,11 @@ void generate_pss_nr(NR_DL_FRAME_PARMS *fp,int N_ID_2) bzero(synchroF_tmp, size); - void (*dft)(int16_t *,int16_t *, int) = get_dft(length); + /* get pss in the time domain by applying an inverse FFT */ - dft(synchro_tmp, /* complex input */ + dft((int16_t)get_dft(length), + synchro_tmp, /* complex input */ synchroF_tmp, /* complex output */ 1); /* scaling factor */ diff --git a/openair1/PHY/NR_UE_TRANSPORT/sss_nr.c b/openair1/PHY/NR_UE_TRANSPORT/sss_nr.c index 44d500b0b7ebfeacdf9f68704bca8f875541b3e7..e3f1f13a8d18f83d90286761ac65edff673ebbf9 100644 --- a/openair1/PHY/NR_UE_TRANSPORT/sss_nr.c +++ b/openair1/PHY/NR_UE_TRANSPORT/sss_nr.c @@ -182,7 +182,7 @@ void insert_sss_nr(int16_t *sss_time, } /* get sss in the frequency domain by applying an inverse FFT */ - idft2048(synchroF_tmp, /* complex input */ + idft(IDFT_2048,synchroF_tmp, /* complex input */ synchro_tmp, /* complex output */ 1); /* scaling factor */ diff --git a/openair1/PHY/TOOLS/dfts_load.c b/openair1/PHY/TOOLS/dfts_load.c new file mode 100644 index 0000000000000000000000000000000000000000..d758f46a4330977dd7cd3a667ede8f8998ef6614 --- /dev/null +++ b/openair1/PHY/TOOLS/dfts_load.c @@ -0,0 +1,65 @@ +/* + * 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 + */ + +/*! \file openair1/PHY/CODING/coding_nr_load.c + * \brief: load library implementing coding/decoding algorithms + * \author Francois TABURET + * \date 2020 + * \version 0.1 + * \company NOKIA BellLabs France + * \email: francois.taburet@nokia-bell-labs.com + * \note + * \warning + */ +#define _GNU_SOURCE +#include <sys/types.h> +#include <stdlib.h> +#include <malloc.h> +#include "assertions.h" +#include "common/utils/LOG/log.h" +#define OAIDFTS_LOADER +#include "tools_defs.h" +#include "common/config/config_userapi.h" +#include "common/utils/load_module_shlib.h" + + +/* function description array, to be used when loading the dfts/idfts lib */ +static loader_shlibfunc_t shlib_fdesc[2]; +static char *arg[64]={"phytest","-O","cmdlineonly::dbgl0"}; + + +int load_dftslib(void) { + + char *ptr = (char*)config_get_if(); + if ( ptr==NULL ) {// phy simulators, config module possibly not loaded + load_configmodule(3,(char **)arg,CONFIG_ENABLECMDLINEONLY) ; + logInit(); + } + shlib_fdesc[0].fname = "dft"; + shlib_fdesc[1].fname = "idft"; + int ret=load_module_shlib("dfts",shlib_fdesc,sizeof(shlib_fdesc)/sizeof(loader_shlibfunc_t),NULL); + AssertFatal( (ret >= 0),"Error loading dftsc decoder"); + dft = (dftfunc_t)shlib_fdesc[0].fptr; + idft = (idftfunc_t)shlib_fdesc[1].fptr; +return 0; +} + + diff --git a/openair1/PHY/TOOLS/nr_phy_scope.c b/openair1/PHY/TOOLS/nr_phy_scope.c index 40803c30f4fc7486989f05aaf08b62ea13cb64e4..4682a890299786dd491c30e3e9500a9749468b45 100644 --- a/openair1/PHY/TOOLS/nr_phy_scope.c +++ b/openair1/PHY/TOOLS/nr_phy_scope.c @@ -182,7 +182,7 @@ void phy_scope_gNB(FD_phy_scope_gnb *form, int Qm = 2; /* - if (!RC.nrmac[0]->UE_list.active[UE_id]) + if (!RC.nrmac[0]->UE_info.active[UE_id]) return; // choose max MCS to compute coded_bits_per_codeword diff --git a/openair1/PHY/TOOLS/lte_dfts.c b/openair1/PHY/TOOLS/oai_dfts.c similarity index 98% rename from openair1/PHY/TOOLS/lte_dfts.c rename to openair1/PHY/TOOLS/oai_dfts.c index 2de8653ab3900652e4e0ca8d95f0919c989709bd..d0b39184bb63aed51bb91623bd4fcd233e91ecf5 100644 --- a/openair1/PHY/TOOLS/lte_dfts.c +++ b/openair1/PHY/TOOLS/oai_dfts.c @@ -31,11 +31,10 @@ #ifndef M_PI #define M_PI 3.14159265358979323846 #endif - +#define OAIDFTS_MAIN #ifndef MR_MAIN #include "PHY/defs_common.h" #include "PHY/impl_defs_top.h" -#include "tools_defs.h" #else #include "time_meas.h" #include "LOG/log.h" @@ -64,6 +63,9 @@ const static int16_t reflip[32] __attribute__((aligned(32))) = {1,-1,1,-1,1,-1, + + + #if defined(__x86_64__) || defined(__i386__) static inline void cmac(__m128i a,__m128i b, __m128i *re32, __m128i *im32) __attribute__((always_inline)); static inline void cmac(__m128i a,__m128i b, __m128i *re32, __m128i *im32) @@ -2588,7 +2590,7 @@ const static int16_t tw64c[96] __attribute__((aligned(32))) = { #endif #ifndef __AVX2__ -void dft64(int16_t *x,int16_t *y,int scale) +void dft64(int16_t *x,int16_t *y,unsigned char scale) { simd_q15_t xtmp[16],ytmp[16],*tw64a_128=(simd_q15_t *)tw64a,*tw64b_128=(simd_q15_t *)tw64b,*x128=(simd_q15_t *)x,*y128=(simd_q15_t *)y; @@ -2702,7 +2704,7 @@ void dft64(int16_t *x,int16_t *y,int scale) } #else // __AVX2__ -void dft64(int16_t *x,int16_t *y,int scale) +void dft64(int16_t *x,int16_t *y,unsigned char scale) { simd256_q15_t xtmp[16],ytmp[16],*tw64a_256=(simd256_q15_t *)tw64a,*tw64b_256=(simd256_q15_t *)tw64b,*x256=(simd256_q15_t *)x,*y256=(simd256_q15_t *)y; @@ -2850,7 +2852,7 @@ void dft64(int16_t *x,int16_t *y,int scale) #endif #ifndef __AVX2__ -void idft64(int16_t *x,int16_t *y,int scale) +void idft64(int16_t *x,int16_t *y,unsigned char scale) { simd_q15_t xtmp[16],ytmp[16],*tw64a_128=(simd_q15_t *)tw64,*tw64b_128=(simd_q15_t *)tw64c,*x128=(simd_q15_t *)x,*y128=(simd_q15_t *)y; @@ -2942,7 +2944,7 @@ void idft64(int16_t *x,int16_t *y,int scale) } #else // __AVX2__ -void idft64(int16_t *x,int16_t *y,int scale) +void idft64(int16_t *x,int16_t *y,unsigned char scale) { simd256_q15_t xtmp[16],ytmp[16],*tw64a_256=(simd256_q15_t *)tw64,*tw64b_256=(simd256_q15_t *)tw64c,*x256=(simd256_q15_t *)x,*y256=(simd256_q15_t *)y; @@ -3052,7 +3054,7 @@ int16_t tw128b[128] __attribute__((aligned(32))) = {0,32767,-1608,32727,-3212,32 int16_t tw128c[128] __attribute__((aligned(32))) = {0,32767,1608,32727,3212,32609,4808,32412,6393,32137,7962,31785,9512,31356,11039,30851,12540,30272,14010,29621,15447,28897,16846,28105,18205,27244,19520,26318,20788,25329,22005,24278,23170,23169,24279,22004,25330,20787,26319,19519,27245,18204,28106,16845,28898,15446,29622,14009,30273,12539,30852,11038,31357,9511,31786,7961,32138,6392,32413,4807,32610,3211,32728,1607,32767,0,32728,-1608,32610,-3212,32413,-4808,32138,-6393,31786,-7962,31357,-9512,30852,-11039,30273,-12540,29622,-14010,28898,-15447,28106,-16846,27245,-18205,26319,-19520,25330,-20788,24279,-22005,23170,-23170,22005,-24279,20788,-25330,19520,-26319,18205,-27245,16846,-28106,15447,-28898,14010,-29622,12540,-30273,11039,-30852,9512,-31357,7962,-31786,6393,-32138,4808,-32413,3212,-32610,1608,-32728}; #ifndef __AVX2__ -void dft128(int16_t *x,int16_t *y,int scale) +void dft128(int16_t *x,int16_t *y,unsigned char scale) { simdshort_q15_t xtmp[64],*x64 = (simdshort_q15_t *)x; @@ -3159,7 +3161,7 @@ void dft128(int16_t *x,int16_t *y,int scale) } #else // __AVX2__ -void dft128(int16_t *x,int16_t *y,int scale) +void dft128(int16_t *x,int16_t *y,unsigned char scale) { simd256_q15_t xtmp[16],*x256 = (simd256_q15_t *)x; @@ -3229,7 +3231,7 @@ void dft128(int16_t *x,int16_t *y,int scale) #endif #ifndef __AVX2__ -void idft128(int16_t *x,int16_t *y,int scale) +void idft128(int16_t *x,int16_t *y,unsigned char scale) { simdshort_q15_t xtmp[64],*x64 = (simdshort_q15_t *)x; @@ -3328,7 +3330,7 @@ void idft128(int16_t *x,int16_t *y,int scale) } #else // __AVX2__ -void idft128(int16_t *x,int16_t *y,int scale) +void idft128(int16_t *x,int16_t *y,unsigned char scale) { simd256_q15_t xtmp[16],*x256 = (simd256_q15_t *)x; @@ -3401,7 +3403,7 @@ int16_t tw256b[384] __attribute__((aligned(32))) = {0,32767,-805,32757,-1608,327 0,32767,-2411,32678,-4808,32412,-7180,31970,-9512,31356,-11793,30571,-14010,29621,-16151,28510,-18205,27244,-20160,25831,-22005,24278,-23732,22594,-25330,20787,-26790,18867,-28106,16845,-29269,14732,-30273,12539,-31114,10278,-31786,7961,-32285,5601,-32610,3211,-32758,804,-32728,-1608,-32521,-4012,-32138,-6393,-31581,-8740,-30852,-11039,-29956,-13279,-28898,-15447,-27684,-17531,-26319,-19520,-24812,-21403,-23170,-23170,-21403,-24812,-19520,-26319,-17531,-27684,-15447,-28898,-13279,-29956,-11039,-30852,-8740,-31581,-6393,-32138,-4012,-32521,-1608,-32728,804,-32758,3211,-32610,5601,-32285,7961,-31786,10278,-31114,12539,-30273,14732,-29269,16845,-28106,18867,-26790,20787,-25330,22594,-23732,24278,-22005,25831,-20160,27244,-18205,28510,-16151,29621,-14010,30571,-11793,31356,-9512,31970,-7180,32412,-4808,32678,-2411 }; #ifndef __AVX2__ -void dft256(int16_t *x,int16_t *y,int scale) +void dft256(int16_t *x,int16_t *y,unsigned char scale) { simd_q15_t xtmp[64],ytmp[64],*tw256a_128p=(simd_q15_t *)tw256a,*tw256b_128p=(simd_q15_t *)tw256b,*x128=(simd_q15_t *)x,*y128=(simd_q15_t *)y,*y128p=(simd_q15_t *)y; @@ -3513,7 +3515,7 @@ void dft256(int16_t *x,int16_t *y,int scale) -void idft256(int16_t *x,int16_t *y,int scale) +void idft256(int16_t *x,int16_t *y,unsigned char scale) { simd_q15_t xtmp[64],ytmp[64],*tw256_128p=(simd_q15_t *)tw256,*x128=(simd_q15_t *)x,*y128=(simd_q15_t *)y,*y128p=(simd_q15_t *)y; @@ -3571,7 +3573,7 @@ void idft256(int16_t *x,int16_t *y,int scale) #else //__AVX2__ -void dft256(int16_t *x,int16_t *y,int scale) +void dft256(int16_t *x,int16_t *y,unsigned char scale) { simd256_q15_t xtmp[32],ytmp[32],*tw256a_256p=(simd256_q15_t *)tw256a,*tw256b_256p=(simd256_q15_t *)tw256b,*x256=(simd256_q15_t *)x,*y256=(simd256_q15_t *)y,*y256p=(simd256_q15_t *)y; @@ -3663,7 +3665,7 @@ void dft256(int16_t *x,int16_t *y,int scale) } -void idft256(int16_t *x,int16_t *y,int scale) +void idft256(int16_t *x,int16_t *y,unsigned char scale) { simd256_q15_t xtmp[32],ytmp[32],*tw256_256p=(simd256_q15_t *)tw256,*x256=(simd256_q15_t *)x,*y256=(simd256_q15_t *)y,*y256p=(simd256_q15_t *)y; @@ -3768,7 +3770,7 @@ int16_t tw512c[512] __attribute__((aligned(32))) = { }; #ifndef __AVX2__ -void dft512(int16_t *x,int16_t *y,int scale) +void dft512(int16_t *x,int16_t *y,unsigned char scale) { simdshort_q15_t xtmp[256],*xtmpp,*x64 = (simdshort_q15_t *)x; @@ -3888,7 +3890,7 @@ void dft512(int16_t *x,int16_t *y,int scale) } -void idft512(int16_t *x,int16_t *y,int scale) +void idft512(int16_t *x,int16_t *y,unsigned char scale) { simdshort_q15_t xtmp[256],*xtmpp,*x64 = (simdshort_q15_t *)x; @@ -3980,7 +3982,7 @@ void idft512(int16_t *x,int16_t *y,int scale) #else //__AVX2__ -void dft512(int16_t *x,int16_t *y,int scale) +void dft512(int16_t *x,int16_t *y,unsigned char scale) { simd256_q15_t xtmp[64],*x256 = (simd256_q15_t *)x; @@ -4062,7 +4064,7 @@ void dft512(int16_t *x,int16_t *y,int scale) } -void idft512(int16_t *x,int16_t *y,int scale) +void idft512(int16_t *x,int16_t *y,unsigned char scale) { simd256_q15_t xtmp[64],*x256 = (simd256_q15_t *)x; @@ -4149,7 +4151,7 @@ void idft512(int16_t *x,int16_t *y,int scale) int16_t tw1024[1536] __attribute__((aligned(32))); #ifndef __AVX2__ -void dft1024(int16_t *x,int16_t *y,int scale) +void dft1024(int16_t *x,int16_t *y,unsigned char scale) { simd_q15_t xtmp[256],ytmp[256],*tw1024_128p=(simd_q15_t *)tw1024,*x128=(simd_q15_t *)x,*y128=(simd_q15_t *)y,*y128p=(simd_q15_t *)y; @@ -4205,7 +4207,7 @@ void dft1024(int16_t *x,int16_t *y,int scale) } -void idft1024(int16_t *x,int16_t *y,int scale) +void idft1024(int16_t *x,int16_t *y,unsigned char scale) { simd_q15_t xtmp[256],ytmp[256],*tw1024_128p=(simd_q15_t *)tw1024,*x128=(simd_q15_t *)x,*y128=(simd_q15_t *)y,*y128p=(simd_q15_t *)y; @@ -4262,7 +4264,7 @@ void idft1024(int16_t *x,int16_t *y,int scale) } #else //__AVX2__ -void dft1024(int16_t *x,int16_t *y,int scale) +void dft1024(int16_t *x,int16_t *y,unsigned char scale) { simd256_q15_t xtmp[128],ytmp[128],*tw1024_256p=(simd256_q15_t *)tw1024,*x256=(simd256_q15_t *)x,*y256=(simd256_q15_t *)y,*y256p=(simd256_q15_t *)y; @@ -4318,7 +4320,7 @@ void dft1024(int16_t *x,int16_t *y,int scale) } -void idft1024(int16_t *x,int16_t *y,int scale) +void idft1024(int16_t *x,int16_t *y,unsigned char scale) { simd256_q15_t xtmp[128],ytmp[128],*tw1024_256p=(simd256_q15_t *)tw1024,*x256=(simd256_q15_t *)x,*y256=(simd256_q15_t *)y,*y256p=(simd256_q15_t *)y; @@ -4378,7 +4380,7 @@ void idft1024(int16_t *x,int16_t *y,int scale) int16_t tw2048[2048] __attribute__((aligned(32))); #ifndef __AVX2__ -void dft2048(int16_t *x,int16_t *y,int scale) +void dft2048(int16_t *x,int16_t *y,unsigned char scale) { simdshort_q15_t xtmp[1024],*xtmpp,*x64 = (simdshort_q15_t *)x; @@ -4469,7 +4471,7 @@ void dft2048(int16_t *x,int16_t *y,int scale) } -void idft2048(int16_t *x,int16_t *y,int scale) +void idft2048(int16_t *x,int16_t *y,unsigned char scale) { simdshort_q15_t xtmp[1024],*xtmpp,*x64 = (simdshort_q15_t *)x; @@ -4561,7 +4563,7 @@ void idft2048(int16_t *x,int16_t *y,int scale) #else // __AVX2__ -void dft2048(int16_t *x,int16_t *y,int scale) +void dft2048(int16_t *x,int16_t *y,unsigned char scale) { simd256_q15_t xtmp[256],*xtmpp,*x256 = (simd256_q15_t *)x; @@ -4652,7 +4654,7 @@ void dft2048(int16_t *x,int16_t *y,int scale) } -void idft2048(int16_t *x,int16_t *y,int scale) +void idft2048(int16_t *x,int16_t *y,unsigned char scale) { simd256_q15_t xtmp[256],*xtmpp,*x256 = (simd256_q15_t *)x; @@ -4749,7 +4751,7 @@ void idft2048(int16_t *x,int16_t *y,int scale) int16_t tw4096[3*2*1024]; #ifndef __AVX2__ -void dft4096(int16_t *x,int16_t *y,int scale) +void dft4096(int16_t *x,int16_t *y,unsigned char scale) { simd_q15_t xtmp[1024],ytmp[1024],*tw4096_128p=(simd_q15_t *)tw4096,*x128=(simd_q15_t *)x,*y128=(simd_q15_t *)y,*y128p=(simd_q15_t *)y; @@ -4807,7 +4809,7 @@ void dft4096(int16_t *x,int16_t *y,int scale) -void idft4096(int16_t *x,int16_t *y,int scale) +void idft4096(int16_t *x,int16_t *y,unsigned char scale) { simd_q15_t xtmp[1024],ytmp[1024],*tw4096_128p=(simd_q15_t *)tw4096,*x128=(simd_q15_t *)x,*y128=(simd_q15_t *)y,*y128p=(simd_q15_t *)y; @@ -4864,7 +4866,7 @@ void idft4096(int16_t *x,int16_t *y,int scale) } #else //__AVX2__ -void dft4096(int16_t *x,int16_t *y,int scale) +void dft4096(int16_t *x,int16_t *y,unsigned char scale) { simd256_q15_t xtmp[512],ytmp[512],*tw4096_256p=(simd256_q15_t *)tw4096,*x256=(simd256_q15_t *)x,*y256=(simd256_q15_t *)y,*y256p=(simd256_q15_t *)y; @@ -4920,7 +4922,7 @@ void dft4096(int16_t *x,int16_t *y,int scale) } -void idft4096(int16_t *x,int16_t *y,int scale) +void idft4096(int16_t *x,int16_t *y,unsigned char scale) { simd256_q15_t xtmp[512],ytmp[512],*tw4096_256p=(simd256_q15_t *)tw4096,*x256=(simd256_q15_t *)x,*y256=(simd256_q15_t *)y,*y256p=(simd256_q15_t *)y; @@ -4982,7 +4984,7 @@ void idft4096(int16_t *x,int16_t *y,int scale) int16_t tw8192[2*4096] __attribute__((aligned(32))); #ifndef __AVX2__ -void dft8192(int16_t *x,int16_t *y,int scale) +void dft8192(int16_t *x,int16_t *y,unsigned char scale) { simdshort_q15_t xtmp[4096],*xtmpp,*x64 = (simdshort_q15_t *)x; @@ -5072,7 +5074,7 @@ void dft8192(int16_t *x,int16_t *y,int scale) } -void idft8192(int16_t *x,int16_t *y,int scale) +void idft8192(int16_t *x,int16_t *y,unsigned char scale) { simdshort_q15_t xtmp[4096],*xtmpp,*x64 = (simdshort_q15_t *)x; @@ -5163,7 +5165,7 @@ void idft8192(int16_t *x,int16_t *y,int scale) } #else // __AVX2__ -void dft8192(int16_t *x,int16_t *y,int scale) +void dft8192(int16_t *x,int16_t *y,unsigned char scale) { simd256_q15_t xtmp[1024],*xtmpp,*x256 = (simd256_q15_t *)x; @@ -5254,7 +5256,7 @@ void dft8192(int16_t *x,int16_t *y,int scale) } -void idft8192(int16_t *x,int16_t *y,int scale) +void idft8192(int16_t *x,int16_t *y,unsigned char scale) { simd256_q15_t xtmp[1024],*xtmpp,*x256 = (simd256_q15_t *)x; @@ -5350,7 +5352,7 @@ void idft8192(int16_t *x,int16_t *y,int scale) int16_t twa1536[1024],twb1536[1024]; // 512 x 3 -void idft1536(int16_t *input, int16_t *output, int scale) +void idft1536(int16_t *input, int16_t *output, unsigned char scale) { int i,i2,j; uint32_t tmp[3][512 ]__attribute__((aligned(32))); @@ -5402,7 +5404,7 @@ void idft1536(int16_t *input, int16_t *output, int scale) } -void dft1536(int16_t *input, int16_t *output, int scale) +void dft1536(int16_t *input, int16_t *output, unsigned char scale) { int i,i2,j; uint32_t tmp[3][512] __attribute__((aligned(32))); @@ -5467,7 +5469,7 @@ void dft1536(int16_t *input, int16_t *output, int scale) int16_t twa3072[2048] __attribute__((aligned(32))); int16_t twb3072[2048] __attribute__((aligned(32))); // 1024 x 3 -void dft3072(int16_t *input, int16_t *output,int scale) +void dft3072(int16_t *input, int16_t *output,unsigned char scale) { int i,i2,j; uint32_t tmp[3][1024] __attribute__((aligned(32))); @@ -5517,7 +5519,7 @@ void dft3072(int16_t *input, int16_t *output,int scale) _m_empty(); } -void idft3072(int16_t *input, int16_t *output,int scale) +void idft3072(int16_t *input, int16_t *output,unsigned char scale) { int i,i2,j; uint32_t tmp[3][1024]__attribute__((aligned(32))); @@ -5571,7 +5573,7 @@ void idft3072(int16_t *input, int16_t *output,int scale) int16_t twa6144[4096] __attribute__((aligned(32))); int16_t twb6144[4096] __attribute__((aligned(32))); -void idft6144(int16_t *input, int16_t *output,int scale) +void idft6144(int16_t *input, int16_t *output,unsigned char scale) { int i,i2,j; uint32_t tmp[3][2048] __attribute__((aligned(32))); @@ -5631,7 +5633,7 @@ void idft6144(int16_t *input, int16_t *output,int scale) } -void dft6144(int16_t *input, int16_t *output,int scale) +void dft6144(int16_t *input, int16_t *output,unsigned char scale) { int i,i2,j; uint32_t tmp[3][2048] __attribute__((aligned(32))); @@ -5695,12 +5697,12 @@ void dft6144(int16_t *input, int16_t *output,int scale) int16_t twa9216[6144] __attribute__((aligned(32))); int16_t twb9216[6144] __attribute__((aligned(32))); // 3072 x 3 -void dft9216(int16_t *input, int16_t *output,int scale) { +void dft9216(int16_t *input, int16_t *output,uint8_t scale) { AssertFatal(1==0,"Need to do this ..\n"); } -void idft9216(int16_t *input, int16_t *output,int scale) { +void idft9216(int16_t *input, int16_t *output,uint8_t scale) { AssertFatal(1==0,"Need to do this ..\n"); } @@ -5708,7 +5710,7 @@ void idft9216(int16_t *input, int16_t *output,int scale) { int16_t twa12288[8192] __attribute__((aligned(32))); int16_t twb12288[8192] __attribute__((aligned(32))); // 4096 x 3 -void dft12288(int16_t *input, int16_t *output,int scale) +void dft12288(int16_t *input, int16_t *output,unsigned char scale) { int i,i2,j; uint32_t tmp[3][4096] __attribute__((aligned(32))); @@ -5768,7 +5770,7 @@ void dft12288(int16_t *input, int16_t *output,int scale) } -void idft12288(int16_t *input, int16_t *output,int scale) +void idft12288(int16_t *input, int16_t *output,unsigned char scale) { int i,i2,j; uint32_t tmp[3][4096] __attribute__((aligned(32))); @@ -5832,7 +5834,7 @@ void idft12288(int16_t *input, int16_t *output,int scale) int16_t twa18432[12288] __attribute__((aligned(32))); int16_t twb18432[12288] __attribute__((aligned(32))); // 6144 x 3 -void dft18432(int16_t *input, int16_t *output,int scale) { +void dft18432(int16_t *input, int16_t *output,unsigned char scale) { int i,i2,j; uint32_t tmp[3][6144] __attribute__((aligned(32))); @@ -5880,7 +5882,7 @@ void dft18432(int16_t *input, int16_t *output,int scale) { _m_empty(); } -void idft18432(int16_t *input, int16_t *output,int scale) { +void idft18432(int16_t *input, int16_t *output,unsigned char scale) { int i,i2,j; uint32_t tmp[3][6144] __attribute__((aligned(32))); @@ -5932,7 +5934,7 @@ void idft18432(int16_t *input, int16_t *output,int scale) { int16_t twa24576[16384] __attribute__((aligned(32))); int16_t twb24576[16384] __attribute__((aligned(32))); // 8192 x 3 -void dft24576(int16_t *input, int16_t *output,int scale) +void dft24576(int16_t *input, int16_t *output,unsigned char scale) { int i,i2,j; uint32_t tmp[3][8192] __attribute__((aligned(32))); @@ -5995,7 +5997,7 @@ void dft24576(int16_t *input, int16_t *output,int scale) } } -void idft24576(int16_t *input, int16_t *output,int scale) +void idft24576(int16_t *input, int16_t *output,unsigned char scale) { int i,i2,j; uint32_t tmp[3][8192] __attribute__((aligned(32))); @@ -6057,11 +6059,11 @@ void idft24576(int16_t *input, int16_t *output,int scale) int16_t twa36864[24576] __attribute__((aligned(32))); int16_t twb36884[24576] __attribute__((aligned(32))); // 12288 x 3 -void dft36864(int16_t *input, int16_t *output,int scale) { +void dft36864(int16_t *input, int16_t *output,uint8_t scale) { AssertFatal(1==0,"Need to do this ..\n"); } -void idft36864(int16_t *input, int16_t *output,int scale) { +void idft36864(int16_t *input, int16_t *output,uint8_t scale) { AssertFatal(1==0,"Need to do this ..\n"); } @@ -6069,12 +6071,12 @@ void idft36864(int16_t *input, int16_t *output,int scale) { int16_t twa49152[32768] __attribute__((aligned(32))); int16_t twb49152[32768] __attribute__((aligned(32))); // 16384 x 3 -void dft49152(int16_t *input, int16_t *output,int scale) { +void dft49152(int16_t *input, int16_t *output,uint8_t scale) { AssertFatal(1==0,"Need to do this ..\n"); } -void idft49152(int16_t *input, int16_t *output,int scale) { +void idft49152(int16_t *input, int16_t *output,uint8_t scale) { AssertFatal(1==0,"Need to do this ..\n"); } @@ -6082,12 +6084,12 @@ void idft49152(int16_t *input, int16_t *output,int scale) { int16_t twa73728[49152] __attribute__((aligned(32))); int16_t twb73728[49152] __attribute__((aligned(32))); // 24576 x 3 -void dft73728(int16_t *input, int16_t *output,int scale) { +void dft73728(int16_t *input, int16_t *output,uint8_t scale) { AssertFatal(1==0,"Need to do this ..\n"); } -void idft73728(int16_t *input, int16_t *output,int scale) { +void idft73728(int16_t *input, int16_t *output,uint8_t scale) { AssertFatal(1==0,"Need to do this ..\n"); } @@ -6096,12 +6098,12 @@ void idft73728(int16_t *input, int16_t *output,int scale) { int16_t twa98304[49152] __attribute__((aligned(32))); int16_t twb98304[49152] __attribute__((aligned(32))); // 32768 x 3 -void dft98304(int16_t *input, int16_t *output,int scale) { +void dft98304(int16_t *input, int16_t *output,uint8_t scale) { AssertFatal(1==0,"Need to do this ..\n"); } -void idft98304(int16_t *input, int16_t *output,int scale) { +void idft98304(int16_t *input, int16_t *output,uint8_t scale) { AssertFatal(1==0,"Need to do this ..\n"); } @@ -6259,7 +6261,7 @@ static inline void dft12f(simd_q15_t *x0, -void dft12(int16_t *x,int16_t *y) +void dft12(int16_t *x,int16_t *y ,unsigned char scale_flag) { simd_q15_t *x128 = (simd_q15_t *)x,*y128 = (simd_q15_t *)y; @@ -8591,8 +8593,6 @@ void dft1200(int16_t *x,int16_t *y,unsigned char scale_flag) } -//#define round trunc - void init_rad4(int N,int16_t *tw) { int16_t *twa = tw; @@ -8708,12 +8708,13 @@ void init_rad5_rep(int N,int16_t *twa,int16_t *twb,int16_t *twc,int16_t *twd) { twa+=8; twb+=8; twc+=8; - twd+=8; + twd+=8; } } +/*----------------------------------------------------------------*/ +/* dft library entry points: */ - -void init_dfts(void) +int dfts_autoinit(void) { init_rad4(1024,tw1024); init_rad2(2048,tw2048); @@ -8760,9 +8761,23 @@ void init_dfts(void) init_rad3_rep(1080,twa1080,twb1080); init_rad4_rep(1152,twa1152,twb1152,twc1152); init_rad4_rep(1200,twa1200,twb1200,twc1200); + return 0; } -//#undef round + + + +void dft(uint8_t sizeidx, int16_t *sigF,int16_t *sig,unsigned char scale_flag){ + AssertFatal((sizeidx>=0 && sizeidx<(int)DFT_SIZE_IDXTABLESIZE),"Invalid dft size index %i\n",sizeidx); + dft_ftab[sizeidx](sigF,sig,scale_flag); +}; + +void idft(uint8_t sizeidx, int16_t *sigF,int16_t *sig,unsigned char scale_flag){ + AssertFatal((sizeidx>=0 && sizeidx<(int)IDFT_SIZE_IDXTABLESIZE),"Invalid idft size index %i\n",sizeidx); + idft_ftab[sizeidx](sigF,sig,scale_flag); +}; + +/*---------------------------------------------------------------------------------------*/ #ifdef MR_MAIN #include <string.h> @@ -8933,12 +8948,12 @@ int main(int argc, char**argv) #ifdef __AVX2__ simd256_q15_t x[4096],x2[4096],y[4096],tw0,tw1,tw2,tw3; #else - simd_q15_t x[8192],x2[8192],y[8192],tw0,tw1,tw2,tw3; + simd_q15_t x[8192],y[8192],tw0,tw1,tw2,tw3; #endif int i; simd_q15_t *x128=(simd_q15_t*)x,*y128=(simd_q15_t*)y; - init_dfts(); + dfts_autoinit(); set_taus_seed(0); opp_enabled = 1; diff --git a/openair1/PHY/TOOLS/tools_defs.h b/openair1/PHY/TOOLS/tools_defs.h index d753b501b6e7de816f201e98101b483c57211a91..86916cab21b4021cdb1e7e174b177992010d6053 100644 --- a/openair1/PHY/TOOLS/tools_defs.h +++ b/openair1/PHY/TOOLS/tools_defs.h @@ -36,6 +36,8 @@ extern "C" { #include <stdint.h> #include "PHY/sse_intrin.h" +#define CEILIDIV(a,b) ((a+b-1)/b) +#define ROUNDIDIV(a,b) (((a<<1)+b)/(b<<1)) struct complex { double x; @@ -179,44 +181,145 @@ This function performs optimized fixed-point radix-2 FFT/IFFT. ); */ -void idft1536(int16_t *sigF,int16_t *sig,int scale); -void idft6144(int16_t *sigF,int16_t *sig,int scale); -void idft12288(int16_t *sigF,int16_t *sig,int scale); -void idft18432(int16_t *sigF,int16_t *sig,int scale); -void idft3072(int16_t *sigF,int16_t *sig,int scale); -void idft24576(int16_t *sigF,int16_t *sig,int scale); -void dft1536(int16_t *sigF,int16_t *sig,int scale); -void dft3072(int16_t *sigF,int16_t *sig,int scale); +#ifdef OAIDFTS_MAIN +typedef void(*adftfunc_t)(int16_t *sigF,int16_t *sig,unsigned char scale_flag); +typedef void(*aidftfunc_t)(int16_t *sigF,int16_t *sig,unsigned char scale_flag); -void dft6144(int16_t *sigF,int16_t *sig,int scale); - -void dft12288(int16_t *sigF,int16_t *sig,int scale); - -void dft18432(int16_t *sigF,int16_t *sig,int scale); - -void dft24576(int16_t *sigF,int16_t *sig,int scale); - -void dft49152(int16_t *sigF,int16_t *sig,int scale); -void idft49152(int16_t *sigF,int16_t *sig,int scale); - -void dft9216(int16_t *sigF,int16_t *sig,int scale); -void idft9216(int16_t *sigF,int16_t *sig,int scale); +void dft12(int16_t *x,int16_t *y,uint8_t scale_flag); +void dft24(int16_t *x,int16_t *y,uint8_t scale_flag); +void dft36(int16_t *x,int16_t *y,uint8_t scale_flag); +void dft48(int16_t *x,int16_t *y,uint8_t scale_flag); +void dft60(int16_t *x,int16_t *y,uint8_t scale_flag); +void dft64(int16_t *x,int16_t *y,uint8_t scale_flag); +void dft72(int16_t *x,int16_t *y,uint8_t scale_flag); +void dft96(int16_t *x,int16_t *y,uint8_t scale_flag); +void dft108(int16_t *x,int16_t *y,uint8_t scale_flag); +void dft120(int16_t *x,int16_t *y,uint8_t scale_flag); +void dft128(int16_t *x,int16_t *y,uint8_t scale_flag); +void dft144(int16_t *x,int16_t *y,uint8_t scale_flag); +void dft180(int16_t *x,int16_t *y,uint8_t scale_flag); +void dft192(int16_t *x,int16_t *y,uint8_t scale_flag); +void dft216(int16_t *x,int16_t *y,uint8_t scale_flag); +void dft240(int16_t *x,int16_t *y,uint8_t scale_flag); +void dft256(int16_t *x,int16_t *y,uint8_t scale_flag); +void dft288(int16_t *x,int16_t *y,uint8_t scale_flag); +void dft300(int16_t *x,int16_t *y,uint8_t scale_flag); +void dft324(int16_t *x,int16_t *y,uint8_t scale_flag); +void dft360(int16_t *x,int16_t *y,uint8_t scale_flag); +void dft384(int16_t *x,int16_t *y,uint8_t scale_flag); +void dft432(int16_t *x,int16_t *y,uint8_t scale_flag); +void dft480(int16_t *x,int16_t *y,uint8_t scale_flag); +void dft512(int16_t *x,int16_t *y,uint8_t scale_flag); +void dft540(int16_t *x,int16_t *y,uint8_t scale_flag); +void dft576(int16_t *x,int16_t *y,uint8_t scale_flag); +void dft600(int16_t *x,int16_t *y,uint8_t scale_flag); +void dft648(int16_t *x,int16_t *y,uint8_t scale_flag); +void dft720(int16_t *x,int16_t *y,uint8_t scale_flag); +void dft768(int16_t *x,int16_t *y,uint8_t scale_flag); +void dft864(int16_t *x,int16_t *y,uint8_t scale_flag); +void dft900(int16_t *x,int16_t *y,uint8_t scale_flag); +void dft960(int16_t *x,int16_t *y,uint8_t scale_flag); +void dft972(int16_t *x,int16_t *y,uint8_t scale_flag); +void dft1024(int16_t *x,int16_t *y,uint8_t scale_flag); +void dft1080(int16_t *x,int16_t *y,uint8_t scale_flag); +void dft1152(int16_t *x,int16_t *y,uint8_t scale_flag); +void dft1200(int16_t *x,int16_t *y,uint8_t scale_flag); +void dft1536(int16_t *sigF,int16_t *sig,uint8_t scale_flag); +void dft2048(int16_t *x,int16_t *y,uint8_t scale_flag); +void dft3072(int16_t *sigF,int16_t *sig,uint8_t scale_flag); +void dft4096(int16_t *x,int16_t *y,uint8_t scale_flag); +void dft6144(int16_t *sigF,int16_t *sig,uint8_t scale_flag); +void dft8192(int16_t *x,int16_t *y,uint8_t scale_flag); +void dft9216(int16_t *x,int16_t *y,uint8_t scale_flag); +void dft12288(int16_t *x,int16_t *y,uint8_t scale_flag); +void dft18432(int16_t *x,int16_t *y,uint8_t scale_flag); +void dft24576(int16_t *x,int16_t *y,uint8_t scale_flag); +void dft36864(int16_t *x,int16_t *y,uint8_t scale_flag); +void dft49152(int16_t *x,int16_t *y,uint8_t scale_flag); +void dft73728(int16_t *x,int16_t *y,uint8_t scale_flag); +void dft98304(int16_t *x,int16_t *y,uint8_t scale_flag); + + +void idft64(int16_t *x,int16_t *y,uint8_t scale_flag); +void idft128(int16_t *x,int16_t *y,uint8_t scale_flag); +void idft256(int16_t *x,int16_t *y,uint8_t scale_flag); +void idft512(int16_t *x,int16_t *y,uint8_t scale_flag); +void idft1024(int16_t *x,int16_t *y,uint8_t scale_flag); +void idft1536(int16_t *sigF,int16_t *sig,uint8_t scale_flag); +void idft2048(int16_t *x,int16_t *y,uint8_t scale_flag); +void idft3072(int16_t *sigF,int16_t *sig,uint8_t scale_flag); +void idft4096(int16_t *x,int16_t *y,uint8_t scale_flag); +void idft6144(int16_t *sigF,int16_t *sig,uint8_t scale_flag); +void idft8192(int16_t *x,int16_t *y,uint8_t scale_flag); +void idft9216(int16_t *x,int16_t *y,uint8_t scale_flag); +void idft12288(int16_t *sigF,int16_t *sig,uint8_t scale_flag); +void idft18432(int16_t *sigF,int16_t *sig,uint8_t scale_flag); +void idft24576(int16_t *sigF,int16_t *sig,uint8_t scale_flag); +void idft36864(int16_t *sigF,int16_t *sig,uint8_t scale_flag); +void idft49152(int16_t *sigF,int16_t *sig,uint8_t scale_flag); +void idft73728(int16_t *sigF,int16_t *sig,uint8_t scale_flag); +void idft98304(int16_t *sigF,int16_t *sig,uint8_t scale_flag); + + + + +#else + typedef void(*dftfunc_t)(uint8_t sizeidx,int16_t *sigF,int16_t *sig,unsigned char scale_flag); + typedef void(*idftfunc_t)(uint8_t sizeidx,int16_t *sigF,int16_t *sig,unsigned char scale_flag); +# ifdef OAIDFTS_LOADER + dftfunc_t dft; + idftfunc_t idft; +# else + extern dftfunc_t dft; + extern idftfunc_t idft; + extern int load_dftslib(void); +# endif +#endif -void dft36864(int16_t *sigF,int16_t *sig,int scale); -void idft36864(int16_t *sigF,int16_t *sig,int scale); +typedef enum DFT_size_idx { + DFT_12, DFT_24, DFT_36, DFT_48, DFT_60, DFT_72, DFT_96, + DFT_108, DFT_120, DFT_128, DFT_144, DFT_180, DFT_192, DFT_216, DFT_240, + DFT_256, DFT_288, DFT_300, DFT_324, DFT_360, DFT_384, DFT_432, DFT_480, + DFT_512, DFT_540, DFT_576, DFT_600, DFT_648, DFT_720, DFT_768, DFT_864, + DFT_900, DFT_960, DFT_972, DFT_1024, DFT_1080, DFT_1152, DFT_1200, DFT_1536, + DFT_2048, DFT_3072, DFT_4096, DFT_6144, DFT_8192, DFT_9216, DFT_12288, DFT_18432, + DFT_24576, DFT_36864, DFT_49152, DFT_73728, DFT_98304, + DFT_SIZE_IDXTABLESIZE +} dft_size_idx_t; + +#ifdef OAIDFTS_MAIN +adftfunc_t dft_ftab[]={ + dft12, dft24, dft36, dft48, dft60, dft72, dft96, + dft108, dft120, dft128, dft144, dft180, dft192, dft216, dft240, + dft256, dft288, dft300, dft324, dft360, dft384, dft432, dft480, + dft512, dft540, dft576, dft600, dft648, dft720, dft768, dft864, + dft900, dft960, dft972, dft1024, dft1080, dft1152, dft1200, dft1536, + dft2048, dft3072, dft4096, dft6144, dft8192, dft9216, dft12288, dft18432, + dft24576, dft36864, dft49152, dft73728, dft98304 +}; +#endif -void dft98304(int16_t *sigF,int16_t *sig,int scale); -void idft98304(int16_t *sigF,int16_t *sig,int scale); +typedef enum idft_size_idx { + IDFT_128, IDFT_256, IDFT_512, IDFT_1024, IDFT_1536, IDFT_2048, IDFT_3072, IDFT_4096, + IDFT_6144, IDFT_8192, IDFT_9216, IDFT_12288, IDFT_18432, IDFT_24576, IDFT_36864, IDFT_49152, + IDFT_73728, IDFT_98304, + IDFT_SIZE_IDXTABLESIZE +} idft_size_idx_t; +#ifdef OAIDFTS_MAIN +aidftfunc_t idft_ftab[]={ + idft128, idft256, idft512, idft1024, idft1536, idft2048, idft3072, idft4096, + idft6144, idft8192, idft9216, idft12288, idft18432, idft24576, idft36864, idft49152, + idft73728, idft98304 +}; +#endif -void dft73728(int16_t *sigF,int16_t *sig,int scale); -void idft73728(int16_t *sigF,int16_t *sig,int scale); /*!\fn int32_t rotate_cpx_vector(int16_t *x,int16_t *alpha,int16_t *y,uint32_t N,uint16_t output_shift) @@ -387,57 +490,7 @@ int64_t dot_product64(int16_t *x, uint32_t N, //must be a multiple of 8 uint8_t output_shift); -void dft12(int16_t *x,int16_t *y); -void dft24(int16_t *x,int16_t *y,uint8_t scale_flag); -void dft36(int16_t *x,int16_t *y,uint8_t scale_flag); -void dft48(int16_t *x,int16_t *y,uint8_t scale_flag); -void dft60(int16_t *x,int16_t *y,uint8_t scale_flag); -void dft72(int16_t *x,int16_t *y,uint8_t scale_flag); -void dft96(int16_t *x,int16_t *y,uint8_t scale_flag); -void dft108(int16_t *x,int16_t *y,uint8_t scale_flag); -void dft120(int16_t *x,int16_t *y,uint8_t scale_flag); -void dft144(int16_t *x,int16_t *y,uint8_t scale_flag); -void dft180(int16_t *x,int16_t *y,uint8_t scale_flag); -void dft192(int16_t *x,int16_t *y,uint8_t scale_flag); -void dft216(int16_t *x,int16_t *y,uint8_t scale_flag); -void dft240(int16_t *x,int16_t *y,uint8_t scale_flag); -void dft288(int16_t *x,int16_t *y,uint8_t scale_flag); -void dft300(int16_t *x,int16_t *y,uint8_t scale_flag); -void dft324(int16_t *x,int16_t *y,uint8_t scale_flag); -void dft360(int16_t *x,int16_t *y,uint8_t scale_flag); -void dft384(int16_t *x,int16_t *y,uint8_t scale_flag); -void dft432(int16_t *x,int16_t *y,uint8_t scale_flag); -void dft480(int16_t *x,int16_t *y,uint8_t scale_flag); -void dft540(int16_t *x,int16_t *y,uint8_t scale_flag); -void dft576(int16_t *x,int16_t *y,uint8_t scale_flag); -void dft600(int16_t *x,int16_t *y,uint8_t scale_flag); -void dft648(int16_t *x,int16_t *y,uint8_t scale_flag); -void dft720(int16_t *x,int16_t *y,uint8_t scale_flag); -void dft768(int16_t *x,int16_t *y,uint8_t scale_flag); -void dft864(int16_t *x,int16_t *y,uint8_t scale_flag); -void dft900(int16_t *x,int16_t *y,uint8_t scale_flag); -void dft960(int16_t *x,int16_t *y,uint8_t scale_flag); -void dft972(int16_t *x,int16_t *y,uint8_t scale_flag); -void dft1080(int16_t *x,int16_t *y,uint8_t scale_flag); -void dft1152(int16_t *x,int16_t *y,uint8_t scale_flag); -void dft1200(int16_t *x,int16_t *y,uint8_t scale_flag); -void dft64(int16_t *x,int16_t *y,int scale); -void dft128(int16_t *x,int16_t *y,int scale); -void dft256(int16_t *x,int16_t *y,int scale); -void dft512(int16_t *x,int16_t *y,int scale); -void dft1024(int16_t *x,int16_t *y,int scale); -void dft2048(int16_t *x,int16_t *y,int scale); -void dft4096(int16_t *x,int16_t *y,int scale); -void dft8192(int16_t *x,int16_t *y,int scale); -void idft64(int16_t *x,int16_t *y,int scale); -void idft128(int16_t *x,int16_t *y,int scale); -void idft256(int16_t *x,int16_t *y,int scale); -void idft512(int16_t *x,int16_t *y,int scale); -void idft1024(int16_t *x,int16_t *y,int scale); -void idft2048(int16_t *x,int16_t *y,int scale); -void idft4096(int16_t *x,int16_t *y,int scale); -void idft8192(int16_t *x,int16_t *y,int scale); /** @} */ diff --git a/openair1/PHY/defs_gNB.h b/openair1/PHY/defs_gNB.h index b5a24ca793861953eab7ce384cdbda50e469c0a6..7dbb2e796bb9b46eae2949d999e133890c62a3a1 100644 --- a/openair1/PHY/defs_gNB.h +++ b/openair1/PHY/defs_gNB.h @@ -598,6 +598,12 @@ typedef struct { int prach_I0; } PHY_MEASUREMENTS_gNB; +#define MAX_NUM_NR_RX_RACH_PDUS 4 +#define MAX_NUM_NR_RX_PRACH_PREAMBLES 4 +#define MAX_UL_PDUS_PER_SLOT 100 +#define MAX_NUM_NR_SRS_PDUS 100 +#define MAX_NUM_NR_UCI_PDUS 100 + /// Top-level PHY Data Structure for gNB typedef struct PHY_VARS_gNB_s { /// Module ID indicator for this instance @@ -624,19 +630,17 @@ typedef struct PHY_VARS_gNB_s { pthread_mutex_t UL_INFO_mutex; /// NFAPI RX ULSCH information - nfapi_rx_indication_pdu_t rx_pdu_list[NFAPI_RX_IND_MAX_PDU]; + nfapi_nr_rx_data_pdu_t rx_pdu_list[MAX_UL_PDUS_PER_SLOT]; /// NFAPI RX ULSCH CRC information - nfapi_crc_indication_pdu_t crc_pdu_list[NFAPI_CRC_IND_MAX_PDU]; - /// NFAPI HARQ information - nfapi_harq_indication_pdu_t harq_pdu_list[NFAPI_HARQ_IND_MAX_PDU]; - /// NFAPI SR information - nfapi_sr_indication_pdu_t sr_pdu_list[NFAPI_SR_IND_MAX_PDU]; - /// NFAPI CQI information - nfapi_cqi_indication_pdu_t cqi_pdu_list[NFAPI_CQI_IND_MAX_PDU]; - /// NFAPI CQI information (raw component) - nfapi_cqi_indication_raw_pdu_t cqi_raw_pdu_list[NFAPI_CQI_IND_MAX_PDU]; + nfapi_nr_crc_t crc_pdu_list[MAX_UL_PDUS_PER_SLOT]; + /// NFAPI SRS information + nfapi_nr_srs_indication_pdu_t srs_pdu_list[MAX_NUM_NR_SRS_PDUS]; + /// NFAPI UCI information + nfapi_nr_uci_t uci_pdu_list[MAX_NUM_NR_UCI_PDUS]; + /// NFAPI PRACH information + nfapi_nr_prach_indication_pdu_t prach_pdu_indication_list[MAX_NUM_NR_RX_RACH_PDUS]; /// NFAPI PRACH information - nfapi_preamble_pdu_t preamble_list[MAX_NUM_RX_PRACH_PREAMBLES]; + nfapi_nr_prach_indication_preamble_t preamble_list[MAX_NUM_NR_RX_PRACH_PREAMBLES]; //Sched_Rsp_t Sched_INFO; nfapi_nr_ul_tti_request_t UL_tti_req; @@ -713,9 +717,7 @@ typedef struct PHY_VARS_gNB_s { time_stats_t phy_proc; */ time_stats_t phy_proc_tx; - /* time_stats_t phy_proc_rx; - */ time_stats_t rx_prach; /* time_stats_t ofdm_mod_stats; @@ -731,18 +733,21 @@ typedef struct PHY_VARS_gNB_s { time_stats_t dlsch_rate_matching_stats; time_stats_t dlsch_interleaving_stats; time_stats_t dlsch_segmentation_stats; - /* - time_stats_t rx_dft_stats; - time_stats_t ulsch_channel_estimation_stats; - time_stats_t ulsch_freq_offset_estimation_stats; + time_stats_t ulsch_decoding_stats; - time_stats_t ulsch_demodulation_stats; time_stats_t ulsch_rate_unmatching_stats; - time_stats_t ulsch_turbo_decoding_stats; + time_stats_t ulsch_ldpc_decoding_stats; time_stats_t ulsch_deinterleaving_stats; - time_stats_t ulsch_demultiplexing_stats; + time_stats_t ulsch_unscrambling_stats; + time_stats_t ulsch_channel_estimation_stats; + time_stats_t ulsch_channel_compensation_stats; + time_stats_t ulsch_rbs_extraction_stats; time_stats_t ulsch_llr_stats; + /* + time_stats_t rx_dft_stats; + time_stats_t ulsch_freq_offset_estimation_stats; */ + } PHY_VARS_gNB; #endif diff --git a/openair1/SCHED/fapi_l1.c b/openair1/SCHED/fapi_l1.c index 6b7f925c61e090beecd6181014fe21c19d3f2a34..b55ad9938611b734b0e0f87ed9ea005b071266b8 100644 --- a/openair1/SCHED/fapi_l1.c +++ b/openair1/SCHED/fapi_l1.c @@ -597,7 +597,7 @@ void handle_uci_sr_pdu(PHY_VARS_eNB *eNB, uci->frame = frame; uci->subframe = subframe; uci->rnti = ul_config_pdu->uci_sr_pdu.ue_information.ue_information_rel8.rnti; - uci->ue_id = find_dlsch(ul_config_pdu->uci_sr_pdu.ue_information.ue_information_rel8.rnti,eNB,SEARCH_EXIST_OR_FREE); + uci->ue_id = find_ulsch(ul_config_pdu->uci_sr_pdu.ue_information.ue_information_rel8.rnti,eNB,SEARCH_EXIST_OR_FREE); uci->type = SR; uci->pucch_fmt = pucch_format1; uci->num_antenna_ports = 1; @@ -623,7 +623,7 @@ void handle_uci_sr_harq_pdu(PHY_VARS_eNB *eNB,int UE_id,nfapi_ul_config_request_ uci->frame = frame; uci->subframe = subframe; uci->rnti = ul_config_pdu->uci_sr_harq_pdu.ue_information.ue_information_rel8.rnti; - uci->ue_id = find_dlsch(ul_config_pdu->uci_sr_harq_pdu.ue_information.ue_information_rel8.rnti,eNB,SEARCH_EXIST_OR_FREE); + uci->ue_id = find_ulsch(ul_config_pdu->uci_sr_harq_pdu.ue_information.ue_information_rel8.rnti,eNB,SEARCH_EXIST_OR_FREE); uci->type = HARQ_SR; uci->num_antenna_ports = 1; uci->num_pucch_resources = 1; @@ -645,7 +645,7 @@ void handle_uci_harq_pdu(PHY_VARS_eNB *eNB,int UE_id,nfapi_ul_config_request_pdu uci->frame = frame; uci->subframe = subframe; uci->rnti = ul_config_pdu->uci_harq_pdu.ue_information.ue_information_rel8.rnti; - uci->ue_id = find_dlsch(ul_config_pdu->uci_harq_pdu.ue_information.ue_information_rel8.rnti,eNB,SEARCH_EXIST_OR_FREE); + uci->ue_id = find_ulsch(ul_config_pdu->uci_harq_pdu.ue_information.ue_information_rel8.rnti,eNB,SEARCH_EXIST_OR_FREE); uci->type = HARQ; uci->srs_active = srs_active; uci->num_antenna_ports = ul_config_pdu->uci_harq_pdu.harq_information.harq_information_rel11.num_ant_ports; diff --git a/openair1/SCHED/phy_procedures_lte_eNb.c b/openair1/SCHED/phy_procedures_lte_eNb.c index daa9039236fe6993e208709f1bc1c5dbdb27421e..263f4ed99548f12983f7481244564c564db3962c 100644 --- a/openair1/SCHED/phy_procedures_lte_eNb.c +++ b/openair1/SCHED/phy_procedures_lte_eNb.c @@ -657,6 +657,10 @@ uci_procedures(PHY_VARS_eNB *eNB, uci = &(eNB->uci_vars[i]); if ((uci->active == 1) && (uci->frame == frame) && (uci->subframe == subframe)) { + if (uci->ue_id > MAX_MOBILES_PER_ENB) { + LOG_W(PHY, "UCI for UE %d and/or but is not active in MAC\n", uci->ue_id); + continue; + } LOG_D(PHY,"Frame %d, subframe %d: Running uci procedures (type %d) for %d \n", frame, subframe, @@ -1311,7 +1315,121 @@ void pusch_procedures(PHY_VARS_eNB *eNB,L1_rxtx_proc_t *proc) { ulsch_harq->V_UL_DAI, ulsch_harq->nb_rb>20 ? 1 : 0); stop_meas(&eNB->ulsch_decoding_stats); - } + LOG_D(PHY, + "[eNB %d][PUSCH %d] frame %d subframe %d RNTI %x RX power (%d,%d) N0 (%d,%d) dB ACK (%d,%d), decoding iter %d ulsch_harq->cqi_crc_status:%d ackBits:%d ulsch_decoding_stats[t:%lld max:%lld]\n", + eNB->Mod_id,harq_pid, + frame,subframe, + ulsch->rnti, + dB_fixed(eNB->pusch_vars[i]->ulsch_power[0]), + dB_fixed(eNB->pusch_vars[i]->ulsch_power[1]), + 30,//eNB->measurements.n0_power_dB[0], + 30,//eNB->measurements.n0_power_dB[1], + ulsch_harq->o_ACK[0], + ulsch_harq->o_ACK[1], + ret, + ulsch_harq->cqi_crc_status, + ulsch_harq->O_ACK, + eNB->ulsch_decoding_stats.p_time, eNB->ulsch_decoding_stats.max); + if (ulsch_harq->repetition_number < ulsch_harq->total_number_of_repetitions){ + ulsch_harq->rvidx = rvidx_tab[(ulsch_harq->repetition_number%4)] ; // Set the correct rvidx for the next emtc repetitions + ulsch_harq->repetition_number +=1 ; // Increment repetition_number for the next ULSCH allocation + } + //compute the expected ULSCH RX power (for the stats) + ulsch_harq->delta_TF = get_hundred_times_delta_IF_eNB(eNB,i,harq_pid, 0); // 0 means bw_factor is not considered + + if (RC.mac != NULL) { /* ulsim does not use RC.mac context. */ + if (ulsch_harq->cqi_crc_status == 1) { +#ifdef DEBUG_PHY_PROC + //if (((frame%10) == 0) || (frame < 50)) + print_CQI(ulsch_harq->o,ulsch_harq->uci_format,0,fp->N_RB_DL); +#endif + fill_ulsch_cqi_indication(eNB,frame,subframe,ulsch_harq,ulsch->rnti); + RC.mac[eNB->Mod_id]->UE_info.UE_sched_ctrl[i].cqi_req_flag &= (~(1 << subframe)); + } else { + if(RC.mac[eNB->Mod_id]->UE_info.UE_sched_ctrl[i].cqi_req_flag & (1 << subframe) ) { + RC.mac[eNB->Mod_id]->UE_info.UE_sched_ctrl[i].cqi_req_flag &= (~(1 << subframe)); + RC.mac[eNB->Mod_id]->UE_info.UE_sched_ctrl[i].cqi_req_timer=30; + LOG_D(PHY,"Frame %d,Subframe %d, We're supposed to get a cqi here. Set cqi_req_timer to 30.\n",frame,subframe); + } + } + } + + if (ret == (1+MAX_TURBO_ITERATIONS)) { + T(T_ENB_PHY_ULSCH_UE_NACK, T_INT(eNB->Mod_id), T_INT(frame), T_INT(subframe), T_INT(ulsch->rnti), + T_INT(harq_pid)); + fill_crc_indication(eNB,i,frame,subframe,1); // indicate NAK to MAC + fill_rx_indication(eNB,i,frame,subframe); // indicate SDU to MAC + LOG_D(PHY,"[eNB %d][PUSCH %d] frame %d subframe %d UE %d Error receiving ULSCH, round %d/%d (ACK %d,%d)\n", + eNB->Mod_id,harq_pid, + frame,subframe, i, + ulsch_harq->round, + ulsch->Mlimit, + ulsch_harq->o_ACK[0], + ulsch_harq->o_ACK[1]); + + if (ulsch_harq->round >= 3) { + ulsch_harq->status = SCH_IDLE; + ulsch_harq->handled = 0; + ulsch->harq_mask &= ~(1 << harq_pid); + ulsch_harq->round = 0; + } + + MSC_LOG_RX_DISCARDED_MESSAGE( + MSC_PHY_ENB,MSC_PHY_UE, + NULL,0, + "%05u:%02u ULSCH received rnti %x harq id %u round %d", + frame,subframe, + ulsch->rnti,harq_pid, + ulsch_harq->round-1 + ); + /* Mark the HARQ process to release it later if max transmission reached + * (see below). + * MAC does not send the max transmission count, we have to deal with it + * locally in PHY. + */ + ulsch_harq->handled = 1; + } // ulsch in error + else if(ulsch_harq->repetition_number == ulsch_harq->total_number_of_repetitions){ + fill_crc_indication(eNB,i,frame,subframe,0); // indicate ACK to MAC + fill_rx_indication(eNB,i,frame,subframe); // indicate SDU to MAC + ulsch_harq->status = SCH_IDLE; + ulsch->harq_mask &= ~(1 << harq_pid); + T (T_ENB_PHY_ULSCH_UE_ACK, T_INT (eNB->Mod_id), T_INT (frame), T_INT (subframe), T_INT (ulsch->rnti), T_INT (harq_pid)); + MSC_LOG_RX_MESSAGE( + MSC_PHY_ENB,MSC_PHY_UE, + NULL,0, + "%05u:%02u ULSCH received rnti %x harq id %u", + frame,subframe, + ulsch->rnti,harq_pid + ); +#ifdef DEBUG_PHY_PROC +#ifdef DEBUG_ULSCH + LOG_D(PHY,"[eNB] Frame %d, Subframe %d : ULSCH SDU (RX harq_pid %d) %d bytes:",frame,subframe, + harq_pid,ulsch_harq->TBS>>3); + + for (j=0; j<ulsch_harq->TBS>>3; j++) + LOG_T(PHY,"%x.",ulsch->harq_processes[harq_pid]->b[j]); + + LOG_T(PHY,"\n"); +#endif +#endif + } // ulsch not in error + + if (ulsch_harq->O_ACK>0) fill_ulsch_harq_indication(eNB,ulsch_harq,ulsch->rnti,frame,subframe,ulsch->bundling); + + LOG_D(PHY,"[eNB %d] Frame %d subframe %d: received ULSCH harq_pid %d for UE %d, ret = %d, CQI CRC Status %d, ACK %d,%d, ulsch_errors %d/%d\n", + eNB->Mod_id,frame,subframe, + harq_pid, + i, + ret, + ulsch_harq->cqi_crc_status, + ulsch_harq->o_ACK[0], + ulsch_harq->o_ACK[1], + eNB->UE_stats[i].ulsch_errors[harq_pid], + eNB->UE_stats[i].ulsch_decoding_attempts[harq_pid][0]); + } // if ((ulsch) && + // (ulsch->rnti>0) && + // (ulsch_harq->status == ACTIVE)) else if ((ulsch) && (ulsch->rnti>0) && (ulsch_harq->status == ACTIVE) && diff --git a/openair1/SCHED_NR/fapi_nr_l1.h b/openair1/SCHED_NR/fapi_nr_l1.h index 07509b3bb7b846b2608048d589c50de1298727c2..d66d6e7b24201d5db0f8149ba5ef356555f13fb0 100644 --- a/openair1/SCHED_NR/fapi_nr_l1.h +++ b/openair1/SCHED_NR/fapi_nr_l1.h @@ -46,6 +46,5 @@ void handle_nr_nfapi_pdsch_pdu(PHY_VARS_gNB *gNB,int frame,int slot, nfapi_nr_dl_tti_pdsch_pdu *pdsch_pdu, uint8_t *sdu); -void nr_fill_rx_indication(PHY_VARS_gNB *gNB, int frame, int slot_rx, int UE_id, uint8_t harq_pid); -void nr_fill_crc_indication(PHY_VARS_gNB *gNB, int frame, int slot_rx, int UE_id, uint8_t crc_flag); +void nr_fill_indication(PHY_VARS_gNB *gNB, int frame, int slot_rx, int UE_id, uint8_t harq_pid, uint8_t crc_flag); diff --git a/openair1/SCHED_NR/nr_prach_procedures.c b/openair1/SCHED_NR/nr_prach_procedures.c index b9a8ba94f1eefa6559da89beff7ece19282345cb..1ed8f28b49e21661d5d08c3d132b3b209329b3e7 100644 --- a/openair1/SCHED_NR/nr_prach_procedures.c +++ b/openair1/SCHED_NR/nr_prach_procedures.c @@ -32,7 +32,7 @@ #include "PHY/defs_gNB.h" #include "PHY/phy_extern.h" -#include "PHY/NR_TRANSPORT/nr_transport_proto.h" +#include "PHY/NR_TRANSPORT/nr_transport.h" #include "nfapi_nr_interface_scf.h" #include "fapi_nr_l1.h" #include "nfapi_pnf.h" @@ -47,17 +47,19 @@ #include "intertask_interface.h" -extern uint32_t nfapi_mode; +extern uint8_t nfapi_mode; extern int oai_nfapi_nr_rach_ind(nfapi_rach_indication_t *rach_ind); -void L1_nr_prach_procedures(PHY_VARS_gNB *gNB,int frame,int subframe) { +void L1_nr_prach_procedures(PHY_VARS_gNB *gNB,int frame,int slot, + nfapi_nr_prach_pdu_t *prach_pdu) { + uint16_t max_preamble[4],max_preamble_energy[4],max_preamble_delay[4]; uint16_t i; - gNB->UL_INFO.rach_ind.rach_indication_body.number_of_preambles=0; + gNB->UL_INFO.rach_ind.number_of_pdus=0; RU_t *ru; int aa=0; @@ -75,16 +77,18 @@ void L1_nr_prach_procedures(PHY_VARS_gNB *gNB,int frame,int subframe) { } } - rx_nr_prach(gNB, + + /* rx_nr_prach(gNB, + prach_pdu, frame, - subframe, + slot, &max_preamble[0], &max_preamble_energy[0], &max_preamble_delay[0] - ); + );*/ - LOG_D(PHY,"[RAPROC] Frame %d, subframe %d : Most likely preamble %d, energy %d dB delay %d (prach_energy counter %d)\n", - frame,subframe, + LOG_D(PHY,"[RAPROC] Frame %d, slot %d : Most likely preamble %d, energy %d dB delay %d (prach_energy counter %d)\n", + frame,slot, max_preamble[0], max_preamble_energy[0]/10, max_preamble_delay[0], @@ -93,49 +97,43 @@ void L1_nr_prach_procedures(PHY_VARS_gNB *gNB,int frame,int subframe) { if ((gNB->prach_energy_counter == 100) && (max_preamble_energy[0] > gNB->measurements.prach_I0+100)) { - LOG_I(PHY,"[gNB %d][RAPROC] Frame %d, subframe %d Initiating RA procedure with preamble %d, energy %d.%d dB, delay %d\n", + LOG_I(PHY,"[gNB %d][RAPROC] Frame %d, slot %d Initiating RA procedure with preamble %d, energy %d.%d dB, delay %d\n", gNB->Mod_id, frame, - subframe, + slot, max_preamble[0], max_preamble_energy[0]/10, max_preamble_energy[0]%10, max_preamble_delay[0]); - T(T_ENB_PHY_INITIATE_RA_PROCEDURE, T_INT(gNB->Mod_id), T_INT(frame), T_INT(subframe), + T(T_ENB_PHY_INITIATE_RA_PROCEDURE, T_INT(gNB->Mod_id), T_INT(frame), T_INT(slot), T_INT(max_preamble[0]), T_INT(max_preamble_energy[0]), T_INT(max_preamble_delay[0])); - gNB->UL_INFO.rach_ind.rach_indication_body.number_of_preambles = 1; - gNB->UL_INFO.rach_ind.rach_indication_body.preamble_list = &gNB->preamble_list[0]; - gNB->UL_INFO.rach_ind.rach_indication_body.tl.tag = NFAPI_RACH_INDICATION_BODY_TAG; - gNB->UL_INFO.rach_ind.header.message_id = NFAPI_RACH_INDICATION; - gNB->UL_INFO.rach_ind.sfn_sf = frame<<4 | subframe; - - gNB->preamble_list[0].preamble_rel8.tl.tag = NFAPI_PREAMBLE_REL8_TAG; - gNB->preamble_list[0].preamble_rel8.timing_advance = max_preamble_delay[0]; - gNB->preamble_list[0].preamble_rel8.preamble = max_preamble[0]; - gNB->preamble_list[0].preamble_rel8.rnti = 1+subframe; // note: fid is implicitly 0 here - gNB->preamble_list[0].instance_length = 0; //don't know exactly what this is + gNB->UL_INFO.rach_ind.number_of_pdus = 1; + gNB->UL_INFO.rach_ind.pdu_list = &gNB->prach_pdu_indication_list[0]; + gNB->UL_INFO.rach_ind.sfn = frame; + gNB->UL_INFO.rach_ind.slot = slot; - if (nfapi_mode == 1) { // If NFAPI PNF then we need to send the message to the VNF - - LOG_D(PHY,"Filling NFAPI indication for NR RACH : SFN_SF:%d TA %d, Preamble %d, rnti %x\n", - NFAPI_SFNSF2DEC(gNB->UL_INFO.rach_ind.sfn_sf), - gNB->preamble_list[0].preamble_rel8.timing_advance, - gNB->preamble_list[0].preamble_rel8.preamble, - gNB->preamble_list[0].preamble_rel8.rnti); - AssertFatal(1==0,"shouldn't be here yet..\n"); - //oai_nfapi_nr_rach_ind(&gNB->UL_INFO.rach_ind); - - gNB->UL_INFO.rach_ind.rach_indication_body.number_of_preambles = 0; - } - } // max_preamble_energy > prach_I0 + 100 - else { - gNB->measurements.prach_I0 = ((gNB->measurements.prach_I0*900)>>10) + ((max_preamble_energy[0]*124)>>10); - if (frame==0) LOG_I(PHY,"prach_I0 = %d.%d dB\n",gNB->measurements.prach_I0/10,gNB->measurements.prach_I0%10); - if (gNB->prach_energy_counter < 100) gNB->prach_energy_counter++; - } + gNB->prach_pdu_indication_list[0].phy_cell_id = gNB->gNB_config.cell_config.phy_cell_id.value; + gNB->prach_pdu_indication_list[0].symbol_index = prach_pdu->prach_start_symbol; // FIXME to be changed for multi-ssb (this is only the start symbol of first occasion) + gNB->prach_pdu_indication_list[0].slot_index = slot; + gNB->prach_pdu_indication_list[0].freq_index = prach_pdu->num_ra; + gNB->prach_pdu_indication_list[0].avg_rssi = (max_preamble_energy[0]<631) ? (128+(max_preamble_energy[0]/5)) : 254; + gNB->prach_pdu_indication_list[0].avg_snr = 0xff; // invalid for now + + + gNB->prach_pdu_indication_list[0].num_preamble = 1; + gNB->prach_pdu_indication_list[0].preamble_list = gNB->preamble_list; + gNB->prach_pdu_indication_list[0].preamble_list[0].preamble_index = max_preamble[0]; + gNB->prach_pdu_indication_list[0].preamble_list[0].timing_advance = max_preamble_delay[0]; + gNB->prach_pdu_indication_list[0].preamble_list[0].preamble_pwr = 0xffffffff; + } + gNB->measurements.prach_I0 = ((gNB->measurements.prach_I0*900)>>10) + ((max_preamble_energy[0]*124)>>10); + if (frame==0) LOG_I(PHY,"prach_I0 = %d.%d dB\n",gNB->measurements.prach_I0/10,gNB->measurements.prach_I0%10); + if (gNB->prach_energy_counter < 100) gNB->prach_energy_counter++; + VCD_SIGNAL_DUMPER_DUMP_FUNCTION_BY_NAME(VCD_SIGNAL_DUMPER_FUNCTIONS_PHY_ENB_PRACH_RX,0); } + diff --git a/openair1/SCHED_NR/phy_procedures_nr_gNB.c b/openair1/SCHED_NR/phy_procedures_nr_gNB.c index d9a7ee3c69a4819d64412a6a8bf79d7a7b3685fa..be8ad0470f98c0d963aef49a7d9260bfe74156c0 100644 --- a/openair1/SCHED_NR/phy_procedures_nr_gNB.c +++ b/openair1/SCHED_NR/phy_procedures_nr_gNB.c @@ -242,16 +242,18 @@ void nr_ulsch_procedures(PHY_VARS_gNB *gNB, int frame_rx, int slot_rx, int ULSCH //------------------- ULSCH unscrambling ------------------- //---------------------------------------------------------- + start_meas(&gNB->ulsch_unscrambling_stats); nr_ulsch_unscrambling(gNB->pusch_vars[ULSCH_id]->llr, G, 0, pusch_pdu->data_scrambling_id, pusch_pdu->rnti); - + stop_meas(&gNB->ulsch_unscrambling_stats); //---------------------------------------------------------- //--------------------- ULSCH decoding --------------------- //---------------------------------------------------------- + start_meas(&gNB->ulsch_decoding_stats); ret = nr_ulsch_decoding(gNB, ULSCH_id, gNB->pusch_vars[ULSCH_id]->llr, @@ -261,57 +263,30 @@ void nr_ulsch_procedures(PHY_VARS_gNB *gNB, int frame_rx, int slot_rx, int ULSCH slot_rx, harq_pid, G); + stop_meas(&gNB->ulsch_decoding_stats); - - if (ret > gNB->ulsch[ULSCH_id][0]->max_ldpc_iterations) + if (ret > gNB->ulsch[ULSCH_id][0]->max_ldpc_iterations){ LOG_I(PHY, "ULSCH %d in error\n",ULSCH_id); - //gNB->ulsch[ULSCH_id+1][0]->harq_processes[harq_pid]->b + nr_fill_indication(gNB,frame_rx, slot_rx, ULSCH_id, harq_pid, 1); + } else if(gNB->ulsch[ULSCH_id][0]->harq_processes[harq_pid]->b!=NULL){ - LOG_I(PHY, "ULSCH received ok \n"); - if(IS_SOFTMODEM_NOS1){ //&& gNB->ulsch[ULSCH_id][0]->rnti == 0x1234 - nr_fill_crc_indication(gNB,frame_rx, slot_rx, ULSCH_id, 0); - nr_fill_rx_indication(gNB, frame_rx, slot_rx, ULSCH_id, harq_pid); - } + LOG_I(PHY, "ULSCH received ok \n"); + nr_fill_indication(gNB,frame_rx, slot_rx, ULSCH_id, harq_pid, 0); } - } -void nr_fill_rx_indication(PHY_VARS_gNB *gNB, int frame, int slot_rx, int ULSCH_id, uint8_t harq_pid) -{ - // -------------------- - // [hna] TO BE CLEANED - // -------------------- +void nr_fill_indication(PHY_VARS_gNB *gNB, int frame, int slot_rx, int ULSCH_id, uint8_t harq_pid, uint8_t crc_flag) { - nfapi_rx_indication_pdu_t *pdu; + pthread_mutex_lock(&gNB->UL_INFO_mutex); - int timing_advance_update; + int timing_advance_update, cqi; int sync_pos; - uint16_t mu = gNB->frame_parms.numerology_index; - // pthread_mutex_lock(&gNB->UL_INFO_mutex); NR_gNB_ULSCH_t *ulsch = gNB->ulsch[ULSCH_id][0]; NR_UL_gNB_HARQ_t *harq_process = ulsch->harq_processes[harq_pid]; - pthread_mutex_lock(&gNB->UL_INFO_mutex); - - gNB->UL_INFO.rx_ind.sfn_sf = frame<<4| slot_rx; - gNB->UL_INFO.rx_ind.rx_indication_body.tl.tag = NFAPI_RX_INDICATION_BODY_TAG; - gNB->UL_INFO.rx_ind.rx_indication_body.rx_pdu_list->rx_indication_rel8.length = gNB->ulsch[ULSCH_id][0]->harq_processes[harq_pid]->TBS; - - pdu = &gNB->UL_INFO.rx_ind.rx_indication_body.rx_pdu_list[gNB->UL_INFO.rx_ind.rx_indication_body.number_of_pdus]; - - //pdu->rx_ue_information.handle = gNB->ulsch[ULSCH_id+1][0]->handle; - pdu->rx_ue_information.tl.tag = NFAPI_RX_UE_INFORMATION_TAG; - pdu->rx_ue_information.rnti = gNB->ulsch[ULSCH_id][0]->rnti; - pdu->rx_indication_rel8.tl.tag = NFAPI_RX_INDICATION_REL8_TAG; - pdu->rx_indication_rel8.offset = 1; // DJP - I dont understand - but broken unless 1 ???? 0; // filled in at the end of the UL_INFO formation - pdu->data = harq_process->b;//gNB->ulsch[ULSCH_id+1][0]->harq_processes[harq_pid]->b; - // estimate timing advance for MAC - sync_pos = nr_est_timing_advance_pusch(gNB, ULSCH_id); - timing_advance_update = sync_pos; // - gNB->frame_parms.nb_prefix_samples/4; //to check - // printf("\x1B[33m" "timing_advance_update = %d\n" "\x1B[0m", timing_advance_update); - + nfapi_nr_pusch_pdu_t *pusch_pdu = &harq_process->ulsch_pdu; // pdu->data = gNB->ulsch[ULSCH_id+1][0]->harq_processes[harq_pid]->b; sync_pos = nr_est_timing_advance_pusch(gNB, ULSCH_id); // estimate timing advance for MAC @@ -335,39 +310,50 @@ void nr_fill_rx_indication(PHY_VARS_gNB *gNB, int frame, int slot_rx, int ULSCH_ LOG_D(PHY, "Estimated timing advance PUSCH is = %d, timing_advance_update is %d \n", sync_pos,timing_advance_update); - pdu->rx_indication_rel8.timing_advance = timing_advance_update; - // estimate UL_CQI for MAC (from antenna port 0 only) int SNRtimes10 = dB_fixed_times10(gNB->pusch_vars[ULSCH_id]->ulsch_power[0]) - 300;//(10*gNB->measurements.n0_power_dB[0]); - if (SNRtimes10 < -640) pdu->rx_indication_rel8.ul_cqi=0; - else if (SNRtimes10 > 635) pdu->rx_indication_rel8.ul_cqi=255; - else pdu->rx_indication_rel8.ul_cqi=(640+SNRtimes10)/5; - - // LOG_D(PHY,"[PUSCH %d] Frame %d Subframe %d Filling RX_indication with SNR %d (%d), timing_advance %d (update %d)\n", - // harq_pid,frame,slot_rx,SNRtimes10,pdu->rx_indication_rel8.ul_cqi,pdu->rx_indication_rel8.timing_advance, - // timing_advance_update); - - gNB->UL_INFO.rx_ind.rx_indication_body.number_of_pdus++; - gNB->UL_INFO.rx_ind.sfn_sf = frame<<4 | slot_rx; + if (SNRtimes10 < -640) cqi=0; + else if (SNRtimes10 > 635) cqi=255; + else cqi=(640+SNRtimes10)/5; + + // crc indication + uint16_t num_crc = gNB->UL_INFO.crc_ind.number_crcs; + gNB->UL_INFO.crc_ind.crc_list = &gNB->crc_pdu_list[0]; + gNB->UL_INFO.crc_ind.sfn = frame; + gNB->UL_INFO.crc_ind.slot = slot_rx; + + gNB->crc_pdu_list[num_crc].handle = pusch_pdu->handle; + gNB->crc_pdu_list[num_crc].rnti = pusch_pdu->rnti; + gNB->crc_pdu_list[num_crc].harq_id = harq_pid; + gNB->crc_pdu_list[num_crc].tb_crc_status = crc_flag; + gNB->crc_pdu_list[num_crc].num_cb = pusch_pdu->pusch_data.num_cb; + gNB->crc_pdu_list[num_crc].ul_cqi = cqi; + gNB->crc_pdu_list[num_crc].timing_advance = timing_advance_update; + gNB->crc_pdu_list[num_crc].rssi = 0xffff; // invalid value as this is not yet computed + + gNB->UL_INFO.crc_ind.number_crcs++; + + // rx indication + uint16_t num_rx = gNB->UL_INFO.rx_ind.number_of_pdus; + gNB->UL_INFO.rx_ind.pdu_list = &gNB->rx_pdu_list[0]; + gNB->UL_INFO.rx_ind.sfn = frame; + gNB->UL_INFO.rx_ind.slot = slot_rx; + gNB->rx_pdu_list[num_rx].handle = pusch_pdu->handle; + gNB->rx_pdu_list[num_rx].rnti = pusch_pdu->rnti; + gNB->rx_pdu_list[num_rx].harq_id = harq_pid; + gNB->rx_pdu_list[num_rx].ul_cqi = cqi; + gNB->rx_pdu_list[num_rx].timing_advance = timing_advance_update; + gNB->rx_pdu_list[num_rx].rssi = 0xffff; // invalid value as this is not yet computed + if (crc_flag) + gNB->rx_pdu_list[num_rx].pdu_length = 0; + else { + gNB->rx_pdu_list[num_rx].pdu_length = harq_process->TBS; + gNB->rx_pdu_list[num_rx].pdu = harq_process->b; + } - pthread_mutex_unlock(&gNB->UL_INFO_mutex); -} + gNB->UL_INFO.rx_ind.number_of_pdus++; -void nr_fill_crc_indication (PHY_VARS_gNB *gNB, int frame, int slot_rx, int ULSCH_id, uint8_t crc_flag) { - pthread_mutex_lock(&gNB->UL_INFO_mutex); - nfapi_crc_indication_pdu_t *pdu = &gNB->UL_INFO. crc_ind.crc_indication_body.crc_pdu_list[gNB->UL_INFO.crc_ind.crc_indication_body.number_of_crcs]; - gNB->UL_INFO.crc_ind.sfn_sf = frame<<4 | slot_rx; - gNB->UL_INFO.crc_ind.header.message_id = NFAPI_CRC_INDICATION; - gNB->UL_INFO.crc_ind.crc_indication_body.tl.tag = NFAPI_CRC_INDICATION_BODY_TAG; - pdu->instance_length = 0; // don't know what to do with this - // pdu->rx_ue_information.handle = handle; - pdu->rx_ue_information.tl.tag = NFAPI_RX_UE_INFORMATION_TAG; - pdu->rx_ue_information.rnti = gNB->ulsch[ULSCH_id][0]->rnti; - pdu->crc_indication_rel8.tl.tag = NFAPI_CRC_INDICATION_REL8_TAG; - pdu->crc_indication_rel8.crc_flag = crc_flag; - gNB->UL_INFO.crc_ind.crc_indication_body.number_of_crcs++; - //LOG_D(PHY, "%s() rnti:%04x crcs:%d crc_flag:%d\n", __FUNCTION__, pdu->rx_ue_information.rnti, eNB->UL_INFO.crc_ind.crc_indication_body.number_of_crcs, crc_flag); pthread_mutex_unlock(&gNB->UL_INFO_mutex); } @@ -398,7 +384,8 @@ void phy_procedures_gNB_uespec_RX(PHY_VARS_gNB *gNB, int frame_rx, int slot_rx) LOG_D(PHY,"phy_procedures_gNB_uespec_RX frame %d, slot %d, num_pusch_pdu %d\n",frame_rx,slot_rx,num_pusch_pdu); - gNB->UL_INFO.rx_ind.rx_indication_body.number_of_pdus = 0; + gNB->UL_INFO.rx_ind.number_of_pdus = 0; + gNB->UL_INFO.crc_ind.number_crcs = 0; for (int i = 0; i < num_pusch_pdu; i++) { switch (UL_tti_req->pdus_list[i].pdu_type) { @@ -419,8 +406,6 @@ void phy_procedures_gNB_uespec_RX(PHY_VARS_gNB *gNB, int frame_rx, int slot_rx) //LOG_M("rxdataF_comp.m","rxF_comp",gNB->pusch_vars[0]->rxdataF_comp[0],6900,1,1); //LOG_M("rxdataF_ext.m","rxF_ext",gNB->pusch_vars[0]->rxdataF_ext[0],6900,1,1); nr_ulsch_procedures(gNB, frame_rx, slot_rx, ULSCH_id, harq_pid); - nr_fill_rx_indication(gNB, frame_rx, slot_rx, ULSCH_id, harq_pid); // indicate SDU to MAC - nr_fill_crc_indication(gNB, frame_rx, slot_rx, ULSCH_id, 0); } } } diff --git a/openair1/SIMULATION/NR_PHY/dlsim.c b/openair1/SIMULATION/NR_PHY/dlsim.c index ebcedbaeb09f6723019819e1dc8477814a08817b..7982937e6d52d025157cbdfd60b1d0162e034dcb 100644 --- a/openair1/SIMULATION/NR_PHY/dlsim.c +++ b/openair1/SIMULATION/NR_PHY/dlsim.c @@ -412,6 +412,7 @@ int main(int argc, char **argv) printf("-c Start symbol for PDSCH (fixed for now)\n"); printf("-j Number of symbols for PDSCH (fixed for now)\n"); printf("-e MSC index\n"); + printf("-P Print DLSCH performances\n"); exit (-1); break; } @@ -901,7 +902,6 @@ int main(int argc, char **argv) break; } - if (print_perf==1) { printf("\ngNB TX function statistics (per %d us slot, NPRB %d, mcs %d, TBS %d, Kr %d (Zc %d))\n", 1000>>*scc->ssbSubcarrierSpacing,dlsch_config.rbSize,dlsch_config.mcsIndex[0], diff --git a/openair1/SIMULATION/NR_PHY/ulsim.c b/openair1/SIMULATION/NR_PHY/ulsim.c index 2adc67501a51388514412212c1281b01e3a58432..7c1b441b6a30bd1934a4470dd998927f535943d8 100644 --- a/openair1/SIMULATION/NR_PHY/ulsim.c +++ b/openair1/SIMULATION/NR_PHY/ulsim.c @@ -55,7 +55,8 @@ #include "openair2/RRC/NR/MESSAGES/asn1_msg.h" #include "openair2/LAYER2/NR_MAC_UE/mac_proto.h" #include "openair2/LAYER2/NR_MAC_gNB/mac_proto.h" - +#define inMicroS(a) (((double)(a))/(cpu_freq_GHz*1000.0)) +#include "SIMULATION/LTE_PHY/common_sim.h" //#define DEBUG_ULSIM PHY_VARS_gNB *gNB; @@ -140,7 +141,7 @@ int main(int argc, char **argv) int start_rb = 0; int UE_id =0; // [hna] only works for UE_id = 0 because NUMBER_OF_NR_UE_MAX is set to 1 (phy_init_nr_gNB causes segmentation fault) float target_error_rate = 0.01; - + int print_perf = 0; cpuf = get_cpu_freq_GHz(); @@ -155,7 +156,7 @@ int main(int argc, char **argv) //logInit(); randominit(0); - while ((c = getopt(argc, argv, "d:f:g:h:i:j:l:m:n:p:r:s:y:z:F:M:N:P:R:S:L:")) != -1) { + while ((c = getopt(argc, argv, "d:f:g:h:i:j:l:m:n:p:r:s:y:z:F:M:N:PR:S:L:")) != -1) { switch (c) { /*case 'd': @@ -309,9 +310,14 @@ int main(int argc, char **argv) printf("Setting SNR1 to %f\n", snr1); break; - case 'L': - loglvl = atoi(optarg); - break; + case 'P': + print_perf=1; + opp_enabled=1; + break; + + case 'L': + loglvl = atoi(optarg); + break; default: case 'h': @@ -340,6 +346,7 @@ int main(int argc, char **argv) printf("-O oversampling factor (1,2,4,8,16)\n"); printf("-R N_RB_DL\n"); printf("-S Ending SNR, runs from SNR0 to SNR1\n"); + printf("-P Print ULSCH performances\n"); exit(-1); break; } @@ -370,10 +377,10 @@ int main(int argc, char **argv) //gNB_config = &gNB->gNB_config; //memset((void *)&gNB->UL_INFO,0,sizeof(gNB->UL_INFO)); - gNB->UL_INFO.rx_ind.rx_indication_body.rx_pdu_list = (nfapi_rx_indication_pdu_t *)malloc(NB_UE_INST*sizeof(nfapi_rx_indication_pdu_t)); - gNB->UL_INFO.crc_ind.crc_indication_body.crc_pdu_list = (nfapi_crc_indication_pdu_t *)malloc(NB_UE_INST*sizeof(nfapi_crc_indication_pdu_t)); - gNB->UL_INFO.rx_ind.rx_indication_body.number_of_pdus = 0; - gNB->UL_INFO.crc_ind.crc_indication_body.number_of_crcs = 0; + gNB->UL_INFO.rx_ind.pdu_list = (nfapi_nr_rx_data_pdu_t *)malloc(NB_UE_INST*sizeof(nfapi_nr_rx_data_pdu_t)); + gNB->UL_INFO.crc_ind.crc_list = (nfapi_nr_crc_t *)malloc(NB_UE_INST*sizeof(nfapi_nr_crc_t)); + gNB->UL_INFO.rx_ind.number_of_pdus = 0; + gNB->UL_INFO.crc_ind.number_crcs = 0; frame_parms = &gNB->frame_parms; //to be initialized I suppose (maybe not necessary for PBCH) frame_parms->nb_antennas_tx = n_tx; frame_parms->nb_antennas_rx = n_rx; @@ -524,6 +531,18 @@ int main(int argc, char **argv) for (SNR = snr0; SNR < snr1; SNR += snr_step) { + varArray_t *table_rx=initVarArray(1000,sizeof(double)); + reset_meas(&gNB->phy_proc_rx); + reset_meas(&gNB->ulsch_decoding_stats); + reset_meas(&gNB->ulsch_deinterleaving_stats); + reset_meas(&gNB->ulsch_rate_unmatching_stats); + reset_meas(&gNB->ulsch_ldpc_decoding_stats); + reset_meas(&gNB->ulsch_unscrambling_stats); + reset_meas(&gNB->ulsch_channel_estimation_stats); + reset_meas(&gNB->ulsch_llr_stats); + reset_meas(&gNB->ulsch_channel_compensation_stats); + reset_meas(&gNB->ulsch_rbs_extraction_stats); + UE_proc.nr_tti_tx = slot; UE_proc.frame_tx = frame; @@ -651,15 +670,17 @@ int main(int argc, char **argv) //---------------------------------------------------------- //------------------- gNB phy procedures ------------------- //---------------------------------------------------------- - gNB->UL_INFO.rx_ind.rx_indication_body.number_of_pdus = 0; - gNB->UL_INFO.crc_ind.crc_indication_body.number_of_crcs = 0; + gNB->UL_INFO.rx_ind.number_of_pdus = 0; + gNB->UL_INFO.crc_ind.number_crcs = 0; + start_meas(&gNB->phy_proc_rx); phy_procedures_gNB_common_RX(gNB, frame, slot); if (n_trials==1) LOG_M("rxsigF0.m","rxsF0",gNB->common_vars.rxdataF[0],frame_length_complex_samples_no_prefix,1,1); phy_procedures_gNB_uespec_RX(gNB, frame, slot); + start_meas(&gNB->phy_proc_rx); //////////////////////////////////////////////////////////// if (gNB->ulsch[0][0]->last_iteration_cnt >= @@ -713,6 +734,20 @@ int main(int argc, char **argv) printf("*****************************************\n"); printf("\n"); + if (print_perf==1) { + printDistribution(&gNB->phy_proc_rx,table_rx,"Total PHY proc rx"); + printStatIndent(&gNB->ulsch_channel_estimation_stats,"ULSCH channel estimation time"); + printStatIndent(&gNB->ulsch_rbs_extraction_stats,"ULSCH rbs extraction time"); + printStatIndent(&gNB->ulsch_channel_compensation_stats,"ULSCH channel compensation time"); + printStatIndent(&gNB->ulsch_llr_stats,"ULSCH llr computation"); + printStatIndent(&gNB->ulsch_unscrambling_stats,"ULSCH unscrambling"); + printStatIndent(&gNB->ulsch_decoding_stats,"ULSCH total decoding time"); + printStatIndent2(&gNB->ulsch_deinterleaving_stats,"ULSCH deinterleaving"); + printStatIndent2(&gNB->ulsch_rate_unmatching_stats,"ULSCH rate matching rx"); + printStatIndent2(&gNB->ulsch_ldpc_decoding_stats,"ULSCH ldpc decoding"); + printf("\n"); + } + if(n_trials==1) break; diff --git a/openair2/ENB_APP/CONTROL_MODULES/MAC/flexran_agent_mac.c b/openair2/ENB_APP/CONTROL_MODULES/MAC/flexran_agent_mac.c index c489f10dae1f23090cdf94e62e310fb8b5628770..975ac4e96ff5ae3c2492c7a374bcd5359f56a517 100644 --- a/openair2/ENB_APP/CONTROL_MODULES/MAC/flexran_agent_mac.c +++ b/openair2/ENB_APP/CONTROL_MODULES/MAC/flexran_agent_mac.c @@ -939,7 +939,7 @@ int flexran_agent_mac_sf_trigger(mid_t mod_id, const void *params, Protocol__Fle for (i = 0; i < MAX_MOBILES_PER_ENB; i++) { for (j = 0; j < 8; j++) { - if (RC.mac && RC.mac[mod_id] && RC.mac[mod_id]->UE_list.eNB_UE_stats[UE_PCCID(mod_id,i)][i].harq_pid == 1) { + if (RC.mac && RC.mac[mod_id] && RC.mac[mod_id]->UE_info.eNB_UE_stats[UE_PCCID(mod_id,i)][i].harq_pid == 1) { available_harq[i] = j; break; } @@ -977,13 +977,13 @@ int flexran_agent_mac_sf_trigger(mid_t mod_id, const void *params, Protocol__Fle dl_info[i]->harq_process_id = available_harq[UE_id]; if (RC.mac && RC.mac[mod_id]) - RC.mac[mod_id]->UE_list.eNB_UE_stats[UE_PCCID(mod_id, UE_id)][UE_id].harq_pid = 0; + RC.mac[mod_id]->UE_info.eNB_UE_stats[UE_PCCID(mod_id, UE_id)][UE_id].harq_pid = 0; dl_info[i]->has_harq_process_id = 1; /* Fill in the status of the HARQ process (2 TBs)*/ dl_info[i]->n_harq_status = 2; dl_info[i]->harq_status = malloc(sizeof(uint32_t) * dl_info[i]->n_harq_status); for (j = 0; j < dl_info[i]->n_harq_status; j++) { - dl_info[i]->harq_status[j] = RC.mac[mod_id]->UE_list.UE_sched_ctrl[UE_id].round[UE_PCCID(mod_id, UE_id)][j]; + dl_info[i]->harq_status[j] = RC.mac[mod_id]->UE_info.UE_sched_ctrl[UE_id].round[UE_PCCID(mod_id, UE_id)][j]; // TODO: This should be different per TB } // LOG_I(FLEXRAN_AGENT, "Sending subframe trigger for frame %d and subframe %d and harq %d (round %d)\n", flexran_get_current_frame(mod_id), (flexran_get_current_subframe(mod_id) + 1) % 10, dl_info[i]->harq_process_id, dl_info[i]->harq_status[0]); @@ -1357,7 +1357,7 @@ void flexran_agent_init_mac_agent(mid_t mod_id) { for (i = 0; i < MAX_MOBILES_PER_ENB; i++) { for (j = 0; j < 8; j++) { if (RC.mac && RC.mac[mod_id]) - RC.mac[mod_id]->UE_list.eNB_UE_stats[UE_PCCID(mod_id,i)][i].harq_pid = 0; + RC.mac[mod_id]->UE_info.eNB_UE_stats[UE_PCCID(mod_id,i)][i].harq_pid = 0; } } } diff --git a/openair2/ENB_APP/enb_paramdef.h b/openair2/ENB_APP/enb_paramdef.h index f91c7056c5935790b2d2a9faf0cc386bbc243128..344214a1f176bb56686619eb2238b1bd930530d5 100644 --- a/openair2/ENB_APP/enb_paramdef.h +++ b/openair2/ENB_APP/enb_paramdef.h @@ -90,6 +90,7 @@ typedef enum { #define CONFIG_STRING_RU_NBIOTRRC_LIST "NbIoT_RRC_instances" #define CONFIG_STRING_RU_SDR_ADDRS "sdr_addrs" #define CONFIG_STRING_RU_SDR_CLK_SRC "clock_src" +#define CONFIG_STRING_RU_SDR_TME_SRC "time_src" #define CONFIG_STRING_RU_SF_EXTENSION "sf_extension" #define CONFIG_STRING_RU_END_OF_BURST_DELAY "end_of_burst_delay" #define CONFIG_STRING_RU_OTA_SYNC_ENABLE "ota_sync_enabled" @@ -117,11 +118,12 @@ typedef enum { #define RU_NBIOTRRC_LIST_IDX 18 #define RU_SDR_ADDRS 19 #define RU_SDR_CLK_SRC 20 -#define RU_SF_EXTENSION_IDX 21 -#define RU_END_OF_BURST_DELAY_IDX 22 -#define RU_OTA_SYNC_ENABLE_IDX 23 -#define RU_BF_WEIGHTS_LIST_IDX 24 -#define RU_IF_FREQUENCY 25 +#define RU_SDR_TME_SRC 21 +#define RU_SF_EXTENSION_IDX 22 +#define RU_END_OF_BURST_DELAY_IDX 23 +#define RU_OTA_SYNC_ENABLE_IDX 24 +#define RU_BF_WEIGHTS_LIST_IDX 25 +#define RU_IF_FREQUENCY 26 /*-----------------------------------------------------------------------------------------------------------------------------------------*/ /* RU configuration parameters */ @@ -149,6 +151,7 @@ typedef enum { {CONFIG_STRING_RU_NBIOTRRC_LIST, NULL, 0, uptr:NULL, defintarrayval:DEFENBS, TYPE_INTARRAY, 1}, \ {CONFIG_STRING_RU_SDR_ADDRS, NULL, 0, strptr:NULL, defstrval:"type=b200", TYPE_STRING, 0}, \ {CONFIG_STRING_RU_SDR_CLK_SRC, NULL, 0, strptr:NULL, defstrval:"internal", TYPE_STRING, 0}, \ + {CONFIG_STRING_RU_SDR_TME_SRC, NULL, 0, strptr:NULL, defstrval:"internal", TYPE_STRING, 0}, \ {CONFIG_STRING_RU_SF_EXTENSION, NULL, 0, uptr:NULL, defuintval:312, TYPE_UINT, 0}, \ {CONFIG_STRING_RU_END_OF_BURST_DELAY, NULL, 0, uptr:NULL, defuintval:400, TYPE_UINT, 0}, \ {CONFIG_STRING_RU_OTA_SYNC_ENABLE, NULL, 0, strptr:NULL, defstrval:"no", TYPE_STRING, 0}, \ diff --git a/openair2/ENB_APP/flexran_agent_ran_api.c b/openair2/ENB_APP/flexran_agent_ran_api.c index a66081d99f236bdb378a5a887e9ca8835998e3aa..32cb8c74e18d0cde3f657a4dd4e8246ae752ccfe 100644 --- a/openair2/ENB_APP/flexran_agent_ran_api.c +++ b/openair2/ENB_APP/flexran_agent_ran_api.c @@ -98,7 +98,7 @@ uint16_t flexran_get_future_sfn_sf(mid_t mod_id, int ahead_of_time) { int flexran_get_mac_num_ues(mid_t mod_id) { if (!mac_is_present(mod_id)) return 0; - return RC.mac[mod_id]->UE_list.num_UEs; + return RC.mac[mod_id]->UE_info.num_UEs; } int flexran_get_num_ue_lcs(mid_t mod_id, mid_t ue_id) { @@ -123,7 +123,7 @@ int flexran_get_mac_ue_id_rnti(mid_t mod_id, rnti_t rnti) { /* get the (active) UE with RNTI i */ for (n = 0; n < MAX_MOBILES_PER_ENB; ++n) { - if (RC.mac[mod_id]->UE_list.active[n] == TRUE + if (RC.mac[mod_id]->UE_info.active[n] == TRUE && rnti == UE_RNTI(mod_id, n)) { return n; } @@ -139,7 +139,7 @@ int flexran_get_mac_ue_id(mid_t mod_id, int i) { /* get the (i+1)'th active UE */ for (n = 0; n < MAX_MOBILES_PER_ENB; ++n) { - if (RC.mac[mod_id]->UE_list.active[n] == TRUE) { + if (RC.mac[mod_id]->UE_info.active[n] == TRUE) { if (i == 0) return n; @@ -159,19 +159,19 @@ rnti_t flexran_get_mac_ue_crnti(mid_t mod_id, mid_t ue_id) { int flexran_get_ue_bsr_ul_buffer_info(mid_t mod_id, mid_t ue_id, lcid_t lcid) { if (!mac_is_present(mod_id)) return -1; - return RC.mac[mod_id]->UE_list.UE_template[UE_PCCID(mod_id, ue_id)][ue_id].ul_buffer_info[lcid]; + return RC.mac[mod_id]->UE_info.UE_template[UE_PCCID(mod_id, ue_id)][ue_id].ul_buffer_info[lcid]; } int8_t flexran_get_ue_phr(mid_t mod_id, mid_t ue_id) { if (!mac_is_present(mod_id)) return 0; - return RC.mac[mod_id]->UE_list.UE_template[UE_PCCID(mod_id, ue_id)][ue_id].phr_info; + return RC.mac[mod_id]->UE_info.UE_template[UE_PCCID(mod_id, ue_id)][ue_id].phr_info; } uint8_t flexran_get_ue_wcqi(mid_t mod_id, mid_t ue_id) { if (!mac_is_present(mod_id)) return 0; - return RC.mac[mod_id]->UE_list.UE_sched_ctrl[ue_id].dl_cqi[0]; + return RC.mac[mod_id]->UE_info.UE_sched_ctrl[ue_id].dl_cqi[0]; } rlc_buffer_occupancy_t flexran_get_tx_queue_size(mid_t mod_id, mid_t ue_id, logical_chan_id_t channel_id) { @@ -180,7 +180,7 @@ rlc_buffer_occupancy_t flexran_get_tx_queue_size(mid_t mod_id, mid_t ue_id, logi rnti_t rnti = flexran_get_mac_ue_crnti(mod_id, ue_id); frame_t frame = flexran_get_current_frame(mod_id); sub_frame_t subframe = flexran_get_current_subframe(mod_id); - mac_rlc_status_resp_t rlc_status = mac_rlc_status_ind(mod_id,rnti, mod_id, frame, subframe, ENB_FLAG_YES,MBMS_FLAG_NO, channel_id, 0,0, 0 + mac_rlc_status_resp_t rlc_status = mac_rlc_status_ind(mod_id,rnti, mod_id, frame, subframe, ENB_FLAG_YES,MBMS_FLAG_NO, channel_id, 0, 0 ); return rlc_status.bytes_in_buffer; } @@ -191,7 +191,7 @@ rlc_buffer_occupancy_t flexran_get_num_pdus_buffer(mid_t mod_id, mid_t ue_id, lo rnti_t rnti = flexran_get_mac_ue_crnti(mod_id,ue_id); frame_t frame = flexran_get_current_frame(mod_id); sub_frame_t subframe = flexran_get_current_subframe(mod_id); - mac_rlc_status_resp_t rlc_status = mac_rlc_status_ind(mod_id,rnti, mod_id, frame, subframe, ENB_FLAG_YES,MBMS_FLAG_NO, channel_id, 0,0, 0 + mac_rlc_status_resp_t rlc_status = mac_rlc_status_ind(mod_id,rnti, mod_id, frame, subframe, ENB_FLAG_YES,MBMS_FLAG_NO, channel_id, 0, 0 ); return rlc_status.pdus_in_buffer; } @@ -202,7 +202,7 @@ frame_t flexran_get_hol_delay(mid_t mod_id, mid_t ue_id, logical_chan_id_t chann rnti_t rnti = flexran_get_mac_ue_crnti(mod_id,ue_id); frame_t frame = flexran_get_current_frame(mod_id); sub_frame_t subframe = flexran_get_current_subframe(mod_id); - mac_rlc_status_resp_t rlc_status = mac_rlc_status_ind(mod_id, rnti, mod_id, frame, subframe, ENB_FLAG_YES, MBMS_FLAG_NO, channel_id, 0,0, 0 + mac_rlc_status_resp_t rlc_status = mac_rlc_status_ind(mod_id, rnti, mod_id, frame, subframe, ENB_FLAG_YES, MBMS_FLAG_NO, channel_id, 0, 0 ); return rlc_status.head_sdu_creation_time; } @@ -242,7 +242,7 @@ int32_t flexran_get_TA(mid_t mod_id, mid_t ue_id, uint8_t cc_id) { uint32_t flexran_get_total_size_dl_mac_sdus(mid_t mod_id, mid_t ue_id, int cc_id) { if (!mac_is_present(mod_id)) return 0; - return RC.mac[mod_id]->UE_list.eNB_UE_stats[cc_id][ue_id].total_sdu_bytes; + return RC.mac[mod_id]->UE_info.eNB_UE_stats[cc_id][ue_id].total_sdu_bytes; } uint32_t flexran_get_total_size_ul_mac_sdus(mid_t mod_id, mid_t ue_id, int cc_id) { @@ -251,7 +251,7 @@ uint32_t flexran_get_total_size_ul_mac_sdus(mid_t mod_id, mid_t ue_id, int cc_id uint64_t bytes = 0; for (int i = 0; i < NB_RB_MAX; ++i) { - bytes += RC.mac[mod_id]->UE_list.eNB_UE_stats[cc_id][ue_id].num_bytes_rx[i]; + bytes += RC.mac[mod_id]->UE_info.eNB_UE_stats[cc_id][ue_id].num_bytes_rx[i]; } return bytes; @@ -260,135 +260,135 @@ uint32_t flexran_get_total_size_ul_mac_sdus(mid_t mod_id, mid_t ue_id, int cc_id uint32_t flexran_get_TBS_dl(mid_t mod_id, mid_t ue_id, int cc_id) { if (!mac_is_present(mod_id)) return 0; - return RC.mac[mod_id]->UE_list.eNB_UE_stats[cc_id][ue_id].TBS; + return RC.mac[mod_id]->UE_info.eNB_UE_stats[cc_id][ue_id].TBS; } uint32_t flexran_get_TBS_ul(mid_t mod_id, mid_t ue_id, int cc_id) { if (!mac_is_present(mod_id)) return 0; - return RC.mac[mod_id]->UE_list.eNB_UE_stats[cc_id][ue_id].ulsch_TBS; + return RC.mac[mod_id]->UE_info.eNB_UE_stats[cc_id][ue_id].ulsch_TBS; } uint16_t flexran_get_num_prb_retx_dl_per_ue(mid_t mod_id, mid_t ue_id, int cc_id) { if (!mac_is_present(mod_id)) return 0; - return RC.mac[mod_id]->UE_list.eNB_UE_stats[cc_id][ue_id].rbs_used_retx; + return RC.mac[mod_id]->UE_info.eNB_UE_stats[cc_id][ue_id].rbs_used_retx; } uint32_t flexran_get_num_prb_retx_ul_per_ue(mid_t mod_id, mid_t ue_id, int cc_id) { if (!mac_is_present(mod_id)) return 0; - return RC.mac[mod_id]->UE_list.eNB_UE_stats[cc_id][ue_id].rbs_used_retx_rx; + return RC.mac[mod_id]->UE_info.eNB_UE_stats[cc_id][ue_id].rbs_used_retx_rx; } uint16_t flexran_get_num_prb_dl_tx_per_ue(mid_t mod_id, mid_t ue_id, int cc_id) { if (!mac_is_present(mod_id)) return 0; - return RC.mac[mod_id]->UE_list.eNB_UE_stats[cc_id][ue_id].rbs_used; + return RC.mac[mod_id]->UE_info.eNB_UE_stats[cc_id][ue_id].rbs_used; } uint16_t flexran_get_num_prb_ul_rx_per_ue(mid_t mod_id, mid_t ue_id, int cc_id) { if (!mac_is_present(mod_id)) return 0; - return RC.mac[mod_id]->UE_list.eNB_UE_stats[cc_id][ue_id].rbs_used_rx; + return RC.mac[mod_id]->UE_info.eNB_UE_stats[cc_id][ue_id].rbs_used_rx; } uint8_t flexran_get_ue_wpmi(mid_t mod_id, mid_t ue_id, uint8_t cc_id) { if (!mac_is_present(mod_id)) return 0; - return RC.mac[mod_id]->UE_list.UE_sched_ctrl[ue_id].periodic_wideband_pmi[cc_id]; + return RC.mac[mod_id]->UE_info.UE_sched_ctrl[ue_id].periodic_wideband_pmi[cc_id]; } uint8_t flexran_get_mcs1_dl(mid_t mod_id, mid_t ue_id, int cc_id) { if (!mac_is_present(mod_id)) return 0; - return RC.mac[mod_id]->UE_list.eNB_UE_stats[cc_id][ue_id].dlsch_mcs1; + return RC.mac[mod_id]->UE_info.eNB_UE_stats[cc_id][ue_id].dlsch_mcs1; } uint8_t flexran_get_mcs2_dl(mid_t mod_id, mid_t ue_id, int cc_id) { if (!mac_is_present(mod_id)) return 0; - return RC.mac[mod_id]->UE_list.eNB_UE_stats[cc_id][ue_id].dlsch_mcs2; + return RC.mac[mod_id]->UE_info.eNB_UE_stats[cc_id][ue_id].dlsch_mcs2; } uint8_t flexran_get_mcs1_ul(mid_t mod_id, mid_t ue_id, int cc_id) { if (!mac_is_present(mod_id)) return 0; - return RC.mac[mod_id]->UE_list.eNB_UE_stats[cc_id][ue_id].ulsch_mcs1; + return RC.mac[mod_id]->UE_info.eNB_UE_stats[cc_id][ue_id].ulsch_mcs1; } uint8_t flexran_get_mcs2_ul(mid_t mod_id, mid_t ue_id, int cc_id) { if (!mac_is_present(mod_id)) return 0; - return RC.mac[mod_id]->UE_list.eNB_UE_stats[cc_id][ue_id].ulsch_mcs2; + return RC.mac[mod_id]->UE_info.eNB_UE_stats[cc_id][ue_id].ulsch_mcs2; } uint32_t flexran_get_total_prb_dl_tx_per_ue(mid_t mod_id, mid_t ue_id, int cc_id) { if (!mac_is_present(mod_id)) return 0; - return RC.mac[mod_id]->UE_list.eNB_UE_stats[cc_id][ue_id].total_rbs_used; + return RC.mac[mod_id]->UE_info.eNB_UE_stats[cc_id][ue_id].total_rbs_used; } uint32_t flexran_get_total_prb_ul_rx_per_ue(mid_t mod_id, mid_t ue_id, int cc_id) { if (!mac_is_present(mod_id)) return 0; - return RC.mac[mod_id]->UE_list.eNB_UE_stats[cc_id][ue_id].total_rbs_used_rx; + return RC.mac[mod_id]->UE_info.eNB_UE_stats[cc_id][ue_id].total_rbs_used_rx; } uint32_t flexran_get_total_num_pdu_dl(mid_t mod_id, mid_t ue_id, int cc_id) { if (!mac_is_present(mod_id)) return 0; - return RC.mac[mod_id]->UE_list.eNB_UE_stats[cc_id][ue_id].total_num_pdus; + return RC.mac[mod_id]->UE_info.eNB_UE_stats[cc_id][ue_id].total_num_pdus; } uint32_t flexran_get_total_num_pdu_ul(mid_t mod_id, mid_t ue_id, int cc_id) { if (!mac_is_present(mod_id)) return 0; - return RC.mac[mod_id]->UE_list.eNB_UE_stats[cc_id][ue_id].total_num_pdus_rx; + return RC.mac[mod_id]->UE_info.eNB_UE_stats[cc_id][ue_id].total_num_pdus_rx; } uint64_t flexran_get_total_TBS_dl(mid_t mod_id, mid_t ue_id, int cc_id) { if (!mac_is_present(mod_id)) return 0; - return RC.mac[mod_id]->UE_list.eNB_UE_stats[cc_id][ue_id].total_pdu_bytes; + return RC.mac[mod_id]->UE_info.eNB_UE_stats[cc_id][ue_id].total_pdu_bytes; } uint64_t flexran_get_total_TBS_ul(mid_t mod_id, mid_t ue_id, int cc_id) { if (!mac_is_present(mod_id)) return 0; - return RC.mac[mod_id]->UE_list.eNB_UE_stats[cc_id][ue_id].total_ulsch_TBS; + return RC.mac[mod_id]->UE_info.eNB_UE_stats[cc_id][ue_id].total_ulsch_TBS; } int flexran_get_harq_round(mid_t mod_id, uint8_t cc_id, mid_t ue_id) { if (!mac_is_present(mod_id)) return 0; - return RC.mac[mod_id]->UE_list.eNB_UE_stats[cc_id][ue_id].harq_round; + return RC.mac[mod_id]->UE_info.eNB_UE_stats[cc_id][ue_id].harq_round; } uint32_t flexran_get_num_mac_sdu_tx(mid_t mod_id, mid_t ue_id, int cc_id) { if (!mac_is_present(mod_id)) return 0; - return RC.mac[mod_id]->UE_list.eNB_UE_stats[cc_id][ue_id].num_mac_sdu_tx; + return RC.mac[mod_id]->UE_info.eNB_UE_stats[cc_id][ue_id].num_mac_sdu_tx; } unsigned char flexran_get_mac_sdu_lcid_index(mid_t mod_id, mid_t ue_id, int cc_id, int index) { if (!mac_is_present(mod_id)) return 0; - return RC.mac[mod_id]->UE_list.eNB_UE_stats[cc_id][ue_id].lcid_sdu[index]; + return RC.mac[mod_id]->UE_info.eNB_UE_stats[cc_id][ue_id].lcid_sdu[index]; } uint32_t flexran_get_mac_sdu_size(mid_t mod_id, mid_t ue_id, int cc_id, int lcid) { if (!mac_is_present(mod_id)) return 0; - return RC.mac[mod_id]->UE_list.eNB_UE_stats[cc_id][ue_id].sdu_length_tx[lcid]; + return RC.mac[mod_id]->UE_info.eNB_UE_stats[cc_id][ue_id].sdu_length_tx[lcid]; } /* TODO needs to be revised */ void flexran_update_TA(mid_t mod_id, mid_t ue_id, uint8_t cc_id) { /* - UE_list_t *UE_list=&eNB_mac_inst[mod_id].UE_list; - UE_sched_ctrl *ue_sched_ctl = &UE_list->UE_sched_ctrl[ue_id]; + UE_info_t *UE_info=&eNB_mac_inst[mod_id].UE_info; + UE_sched_ctrl *ue_sched_ctl = &UE_info->UE_sched_ctrl[ue_id]; if (ue_sched_ctl->ta_timer == 0) { @@ -432,7 +432,7 @@ int flexran_get_MAC_CE_bitmap_TA(mid_t mod_id, mid_t ue_id, uint8_t cc_id) { int flexran_get_active_CC(mid_t mod_id, mid_t ue_id) { if (!mac_is_present(mod_id)) return 0; - return RC.mac[mod_id]->UE_list.numactiveCCs[ue_id]; + return RC.mac[mod_id]->UE_info.numactiveCCs[ue_id]; } uint8_t flexran_get_current_RI(mid_t mod_id, mid_t ue_id, uint8_t cc_id) { @@ -890,13 +890,13 @@ uint8_t flexran_get_rrc_status(mid_t mod_id, rnti_t rnti) { uint64_t flexran_get_ue_aggregated_max_bitrate_dl(mid_t mod_id, mid_t ue_id) { if (!mac_is_present(mod_id)) return 0; - return RC.mac[mod_id]->UE_list.UE_sched_ctrl[ue_id].ue_AggregatedMaximumBitrateDL; + return 0; //RC.mac[mod_id]->UE_info.UE_sched_ctrl[ue_id].ue_AggregatedMaximumBitrateDL; } uint64_t flexran_get_ue_aggregated_max_bitrate_ul(mid_t mod_id, mid_t ue_id) { if (!mac_is_present(mod_id)) return 0; - return RC.mac[mod_id]->UE_list.UE_sched_ctrl[ue_id].ue_AggregatedMaximumBitrateUL; + return 0; //RC.mac[mod_id]->UE_info.UE_sched_ctrl[ue_id].ue_AggregatedMaximumBitrateUL; } int flexran_get_half_duplex(mid_t mod_id, rnti_t rnti) { @@ -1235,7 +1235,7 @@ uint64_t flexran_get_ue_imsi(mid_t mod_id, rnti_t rnti) { long flexran_get_lcg(mid_t mod_id, mid_t ue_id, mid_t lc_id) { if (!mac_is_present(mod_id)) return 0; - return RC.mac[mod_id]->UE_list.UE_template[UE_PCCID(mod_id, ue_id)][ue_id].lcgidmap[lc_id]; + return RC.mac[mod_id]->UE_info.UE_template[UE_PCCID(mod_id, ue_id)][ue_id].lcgidmap[lc_id]; } /* TODO Navid: needs to be revised */ @@ -3016,7 +3016,7 @@ uint32_t flexran_get_rrc_enb_ue_s1ap_id(mid_t mod_id, rnti_t rnti) int flexran_get_ue_dl_slice_id(mid_t mod_id, mid_t ue_id) { if (!mac_is_present(mod_id)) return -1; - int slice_idx = RC.mac[mod_id]->UE_list.assoc_dl_slice_idx[ue_id]; + int slice_idx = 0; //RC.mac[mod_id]->UE_info.assoc_dl_slice_idx[ue_id]; if (slice_idx >= 0 && slice_idx < RC.mac[mod_id]->slice_info.n_dl) return RC.mac[mod_id]->slice_info.dl[slice_idx].id; @@ -3031,13 +3031,13 @@ void flexran_set_ue_dl_slice_idx(mid_t mod_id, mid_t ue_id, int slice_idx) { if (!flexran_dl_slice_exists(mod_id, slice_idx)) return; - RC.mac[mod_id]->UE_list.assoc_dl_slice_idx[ue_id] = slice_idx; + //RC.mac[mod_id]->UE_info.assoc_dl_slice_idx[ue_id] = slice_idx; } int flexran_get_ue_ul_slice_id(mid_t mod_id, mid_t ue_id) { if (!mac_is_present(mod_id)) return -1; - int slice_idx = RC.mac[mod_id]->UE_list.assoc_ul_slice_idx[ue_id]; + int slice_idx = 0; //RC.mac[mod_id]->UE_info.assoc_ul_slice_idx[ue_id]; if (slice_idx >= 0 && slice_idx < RC.mac[mod_id]->slice_info.n_ul) return RC.mac[mod_id]->slice_info.ul[slice_idx].id; @@ -3052,7 +3052,7 @@ void flexran_set_ue_ul_slice_idx(mid_t mod_id, mid_t ue_id, int slice_idx) { if (!flexran_ul_slice_exists(mod_id, slice_idx)) return; - RC.mac[mod_id]->UE_list.assoc_ul_slice_idx[ue_id] = slice_idx; + //RC.mac[mod_id]->UE_info.assoc_ul_slice_idx[ue_id] = slice_idx; } int flexran_dl_slice_exists(mid_t mod_id, int slice_idx) { @@ -3103,14 +3103,14 @@ int flexran_remove_dl_slice(mid_t mod_id, int slice_idx) { memset(&sli->dl[sli->n_dl], 0, sizeof(sli->dl[sli->n_dl])); /* all UEs that have been in the old slice are put into slice index 0 */ - int *assoc_list = RC.mac[mod_id]->UE_list.assoc_dl_slice_idx; + //int *assoc_list = RC.mac[mod_id]->UE_info.assoc_dl_slice_idx; - for (int i = 0; i < MAX_MOBILES_PER_ENB; ++i) { - if (assoc_list[i] == slice_idx) - assoc_list[i] = 0; - } + //for (int i = 0; i < MAX_MOBILES_PER_ENB; ++i) { + // if (assoc_list[i] == slice_idx) + // assoc_list[i] = 0; + //} - return sli->n_dl; + return 1; } int flexran_get_num_dl_slices(mid_t mod_id) { @@ -3397,12 +3397,12 @@ int flexran_remove_ul_slice(mid_t mod_id, int slice_idx) { memset(&sli->ul[sli->n_ul], 0, sizeof(sli->ul[sli->n_ul])); /* all UEs that have been in the old slice are put into slice index 0 */ - int *assoc_list = RC.mac[mod_id]->UE_list.assoc_ul_slice_idx; + //int *assoc_list = RC.mac[mod_id]->UE_info.assoc_ul_slice_idx; - for (int i = 0; i < MAX_MOBILES_PER_ENB; ++i) { - if (assoc_list[i] == slice_idx) - assoc_list[i] = 0; - } + //for (int i = 0; i < MAX_MOBILES_PER_ENB; ++i) { + // if (assoc_list[i] == slice_idx) + // assoc_list[i] = 0; + //} return sli->n_ul; } diff --git a/openair2/F1AP/f1ap_cu_ue_context_management.c b/openair2/F1AP/f1ap_cu_ue_context_management.c index edc5a2c0a9a30f0091a4345b8ad9db495493ff42..a64f2d529b302b99338d2f6e6b9b2097d46443fe 100644 --- a/openair2/F1AP/f1ap_cu_ue_context_management.c +++ b/openair2/F1AP/f1ap_cu_ue_context_management.c @@ -37,7 +37,6 @@ #include "f1ap_cu_ue_context_management.h" #include <string.h> -#include "openair2/LAYER2/MAC/mac_proto.h" #include "rrc_extern.h" #include "rrc_eNB_UE_context.h" #include "rrc_eNB_S1AP.h" diff --git a/openair2/F1AP/f1ap_du_rrc_message_transfer.c b/openair2/F1AP/f1ap_du_rrc_message_transfer.c index 803551818ae8a76c9c613311ea12a38bbcc702e7..fb9450728b40dada6301df9be74b61c1d3289886 100644 --- a/openair2/F1AP/f1ap_du_rrc_message_transfer.c +++ b/openair2/F1AP/f1ap_du_rrc_message_transfer.c @@ -697,7 +697,7 @@ int DU_send_UL_RRC_MESSAGE_TRANSFER(instance_t instance, break; } - UE_sched_ctrl_t *UE_scheduling_control = &(RC.mac[instance]->UE_list.UE_sched_ctrl[UE_id_mac]); + UE_sched_ctrl_t *UE_scheduling_control = &(RC.mac[instance]->UE_info.UE_sched_ctrl[UE_id_mac]); if (UE_scheduling_control->cdrx_waiting_ack == TRUE) { UE_scheduling_control->cdrx_waiting_ack = FALSE; diff --git a/openair2/F1AP/f1ap_du_ue_context_management.c b/openair2/F1AP/f1ap_du_ue_context_management.c index b9c79e1f18ac7c941aa5373639bbf983274539da..bae59a509e24bf1edb33497df39dac5ad309025c 100644 --- a/openair2/F1AP/f1ap_du_ue_context_management.c +++ b/openair2/F1AP/f1ap_du_ue_context_management.c @@ -633,9 +633,9 @@ int DU_handle_UE_CONTEXT_RELEASE_COMMAND(instance_t instance, int UE_out_of_sync = 0; for (int n = 0; n < MAX_MOBILES_PER_ENB; ++n) { - if (RC.mac[instance]->UE_list.active[n] == TRUE + if (RC.mac[instance]->UE_info.active[n] == TRUE && rnti == UE_RNTI(instance, n)) { - UE_out_of_sync = RC.mac[instance]->UE_list.UE_sched_ctrl[n].ul_out_of_sync; + UE_out_of_sync = RC.mac[instance]->UE_info.UE_sched_ctrl[n].ul_out_of_sync; break; } } diff --git a/openair2/LAYER2/MAC/config.c b/openair2/LAYER2/MAC/config.c index 76c8e33b168c34ba1319e665aeff97ecdb8c728f..49949bd771b119447a1694755a1a80455644d7b3 100644 --- a/openair2/LAYER2/MAC/config.c +++ b/openair2/LAYER2/MAC/config.c @@ -782,7 +782,7 @@ int rrc_mac_config_req_eNB(module_id_t Mod_idP, int i; int UE_id = -1; eNB_MAC_INST *eNB = RC.mac[Mod_idP]; - UE_list_t *UE_list= &eNB->UE_list; + UE_info_t *UE_info= &eNB->UE_info; VCD_SIGNAL_DUMPER_DUMP_FUNCTION_BY_NAME(VCD_SIGNAL_DUMPER_FUNCTIONS_RRC_MAC_CONFIG, VCD_FUNCTION_IN); LOG_D(MAC, "RC.mac:%p mib:%p\n", RC.mac, mib); @@ -882,6 +882,34 @@ int rrc_mac_config_req_eNB(module_id_t Mod_idP, } } + if (logicalChannelIdentity > 0) { // is SRB1,2 or DRB + if ((UE_id = find_UE_id(Mod_idP, rntiP)) < 0) { + LOG_E(MAC,"Configuration received for unknown UE (%x), shouldn't happen\n",rntiP); + return(-1); + } + int idx = -1; + UE_sched_ctrl_t *sched_ctrl = &UE_info->UE_sched_ctrl[UE_id]; + for (int i = 0; i < sched_ctrl->dl_lc_num; ++i) { + if (sched_ctrl->dl_lc_ids[i] == logicalChannelIdentity) { + /* TODO this might also mean we have to remove it, not clear */ + idx = i; + break; + } + } + if (idx < 0) { + sched_ctrl->dl_lc_num++; + sched_ctrl->dl_lc_ids[sched_ctrl->dl_lc_num-1] = logicalChannelIdentity; + sched_ctrl->dl_lc_bytes[sched_ctrl->dl_lc_num-1] = 0; + LOG_I(MAC, "UE %d RNTI %x adding LC %ld idx %d to scheduling control (total %d)\n", UE_id, rntiP, logicalChannelIdentity, sched_ctrl->dl_lc_num-1, sched_ctrl->dl_lc_num); + if (logicalChannelIdentity == 1) { // if it is SRB1, add SRB2 directly because RRC does not indicate this separately + sched_ctrl->dl_lc_num++; + sched_ctrl->dl_lc_ids[sched_ctrl->dl_lc_num-1] = 2; + sched_ctrl->dl_lc_bytes[sched_ctrl->dl_lc_num-1] = 0; + LOG_I(MAC, "UE %d RNTI %x adding LC 2 idx %d to scheduling control (total %d)\n", UE_id, rntiP, sched_ctrl->dl_lc_num-1, sched_ctrl->dl_lc_num); + } + } + } + // SRB2_lchan_config->choice.explicitValue.ul_SpecificParameters->logicalChannelGroup if (logicalChannelConfig != NULL) { // check for eMTC specific things UE_id = find_UE_id(Mod_idP, rntiP); @@ -892,9 +920,9 @@ int rrc_mac_config_req_eNB(module_id_t Mod_idP, } if (logicalChannelConfig) { - UE_list->UE_template[CC_idP][UE_id].lcgidmap[logicalChannelIdentity] = *logicalChannelConfig->ul_SpecificParameters->logicalChannelGroup; - UE_list->UE_template[CC_idP][UE_id].lcgidpriority[logicalChannelIdentity] = logicalChannelConfig->ul_SpecificParameters->priority; - } else UE_list->UE_template[CC_idP][UE_id].lcgidmap[logicalChannelIdentity] = 0; + UE_info->UE_template[CC_idP][UE_id].lcgidmap[logicalChannelIdentity] = *logicalChannelConfig->ul_SpecificParameters->logicalChannelGroup; + UE_info->UE_template[CC_idP][UE_id].lcgidpriority[logicalChannelIdentity] = logicalChannelConfig->ul_SpecificParameters->priority; + } else UE_info->UE_template[CC_idP][UE_id].lcgidmap[logicalChannelIdentity] = 0; } if (physicalConfigDedicated != NULL) { @@ -905,7 +933,7 @@ int rrc_mac_config_req_eNB(module_id_t Mod_idP, return(-1); } - UE_list->UE_template[CC_idP][UE_id].physicalConfigDedicated = physicalConfigDedicated; + UE_info->UE_template[CC_idP][UE_id].physicalConfigDedicated = physicalConfigDedicated; LOG_I(MAC,"Added physicalConfigDedicated %p for %d.%d\n",physicalConfigDedicated,CC_idP,UE_id); } @@ -1048,15 +1076,11 @@ void eNB_Config_Local_DRX(instance_t Mod_id, rrc_mac_drx_config_req_t *rrc_mac_drx_config_req) //----------------------------------------------------------------------------- { - UE_list_t *UE_list_mac = NULL; + UE_info_t *UE_info_mac = &RC.mac[Mod_id]->UE_info; UE_sched_ctrl_t *UE_scheduling_control = NULL; - int UE_id = -1; - - rnti_t rnti = rrc_mac_drx_config_req->rnti; LTE_DRX_Config_t *const drx_Configuration = rrc_mac_drx_config_req->drx_Configuration; - - UE_list_mac = &(RC.mac[Mod_id]->UE_list); - UE_id = find_UE_id(Mod_id, rnti); + rnti_t rnti = rrc_mac_drx_config_req->rnti; + int UE_id = find_UE_id(Mod_id, rnti); /* Check UE_id */ if (UE_id == -1) { @@ -1065,7 +1089,7 @@ void eNB_Config_Local_DRX(instance_t Mod_id, } /* Get struct to modify */ - UE_scheduling_control = &(UE_list_mac->UE_sched_ctrl[UE_id]); + UE_scheduling_control = &(UE_info_mac->UE_sched_ctrl[UE_id]); UE_scheduling_control->cdrx_configured = FALSE; // will be set to true when no error /* Check drx_Configuration */ diff --git a/openair2/LAYER2/MAC/defs.h b/openair2/LAYER2/MAC/defs.h deleted file mode 100644 index 05660b727e9f6c737b7e9a38e811c994a1871979..0000000000000000000000000000000000000000 --- a/openair2/LAYER2/MAC/defs.h +++ /dev/null @@ -1,1321 +0,0 @@ -/* - * 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 - */ - -/*! \file LAYER2/MAC/defs.h -* \brief MAC data structures, constant, and function prototype -* \author Navid Nikaein and Raymond Knopp -* \date 2011 -* \version 0.5 -* \email navid.nikaein@eurecom.fr - -*/ -/** @defgroup _oai2 openair2 Reference Implementation - * @ingroup _ref_implementation_ - * @{ - */ - -/*@}*/ - -#ifndef __LAYER2_MAC_DEFS_H__ -#define __LAYER2_MAC_DEFS_H__ - - - -#ifdef USER_MODE - #include <stdio.h> - #include <stdlib.h> - #include <string.h> -#endif - -//#include "COMMON/openair_defs.h" - - - -#include "PHY/defs.h" -#include "PHY/LTE_TRANSPORT/defs.h" -#include "COMMON/platform_constants.h" -#include "BCCH-BCH-Message.h" -#include "RadioResourceConfigCommon.h" -#include "RadioResourceConfigDedicated.h" -#include "MeasGapConfig.h" -#include "SchedulingInfoList.h" -#include "TDD-Config.h" -#include "RACH-ConfigCommon.h" -#include "MeasObjectToAddModList.h" -#include "MobilityControlInfo.h" -#include "MBSFN-AreaInfoList-r9.h" -#include "MBSFN-SubframeConfigList.h" -#include "PMCH-InfoList-r9.h" -#include "SCellToAddMod-r10.h" -#include "SystemInformationBlockType1-v1310-IEs.h" - - -#include "nfapi_interface.h" -#include "PHY_INTERFACE/IF_Module.h" - -/** @defgroup _mac MAC - * @ingroup _oai2 - * @{ - */ - -#define BCCH_PAYLOAD_SIZE_MAX 128 -#define CCCH_PAYLOAD_SIZE_MAX 128 -#define PCCH_PAYLOAD_SIZE_MAX 128 -#define RAR_PAYLOAD_SIZE_MAX 128 - -#define SCH_PAYLOAD_SIZE_MAX 4096 -/// Logical channel ids from 36-311 (Note BCCH is not specified in 36-311, uses the same as first DRB) - - -// Mask for identifying subframe for MBMS -#define MBSFN_TDD_SF3 0x80// for TDD -#define MBSFN_TDD_SF4 0x40 -#define MBSFN_TDD_SF7 0x20 -#define MBSFN_TDD_SF8 0x10 -#define MBSFN_TDD_SF9 0x08 -#define MBSFN_FDD_SF1 0x80// for FDD -#define MBSFN_FDD_SF2 0x40 -#define MBSFN_FDD_SF3 0x20 -#define MBSFN_FDD_SF6 0x10 -#define MBSFN_FDD_SF7 0x08 -#define MBSFN_FDD_SF8 0x04 - -#define MAX_MBSFN_AREA 8 -#define MAX_PMCH_perMBSFN 15 -/*!\brief MAX MCCH payload size */ -#define MCCH_PAYLOAD_SIZE_MAX 128 - - -#ifdef USER_MODE - #define printk printf -#endif //USER_MODE - -/*!\brief Maximum number of logical channl group IDs */ -#define MAX_NUM_LCGID 4 -/*!\brief logical channl group ID 0 */ -#define LCGID0 0 -/*!\brief logical channl group ID 1 */ -#define LCGID1 1 -/*!\brief logical channl group ID 2 */ -#define LCGID2 2 -/*!\brief logical channl group ID 3 */ -#define LCGID3 3 -/*!\brief Maximum number of logical chanels */ -#define MAX_NUM_LCID 11 -/*!\brief Maximum number od control elemenets */ -#define MAX_NUM_CE 5 -/*!\brief Maximum number of random access process */ -#define NB_RA_PROC_MAX 4 -/*!\brief size of buffer status report table */ -#define BSR_TABLE_SIZE 64 -/*!\brief The power headroom reporting range is from -23 ...+40 dB and beyond, with step 1 */ -#define PHR_MAPPING_OFFSET 23 // if ( x>= -23 ) val = floor (x + 23) -/*!\brief maximum number of resource block groups */ -#define N_RBG_MAX 25 // for 20MHz channel BW -/*!\brief minimum value for channel quality indicator */ -#define MIN_CQI_VALUE 0 -/*!\brief maximum value for channel quality indicator */ -#define MAX_CQI_VALUE 15 -/*!\briefmaximum number of supported bandwidth (1.4, 5, 10, 20 MHz) */ -#define MAX_SUPPORTED_BW 4 -/*!\brief CQI values range from 1 to 15 (4 bits) */ -#define CQI_VALUE_RANGE 16 - -/*!\brief value for indicating BSR Timer is not running */ -#define MAC_UE_BSR_TIMER_NOT_RUNNING (0xFFFF) - -#define LCID_EMPTY 0 -#define LCID_NOT_EMPTY 1 - -/*!\brief minimum RLC PDU size to be transmitted = min RLC Status PDU or RLC UM PDU SN 5 bits */ -#define MIN_RLC_PDU_SIZE (2) - -/*!\brief minimum MAC data needed for transmitting 1 min RLC PDU size + 1 byte MAC subHeader */ -#define MIN_MAC_HDR_RLC_SIZE (1 + MIN_RLC_PDU_SIZE) - -/*!\brief maximum number of slices / groups */ -#define MAX_NUM_SLICES 4 - -/* - * eNB part - */ - - -/* - * UE/ENB common part - */ -/*!\brief MAC header of Random Access Response for Random access preamble identifier (RAPID) */ -typedef struct { - uint8_t RAPID:6; - uint8_t T:1; - uint8_t E:1; -} __attribute__((__packed__))RA_HEADER_RAPID; - -/*!\brief MAC header of Random Access Response for backoff indicator (BI)*/ -typedef struct { - uint8_t BI:4; - uint8_t R:2; - uint8_t T:1; - uint8_t E:1; -} __attribute__((__packed__))RA_HEADER_BI; -/* -typedef struct { - uint64_t padding:16; - uint64_t t_crnti:16; - uint64_t hopping_flag:1; - uint64_t rb_alloc:10; - uint64_t mcs:4; - uint64_t TPC:3; - uint64_t UL_delay:1; - uint64_t cqi_req:1; - uint64_t Timing_Advance_Command:11; // first/2nd octet LSB - uint64_t R:1; // octet MSB - } __attribute__((__packed__))RAR_PDU; - -typedef struct { - uint64_t padding:16; - uint64_t R:1; // octet MSB - uint64_t Timing_Advance_Command:11; // first/2nd octet LSB - uint64_t cqi_req:1; - uint64_t UL_delay:1; - uint64_t TPC:3; - uint64_t mcs:4; - uint64_t rb_alloc:10; - uint64_t hopping_flag:1; - uint64_t t_crnti:16; - } __attribute__((__packed__))RAR_PDU; - -#define sizeof_RAR_PDU 6 -*/ -/*!\brief MAC subheader short with 7bit Length field */ -typedef struct { - uint8_t LCID:5; // octet 1 LSB - uint8_t E:1; - uint8_t R:2; // octet 1 MSB - uint8_t L:7; // octet 2 LSB - uint8_t F:1; // octet 2 MSB -} __attribute__((__packed__))SCH_SUBHEADER_SHORT; -/*!\brief MAC subheader long with 15bit Length field */ -typedef struct { - uint8_t LCID:5; // octet 1 LSB - uint8_t E:1; - uint8_t R:2; // octet 1 MSB - uint8_t L_MSB:7; - uint8_t F:1; // octet 2 MSB - uint8_t L_LSB:8; - uint8_t padding; -} __attribute__((__packed__))SCH_SUBHEADER_LONG; -/*!\brief MAC subheader short without length field */ -typedef struct { - uint8_t LCID:5; - uint8_t E:1; - uint8_t R:2; -} __attribute__((__packed__))SCH_SUBHEADER_FIXED; - -/*!\brief mac control element: short buffer status report for a specific logical channel group ID*/ -typedef struct { - uint8_t Buffer_size:6; // octet 1 LSB - uint8_t LCGID:2; // octet 1 MSB -} __attribute__((__packed__))BSR_SHORT; - -typedef BSR_SHORT BSR_TRUNCATED; -/*!\brief mac control element: long buffer status report for all logical channel group ID*/ -typedef struct { - uint8_t Buffer_size3:6; - uint8_t Buffer_size2:6; - uint8_t Buffer_size1:6; - uint8_t Buffer_size0:6; -} __attribute__((__packed__))BSR_LONG; - -#define BSR_LONG_SIZE (sizeof(BSR_LONG)) -/*!\brief mac control element: timing advance */ -typedef struct { - uint8_t TA:6; - uint8_t R:2; -} __attribute__((__packed__))TIMING_ADVANCE_CMD; -/*!\brief mac control element: power headroom report */ -typedef struct { - uint8_t PH:6; - uint8_t R:2; -} __attribute__((__packed__))POWER_HEADROOM_CMD; - -/*! \brief MIB payload */ -typedef struct { - uint8_t payload[3] ; -} __attribute__((__packed__))MIB_PDU; -/*! \brief CCCH payload */ -typedef struct { - uint8_t payload[CCCH_PAYLOAD_SIZE_MAX] ; -} __attribute__((__packed__))CCCH_PDU; -/*! \brief BCCH payload */ -typedef struct { - uint8_t payload[BCCH_PAYLOAD_SIZE_MAX] ; -} __attribute__((__packed__))BCCH_PDU; -/*! \brief RAR payload */ -typedef struct { - uint8_t payload[RAR_PAYLOAD_SIZE_MAX]; -} __attribute__ ((__packed__)) RAR_PDU; -/*! \brief BCCH payload */ -typedef struct { - uint8_t payload[PCCH_PAYLOAD_SIZE_MAX] ; -} __attribute__((__packed__))PCCH_PDU; - -/*! \brief MCCH payload */ -typedef struct { - uint8_t payload[MCCH_PAYLOAD_SIZE_MAX] ; -} __attribute__((__packed__))MCCH_PDU; -/*!< \brief MAC control element for activation and deactivation of component carriers */ -typedef struct { - uint8_t C7:1;/*!< \brief Component carrier 7 */ - uint8_t C6:1;/*!< \brief Component carrier 6 */ - uint8_t C5:1;/*!< \brief Component carrier 5 */ - uint8_t C4:1;/*!< \brief Component carrier 4 */ - uint8_t C3:1;/*!< \brief Component carrier 3 */ - uint8_t C2:1;/*!< \brief Component carrier 2 */ - uint8_t C1:1;/*!< \brief Component carrier 1 */ - uint8_t R:1;/*!< \brief Reserved */ -} __attribute__((__packed__))CC_ELEMENT; -/*! \brief MAC control element: MCH Scheduling Information */ -typedef struct { - uint8_t stop_sf_MSB:3; // octet 1 LSB - uint8_t lcid:5; // octet 2 MSB - uint8_t stop_sf_LSB:8; -} __attribute__((__packed__))MSI_ELEMENT; -/*! \brief Values of CCCH LCID for DLSCH */ -#define CCCH_LCHANID 0 -/*!\brief Values of BCCH logical channel (fake)*/ -#define BCCH 3 // SI -/*!\brief Values of PCCH logical channel (fake)*/ -#define PCCH 4 // Paging -/*!\brief Values of PCCH logical channel (fake) */ -#define MIBCH 5 // MIB -/*!\brief Values of BCCH SIB1_BR logical channel (fake) */ -#define BCCH_SIB1_BR 6 // SIB1_BR -/*!\brief Values of BCCH SIB_BR logical channel (fake) */ -#define BCCH_SI_BR 7 // SI-BR -/*!\brief Value of CCCH / SRB0 logical channel */ -#define CCCH 0 // srb0 -/*!\brief DCCH / SRB1 logical channel */ -#define DCCH 1 // srb1 -/*!\brief DCCH1 / SRB2 logical channel */ -#define DCCH1 2 // srb2 -/*!\brief DTCH DRB1 logical channel */ -#define DTCH 3 // LCID -/*!\brief MCCH logical channel */ -#define MCCH 11 -/*!\brief MTCH logical channel */ -#define MTCH 1 -// DLSCH LCHAN ID -/*!\brief LCID of UE contention resolution identity for DLSCH*/ -#define UE_CONT_RES 28 -/*!\brief LCID of timing advance for DLSCH */ -#define TIMING_ADV_CMD 29 -/*!\brief LCID of discontinous reception mode for DLSCH */ -#define DRX_CMD 30 -/*!\brief LCID of padding LCID for DLSCH */ -#define SHORT_PADDING 31 - -// MCH LCHAN IDs (table6.2.1-4 TS36.321) -/*!\brief LCID of MCCH for DL */ -#define MCCH_LCHANID 0 -/*!\brief LCID of MCH scheduling info for DL */ -#define MCH_SCHDL_INFO 3 -/*!\brief LCID of Carrier component activation/deactivation */ -#define CC_ACT_DEACT 27 - -// ULSCH LCHAN IDs -/*!\brief LCID of extended power headroom for ULSCH */ -#define EXTENDED_POWER_HEADROOM 25 -/*!\brief LCID of power headroom for ULSCH */ -#define POWER_HEADROOM 26 -/*!\brief LCID of CRNTI for ULSCH */ -#define CRNTI 27 -/*!\brief LCID of truncated BSR for ULSCH */ -#define TRUNCATED_BSR 28 -/*!\brief LCID of short BSR for ULSCH */ -#define SHORT_BSR 29 -/*!\brief LCID of long BSR for ULSCH */ -#define LONG_BSR 30 -/*!\bitmaps for BSR Triggers */ -#define BSR_TRIGGER_NONE (0) /* No BSR Trigger */ -#define BSR_TRIGGER_REGULAR (1) /* For Regular and ReTxBSR Expiry Triggers */ -#define BSR_TRIGGER_PERIODIC (2) /* For BSR Periodic Timer Expiry Trigger */ -#define BSR_TRIGGER_PADDING (4) /* For Padding BSR Trigger */ - - -/*! \brief Downlink SCH PDU Structure */ -typedef struct { - uint8_t payload[8][SCH_PAYLOAD_SIZE_MAX]; - uint16_t Pdu_size[8]; -} __attribute__ ((__packed__)) DLSCH_PDU; - - -/*! \brief MCH PDU Structure */ -typedef struct { - int8_t payload[SCH_PAYLOAD_SIZE_MAX]; - uint16_t Pdu_size; - uint8_t mcs; - uint8_t sync_area; - uint8_t msi_active; - uint8_t mcch_active; - uint8_t mtch_active; -} __attribute__ ((__packed__)) MCH_PDU; - -/*! \brief Uplink SCH PDU Structure */ -typedef struct { - int8_t payload[SCH_PAYLOAD_SIZE_MAX]; /*!< \brief SACH payload */ - uint16_t Pdu_size; -} __attribute__ ((__packed__)) ULSCH_PDU; - -#include "PHY/impl_defs_top.h" - -/*!\brief UE ULSCH scheduling states*/ -typedef enum { - S_UL_NONE =0, - S_UL_WAITING, - S_UL_SCHEDULED, - S_UL_BUFFERED, - S_UL_NUM_STATUS -} UE_ULSCH_STATUS; - -/*!\brief UE DLSCH scheduling states*/ -typedef enum { - S_DL_NONE =0, - S_DL_WAITING, - S_DL_SCHEDULED, - S_DL_BUFFERED, - S_DL_NUM_STATUS -} UE_DLSCH_STATUS; - -/*!\brief scheduling policy for the contention-based access */ -typedef enum { - CBA_ES=0, /// equal share of RB among groups w - CBA_ES_S, /// equal share of RB among groups with small allocation - CBA_PF, /// proportional fair (kind of) - CBA_PF_S, /// proportional fair (kind of) with small RB allocation - CBA_RS /// random allocation -} CBA_POLICY; - - -/*! \brief temporary struct for ULSCH sched */ -typedef struct { - rnti_t rnti; - uint16_t subframe; - uint16_t serving_num; - UE_ULSCH_STATUS status; -} eNB_ULSCH_INFO; -/*! \brief temp struct for DLSCH sched */ -typedef struct { - rnti_t rnti; - uint16_t weight; - uint16_t subframe; - uint16_t serving_num; - UE_DLSCH_STATUS status; -} eNB_DLSCH_INFO; -/*! \brief eNB overall statistics */ -typedef struct { - /// num BCCH PDU per CC - uint32_t total_num_bcch_pdu; - /// BCCH buffer size - uint32_t bcch_buffer; - /// total BCCH buffer size - uint32_t total_bcch_buffer; - /// BCCH MCS - uint32_t bcch_mcs; - - /// num CCCH PDU per CC - uint32_t total_num_ccch_pdu; - /// BCCH buffer size - uint32_t ccch_buffer; - /// total BCCH buffer size - uint32_t total_ccch_buffer; - /// BCCH MCS - uint32_t ccch_mcs; - - /// num active users - uint16_t num_dlactive_UEs; - /// available number of PRBs for a give SF - uint16_t available_prbs; - /// total number of PRB available for the user plane - uint32_t total_available_prbs; - /// aggregation - /// total avilable nccc : num control channel element - uint16_t available_ncces; - // only for a new transmission, should be extended for retransmission - // current dlsch bit rate for all transport channels - uint32_t dlsch_bitrate; - // - uint32_t dlsch_bytes_tx; - // - uint32_t dlsch_pdus_tx; - // - uint32_t total_dlsch_bitrate; - // - uint32_t total_dlsch_bytes_tx; - // - uint32_t total_dlsch_pdus_tx; - - // here for RX - // - uint32_t ulsch_bitrate; - // - uint32_t ulsch_bytes_rx; - // - uint64_t ulsch_pdus_rx; - - uint32_t total_ulsch_bitrate; - // - uint32_t total_ulsch_bytes_rx; - // - uint32_t total_ulsch_pdus_rx; - - - /// MAC agent-related stats - /// total number of scheduling decisions - int sched_decisions; - /// missed deadlines - int missed_deadlines; - -} eNB_STATS; -/*! \brief eNB statistics for the connected UEs*/ -typedef struct { - - /// CRNTI of UE - rnti_t crnti; ///user id (rnti) of connected UEs - // rrc status - uint8_t rrc_status; - /// harq pid - uint8_t harq_pid; - /// harq rounf - uint8_t harq_round; - /// total available number of PRBs for a new transmission - uint16_t rbs_used; - /// total available number of PRBs for a retransmission - uint16_t rbs_used_retx; - /// total nccc used for a new transmission: num control channel element - uint16_t ncce_used; - /// total avilable nccc for a retransmission: num control channel element - uint16_t ncce_used_retx; - - // mcs1 before the rate adaptaion - uint8_t dlsch_mcs1; - /// Target mcs2 after rate-adaptation - uint8_t dlsch_mcs2; - // current TBS with mcs2 - uint32_t TBS; - // total TBS with mcs2 - // uint32_t total_TBS; - // total rb used for a new transmission - uint32_t total_rbs_used; - // total rb used for retransmission - uint32_t total_rbs_used_retx; - - /// TX - /// Num pkt - uint32_t num_pdu_tx[NB_RB_MAX]; - /// num bytes - uint32_t num_bytes_tx[NB_RB_MAX]; - /// num retransmission / harq - uint32_t num_retransmission; - /// instantaneous tx throughput for each TTI - // uint32_t tti_throughput[NB_RB_MAX]; - - /// overall - // - uint32_t dlsch_bitrate; - //total - uint32_t total_dlsch_bitrate; - /// headers+ CE + padding bytes for a MAC PDU - uint64_t overhead_bytes; - /// headers+ CE + padding bytes for a MAC PDU - uint64_t total_overhead_bytes; - /// headers+ CE + padding bytes for a MAC PDU - uint64_t avg_overhead_bytes; - // MAC multiplexed payload - uint64_t total_sdu_bytes; - // total MAC pdu bytes - uint64_t total_pdu_bytes; - - // total num pdu - uint32_t total_num_pdus; - // - // uint32_t avg_pdu_size; - - /// RX - - /// PUCCH1a/b power (dBm) - int32_t Po_PUCCH_dBm; - /// Indicator that Po_PUCCH has been updated by PHY - int32_t Po_PUCCH_update; - /// Uplink measured RSSI - int32_t UL_rssi; - /// preassigned mcs after rate adaptation - uint8_t ulsch_mcs1; - /// adjusted mcs - uint8_t ulsch_mcs2; - - /// estimated average pdu inter-departure time - uint32_t avg_pdu_idt; - /// estimated average pdu size - uint32_t avg_pdu_ps; - /// - uint32_t aggregated_pdu_size; - uint32_t aggregated_pdu_arrival; - - /// uplink transport block size - uint32_t ulsch_TBS; - - /// total rb used for a new uplink transmission - uint32_t num_retransmission_rx; - /// total rb used for a new uplink transmission - uint32_t rbs_used_rx; - /// total rb used for a new uplink retransmission - uint32_t rbs_used_retx_rx; - /// total rb used for a new uplink transmission - uint32_t total_rbs_used_rx; - /// snr - int32_t snr; - /// target snr - int32_t target_snr; - - /// num rx pdu - uint32_t num_pdu_rx[NB_RB_MAX]; - /// num bytes rx - uint32_t num_bytes_rx[NB_RB_MAX]; - /// instantaneous rx throughput for each TTI - // uint32_t tti_goodput[NB_RB_MAX]; - /// errors - uint32_t num_errors_rx; - - uint64_t overhead_bytes_rx; - /// headers+ CE + padding bytes for a MAC PDU - uint64_t total_overhead_bytes_rx; - /// headers+ CE + padding bytes for a MAC PDU - uint64_t avg_overhead_bytes_rx; - // - uint32_t ulsch_bitrate; - //total - uint32_t total_ulsch_bitrate; - /// overall - /// MAC pdu bytes - uint64_t pdu_bytes_rx; - /// total MAC pdu bytes - uint64_t total_pdu_bytes_rx; - /// total num pdu - uint32_t total_num_pdus_rx; - /// num of error pdus - uint32_t total_num_errors_rx; - -} eNB_UE_STATS; -/*! \brief eNB template for UE context information */ -typedef struct { - /// C-RNTI of UE - rnti_t rnti; - /// NDI from last scheduling - uint8_t oldNDI[8]; - /// mcs1 from last scheduling - uint8_t oldmcs1[8]; - /// mcs2 from last scheduling - uint8_t oldmcs2[8]; - /// NDI from last UL scheduling - uint8_t oldNDI_UL[8]; - /// mcs from last UL scheduling - uint8_t mcs_UL[8]; - /// TBS from last UL scheduling - uint8_t TBS_UL[8]; - /// CQI_req from last scheduling - uint8_t oldCQI_UL[8]; - /// TPC from last scheduling - uint8_t oldTPC_UL[8]; - /// Flag to indicate UL has been scheduled at least once - boolean_t ul_active; - /// Flag to indicate UE has been configured (ACK from RRCConnectionSetup received) - boolean_t configured; - - /// MCS from last scheduling - uint8_t mcs[8]; - - /// TPC from last scheduling - uint8_t oldTPC[8]; - - // PHY interface info - - /// Number of Allocated RBs for DL after scheduling (prior to frequency allocation) - uint16_t nb_rb[8]; // num_max_harq - - /// Number of Allocated RBs for UL after scheduling - uint16_t nb_rb_ul[8]; // num_max_harq - - /// Number of Allocated RBs for UL after scheduling - uint16_t first_rb_ul[8]; // num_max_harq - - /// Is CQI requested for UL after scheduling 1st transmission - uint8_t cqi_req[8]; // num_max_harq - - /// Cyclic shift for DMRS after scheduling - uint16_t cshift[8]; // num_max_harq - - /// Number of Allocated RBs by the ulsch preprocessor - uint8_t pre_allocated_nb_rb_ul; - - /// index of Allocated RBs by the ulsch preprocessor - int8_t pre_allocated_rb_table_index_ul; - - /// total allocated RBs - int8_t total_allocated_rbs; - - /// pre-assigned MCS by the ulsch preprocessor - uint8_t pre_assigned_mcs_ul; - - /// assigned MCS by the ulsch scheduler - uint8_t assigned_mcs_ul; - - /// DL DAI - uint8_t DAI; - - /// UL DAI - uint8_t DAI_ul[10]; - - /// UL Scheduling Request Received - uint8_t ul_SR; - - ///Resource Block indication for each sub-band in MU-MIMO - uint8_t rballoc_subband[8][50]; - - // Logical channel info for link with RLC - - /// Last received UE BSR info for each logical channel group id - uint8_t bsr_info[MAX_NUM_LCGID]; - - /// LCGID mapping - long lcgidmap[11]; - - /// phr information - int8_t phr_info; - - /// phr information - int8_t phr_info_configured; - - ///dl buffer info - uint32_t dl_buffer_info[MAX_NUM_LCID]; - /// total downlink buffer info - uint32_t dl_buffer_total; - /// total downlink pdus - uint32_t dl_pdus_total; - /// downlink pdus for each LCID - uint32_t dl_pdus_in_buffer[MAX_NUM_LCID]; - /// creation time of the downlink buffer head for each LCID - uint32_t dl_buffer_head_sdu_creation_time[MAX_NUM_LCID]; - /// maximum creation time of the downlink buffer head across all LCID - uint32_t dl_buffer_head_sdu_creation_time_max; - /// a flag indicating that the downlink head SDU is segmented - uint8_t dl_buffer_head_sdu_is_segmented[MAX_NUM_LCID]; - /// size of remaining size to send for the downlink head SDU - uint32_t dl_buffer_head_sdu_remaining_size_to_send[MAX_NUM_LCID]; - - /// total uplink buffer size - uint32_t ul_total_buffer; - /// uplink buffer creation time for each LCID - uint32_t ul_buffer_creation_time[MAX_NUM_LCGID]; - /// maximum uplink buffer creation time across all the LCIDs - uint32_t ul_buffer_creation_time_max; - /// uplink buffer size per LCID - uint32_t ul_buffer_info[MAX_NUM_LCGID]; - - /// UE tx power - int32_t ue_tx_power; - - /// stores the frame where the last TPC was transmitted - uint32_t pusch_tpc_tx_frame; - uint32_t pusch_tpc_tx_subframe; - uint32_t pucch_tpc_tx_frame; - uint32_t pucch_tpc_tx_subframe; - -#ifdef LOCALIZATION - eNB_UE_estimated_distances distance; -#endif - - - uint8_t rach_resource_type; - - uint16_t mpdcch_repetition_cnt; - struct PhysicalConfigDedicated *physicalConfigDedicated; - frame_t Msg2_frame; - sub_frame_t Msg2_subframe; - -} UE_TEMPLATE; - -/*! \brief scheduling control information set through an API (not used)*/ -typedef struct { - ///UL transmission bandwidth in RBs - uint8_t ul_bandwidth[MAX_NUM_LCID]; - ///DL transmission bandwidth in RBs - uint8_t dl_bandwidth[MAX_NUM_LCID]; - - //To do GBR bearer - uint8_t min_ul_bandwidth[MAX_NUM_LCID]; - - uint8_t min_dl_bandwidth[MAX_NUM_LCID]; - - ///aggregated bit rate of non-gbr bearer per UE - uint64_t ue_AggregatedMaximumBitrateDL; - ///aggregated bit rate of non-gbr bearer per UE - uint64_t ue_AggregatedMaximumBitrateUL; - ///CQI scheduling interval in subframes. - uint16_t cqiSchedInterval; - ///Contention resolution timer used during random access - uint8_t mac_ContentionResolutionTimer; - - uint16_t max_allowed_rbs[MAX_NUM_LCID]; - - uint8_t max_mcs[MAX_NUM_LCID]; - - uint16_t priority[MAX_NUM_LCID]; - - // resource scheduling information - - /// Current DL harq round per harq_pid on each CC - uint8_t round[MAX_NUM_CCs][10]; - /// Current Active TBs per harq_pid on each CC - uint8_t tbcnt[MAX_NUM_CCs][10]; - /// Current UL harq round per harq_pid on each CC - uint8_t round_UL[MAX_NUM_CCs][8]; - uint8_t dl_pow_off[MAX_NUM_CCs]; - uint16_t pre_nb_available_rbs[MAX_NUM_CCs]; - unsigned char rballoc_sub_UE[MAX_NUM_CCs][N_RBG_MAX]; - uint16_t ta_timer; - int16_t ta_update; - uint16_t ul_consecutive_errors; - int32_t context_active_timer; - int32_t cqi_req_timer; - int32_t ul_inactivity_timer; - int32_t ul_failure_timer; - int32_t ul_scheduled; - int32_t ra_pdcch_order_sent; - int32_t ul_out_of_sync; - int32_t phr_received; - uint8_t periodic_ri_received[NFAPI_CC_MAX]; - uint8_t aperiodic_ri_received[NFAPI_CC_MAX]; - uint32_t pucch_tpc_accumulated[NFAPI_CC_MAX]; - uint8_t pucch1_cqi_update[NFAPI_CC_MAX]; - uint8_t pucch1_snr[NFAPI_CC_MAX]; - uint8_t pucch2_cqi_update[NFAPI_CC_MAX]; - uint8_t pucch2_snr[NFAPI_CC_MAX]; - uint8_t pucch3_cqi_update[NFAPI_CC_MAX]; - uint8_t pucch3_snr[NFAPI_CC_MAX]; - uint8_t pusch_snr[NFAPI_CC_MAX]; - uint16_t feedback_cnt[NFAPI_CC_MAX]; - uint16_t timing_advance; - uint16_t timing_advance_r9; - uint8_t periodic_wideband_cqi[NFAPI_CC_MAX]; - uint8_t periodic_wideband_spatial_diffcqi[NFAPI_CC_MAX]; - uint8_t periodic_wideband_pmi[NFAPI_CC_MAX]; - uint8_t periodic_subband_cqi[NFAPI_CC_MAX][16]; - uint8_t periodic_subband_spatial_diffcqi[NFAPI_CC_MAX][16]; - uint8_t aperiodic_subband_cqi0[NFAPI_CC_MAX][25]; - uint8_t aperiodic_subband_pmi[NFAPI_CC_MAX][25]; - uint8_t aperiodic_subband_diffcqi0[NFAPI_CC_MAX][25]; - uint8_t aperiodic_subband_cqi1[NFAPI_CC_MAX][25]; - uint8_t aperiodic_subband_diffcqi1[NFAPI_CC_MAX][25]; - uint8_t aperiodic_wideband_cqi0[NFAPI_CC_MAX]; - uint8_t aperiodic_wideband_pmi[NFAPI_CC_MAX]; - uint8_t aperiodic_wideband_cqi1[NFAPI_CC_MAX]; - uint8_t aperiodic_wideband_pmi1[NFAPI_CC_MAX]; - uint8_t dl_cqi[NFAPI_CC_MAX]; -} UE_sched_ctrl; -/*! \brief eNB template for the Random access information */ -typedef struct { - /// Flag to indicate this process is active - boolean_t RA_active; - /// Size of DCI for RA-Response (bytes) - uint8_t RA_dci_size_bytes1; - /// Size of DCI for RA-Response (bits) - uint8_t RA_dci_size_bits1; - /// Actual DCI to transmit for RA-Response - uint8_t RA_alloc_pdu1[(MAX_DCI_SIZE_BITS>>3)+1]; - /// DCI format for RA-Response (should be 1A) - uint8_t RA_dci_fmt1; - /// Size of DCI for Msg4/ContRes (bytes) - uint8_t RA_dci_size_bytes2; - /// Size of DCI for Msg4/ContRes (bits) - uint8_t RA_dci_size_bits2; - /// Actual DCI to transmit for Msg4/ContRes - uint8_t RA_alloc_pdu2[(MAX_DCI_SIZE_BITS>>3)+1]; - /// DCI format for Msg4/ContRes (should be 1A) - uint8_t RA_dci_fmt2; - /// Flag to indicate the eNB should generate RAR. This is triggered by detection of PRACH - uint8_t generate_rar; - /// Subframe where preamble was received - uint8_t preamble_subframe; - /// Subframe where Msg2 is to be sent - uint8_t Msg2_subframe; - /// Frame where Msg2 is to be sent - frame_t Msg2_frame; - /// Subframe where Msg3 is to be sent - sub_frame_t Msg3_subframe; - /// Frame where Msg3 is to be sent - frame_t Msg3_frame; - /// Subframe where Msg4 is to be sent - sub_frame_t Msg4_subframe; - /// Frame where Msg4 is to be sent - frame_t Msg4_frame; - /// Flag to indicate the eNB should generate Msg4 upon reception of SDU from RRC. This is triggered by first ULSCH reception at eNB for new user. - uint8_t generate_Msg4; - /// Flag to indicate that eNB is waiting for ACK that UE has received Msg3. - uint8_t wait_ack_Msg4; - /// harq_pid used for Msg4 transmission - uint8_t harq_pid; - /// UE RNTI allocated during RAR - rnti_t rnti; - /// RA RNTI allocated from received PRACH - uint16_t RA_rnti; - /// Received preamble_index - uint8_t preamble_index; - /// Received UE Contention Resolution Identifier - uint8_t cont_res_id[6]; - /// Timing offset indicated by PHY - int16_t timing_offset; - /// Timeout for RRC connection - int16_t RRC_timer; - /// Msg3 first RB - uint8_t msg3_first_rb; - /// Msg3 number of RB - uint8_t msg3_nb_rb; - /// Msg3 MCS - uint8_t msg3_mcs; - /// Msg3 TPC command - uint8_t msg3_TPC; - /// Msg3 ULdelay command - uint8_t msg3_ULdelay; - /// Msg3 cqireq command - uint8_t msg3_cqireq; - /// Round of Msg3 HARQ - uint8_t msg3_round; - /// TBS used for Msg4 - int msg4_TBsize; - /// MCS used for Msg4 - int msg4_mcs; - /// size off piggybacked RRC SDU - uint8_t msg4_rrc_sdu_length; - uint32_t msg4_delay; - uint8_t rach_resource_type; - uint8_t msg2_mpdcch_repetition_cnt; - uint8_t msg2_mpdcch_done; - uint8_t msg4_mpdcch_repetition_cnt; - uint8_t msg4_mpdcch_done; - uint8_t msg2_narrowband; - uint32_t msg34_narrowband; -} RA_TEMPLATE; - - -/*! \brief subband bitmap confguration (for ALU icic algo purpose), in test phase */ -typedef struct { - uint8_t sbmap[NUMBER_OF_SUBBANDS_MAX]; //13 = number of SB MAX for 100 PRB - uint8_t periodicity; - uint8_t first_subframe; - uint8_t sb_size; - uint8_t nb_active_sb; -} SBMAP_CONF; -/*! \brief UE list used by eNB to order UEs/CC for scheduling*/ -typedef struct { - /// Dedicated information for UEs - struct PhysicalConfigDedicated *physicalConfigDedicated[MAX_NUM_CCs][NUMBER_OF_UE_MAX]; - /// DLSCH pdu - DLSCH_PDU DLSCH_pdu[MAX_NUM_CCs][2][NUMBER_OF_UE_MAX]; - /// DCI template and MAC connection parameters for UEs - UE_TEMPLATE UE_template[MAX_NUM_CCs][NUMBER_OF_UE_MAX]; - /// DCI template and MAC connection for RA processes - int pCC_id[NUMBER_OF_UE_MAX]; - /// sorted downlink component carrier for the scheduler - int ordered_CCids[MAX_NUM_CCs][NUMBER_OF_UE_MAX]; - /// number of downlink active component carrier - int numactiveCCs[NUMBER_OF_UE_MAX]; - /// sorted uplink component carrier for the scheduler - int ordered_ULCCids[MAX_NUM_CCs][NUMBER_OF_UE_MAX]; - /// number of uplink active component carrier - int numactiveULCCs[NUMBER_OF_UE_MAX]; - /// number of downlink active component carrier - uint8_t dl_CC_bitmap[NUMBER_OF_UE_MAX]; - /// eNB to UE statistics - eNB_UE_STATS eNB_UE_stats[MAX_NUM_CCs][NUMBER_OF_UE_MAX]; - /// scheduling control info - UE_sched_ctrl UE_sched_ctrl[NUMBER_OF_UE_MAX]; - int next[NUMBER_OF_UE_MAX]; - int head; - int next_ul[NUMBER_OF_UE_MAX]; - int head_ul; - int avail; - int num_UEs; - boolean_t active[NUMBER_OF_UE_MAX]; -} UE_list_t; - -/*! \brief eNB common channels */ -typedef struct { - int physCellId; - int p_eNB; - int Ncp; - int eutra_band; - uint32_t dl_CarrierFreq; - BCCH_BCH_Message_t *mib; - RadioResourceConfigCommonSIB_t *radioResourceConfigCommon; - RadioResourceConfigCommonSIB_t *radioResourceConfigCommon_BR; - TDD_Config_t *tdd_Config; - SchedulingInfoList_t *schedulingInfoList; - ARFCN_ValueEUTRA_t ul_CarrierFreq; - long ul_Bandwidth; - /// Outgoing MIB PDU for PHY - MIB_PDU MIB_pdu; - /// Outgoing BCCH pdu for PHY - BCCH_PDU BCCH_pdu; - /// Outgoing BCCH DCI allocation - uint32_t BCCH_alloc_pdu; - /// Outgoing CCCH pdu for PHY - CCCH_PDU CCCH_pdu; - /// Outgoing RAR pdu for PHY - RAR_PDU RAR_pdu; - /// Template for RA computations - RA_TEMPLATE RA_template[NB_RA_PROC_MAX]; - /// VRB map for common channels - uint8_t vrb_map[100]; - /// VRB map for common channels and retransmissions by PHICH - uint8_t vrb_map_UL[100]; - /// MBSFN SubframeConfig - struct MBSFN_SubframeConfig *mbsfn_SubframeConfig[8]; - /// number of subframe allocation pattern available for MBSFN sync area - uint8_t num_sf_allocation_pattern; - /// MBMS Flag - uint8_t MBMS_flag; - /// Outgoing MCCH pdu for PHY - MCCH_PDU MCCH_pdu; - /// MCCH active flag - uint8_t msi_active; - /// MCCH active flag - uint8_t mcch_active; - /// MTCH active flag - uint8_t mtch_active; - /// number of active MBSFN area - uint8_t num_active_mbsfn_area; - /// MBSFN Area Info - struct MBSFN_AreaInfo_r9 *mbsfn_AreaInfo[MAX_MBSFN_AREA]; - /// PMCH Config - struct PMCH_Config_r9 *pmch_Config[MAX_PMCH_perMBSFN]; - /// MBMS session info list - struct MBMS_SessionInfoList_r9 *mbms_SessionList[MAX_PMCH_perMBSFN]; - /// Outgoing MCH pdu for PHY - MCH_PDU MCH_pdu; - /// Rel13 parameters from SIB1 - SystemInformationBlockType1_v1310_IEs_t *sib1_v13ext; - /// Counter for SIB1-BR scheduling - int SIB1_BR_cnt; - /// Outgoing BCCH-BR pdu for PHY - BCCH_PDU BCCH_BR_pdu[20]; -} COMMON_channels_t; -/*! \brief top level eNB MAC structure */ -typedef struct eNB_MAC_INST_s { - /// Ethernet parameters for northbound midhaul interface - eth_params_t eth_params_n; - /// Ethernet parameters for fronthaul interface - eth_params_t eth_params_s; - /// - module_id_t Mod_id; - /// frame counter - frame_t frame; - /// subframe counter - sub_frame_t subframe; - /// Pointer to IF module instance for PHY - IF_Module_t *if_inst; - /// Common cell resources - COMMON_channels_t common_channels[MAX_NUM_CCs]; - /// current PDU index (BCH,MCH,DLSCH) - uint16_t pdu_index[MAX_NUM_CCs]; - - /// NFAPI Config Request Structure - nfapi_config_request_t config[MAX_NUM_CCs]; - /// Preallocated DL pdu list - nfapi_dl_config_request_pdu_t dl_config_pdu_list[MAX_NUM_CCs][MAX_NUM_DL_PDU]; - /// NFAPI DL Config Request Structure - nfapi_dl_config_request_t DL_req[MAX_NUM_CCs]; - /// Preallocated UL pdu list - nfapi_ul_config_request_pdu_t ul_config_pdu_list[MAX_NUM_CCs][MAX_NUM_UL_PDU]; - /// Preallocated UL pdu list for ULSCH (n+k delay) - nfapi_ul_config_request_pdu_t ul_config_pdu_list_tmp[MAX_NUM_CCs][10][MAX_NUM_UL_PDU]; - /// NFAPI UL Config Request Structure, send to L1 4 subframes before processing takes place - nfapi_ul_config_request_t UL_req[MAX_NUM_CCs]; - /// NFAPI "Temporary" UL Config Request Structure, holds future UL_config requests - nfapi_ul_config_request_t UL_req_tmp[MAX_NUM_CCs][10]; - /// Preallocated HI_DCI0 pdu list - nfapi_hi_dci0_request_pdu_t hi_dci0_pdu_list[MAX_NUM_CCs][MAX_NUM_HI_DCI0_PDU]; - /// NFAPI HI/DCI0 Config Request Structure - nfapi_hi_dci0_request_t HI_DCI0_req[MAX_NUM_CCs]; - /// Prealocated TX pdu list - nfapi_tx_request_pdu_t tx_request_pdu[MAX_NUM_CCs][MAX_NUM_TX_REQUEST_PDU]; - /// NFAPI DL PDU structure - nfapi_tx_request_t TX_req[MAX_NUM_CCs]; - /// UL handle - uint32_t ul_handle; - UE_list_t UE_list; - - ///subband bitmap configuration - SBMAP_CONF sbmap_conf; - /// CCE table used to build DCI scheduling information - int CCE_table[MAX_NUM_CCs][800]; - /// active flag for Other lcid - uint8_t lcid_active[NB_RB_MAX]; - /// eNB stats - eNB_STATS eNB_stats[MAX_NUM_CCs]; - // MAC function execution peformance profiler - /// processing time of eNB scheduler - time_stats_t eNB_scheduler; - /// processing time of eNB scheduler for SI - time_stats_t schedule_si; - /// processing time of eNB scheduler for Random access - time_stats_t schedule_ra; - /// processing time of eNB ULSCH scheduler - time_stats_t schedule_ulsch; - /// processing time of eNB DCI generation - time_stats_t fill_DLSCH_dci; - /// processing time of eNB MAC preprocessor - time_stats_t schedule_dlsch_preprocessor; - /// processing time of eNB DLSCH scheduler - time_stats_t schedule_dlsch; // include rlc_data_req + MAC header + preprocessor - /// processing time of eNB MCH scheduler - time_stats_t schedule_mch; - /// processing time of eNB ULSCH reception - time_stats_t rx_ulsch_sdu; // include rlc_data_ind -} eNB_MAC_INST; - -/* - * UE part - */ - -typedef enum { - TYPE0, - TYPE1, - TYPE1A, - TYPE2, - TYPE2A, - TYPEUESPEC -} MPDCCH_TYPES_t; - -/*!\brief UE layer 2 status */ -typedef enum { - CONNECTION_OK=0, - CONNECTION_LOST, - PHY_RESYNCH, - PHY_HO_PRACH -} UE_L2_STATE_t; - -/*!\brief UE scheduling info */ -typedef struct { - /// buffer status for each lcgid - uint8_t BSR[MAX_NUM_LCGID]; // should be more for mesh topology - /// keep the number of bytes in rlc buffer for each lcgid - int32_t BSR_bytes[MAX_NUM_LCGID]; - /// after multiplexing buffer remain for each lcid - int32_t LCID_buffer_remain[MAX_NUM_LCID]; - /// sum of all lcid buffer size - uint16_t All_lcid_buffer_size_lastTTI; - /// buffer status for each lcid - uint8_t LCID_status[MAX_NUM_LCID]; - /// SR pending as defined in 36.321 - uint8_t SR_pending; - /// SR_COUNTER as defined in 36.321 - uint16_t SR_COUNTER; - /// logical channel group ide for each LCID - uint8_t LCGID[MAX_NUM_LCID]; - /// retxBSR-Timer, default value is sf2560 - uint16_t retxBSR_Timer; - /// retxBSR_SF, number of subframe before triggering a regular BSR - uint16_t retxBSR_SF; - /// periodicBSR-Timer, default to infinity - uint16_t periodicBSR_Timer; - /// periodicBSR_SF, number of subframe before triggering a periodic BSR - uint16_t periodicBSR_SF; - /// default value is 0: not configured - uint16_t sr_ProhibitTimer; - /// sr ProhibitTime running - uint8_t sr_ProhibitTimer_Running; - /// default value to n5 - uint16_t maxHARQ_Tx; - /// default value is false - uint16_t ttiBundling; - /// default value is release - struct DRX_Config *drx_config; - /// default value is release - struct MAC_MainConfig__phr_Config *phr_config; - ///timer before triggering a periodic PHR - uint16_t periodicPHR_Timer; - ///timer before triggering a prohibit PHR - uint16_t prohibitPHR_Timer; - ///DL Pathloss change value - uint16_t PathlossChange; - ///number of subframe before triggering a periodic PHR - int16_t periodicPHR_SF; - ///number of subframe before triggering a prohibit PHR - int16_t prohibitPHR_SF; - ///DL Pathloss Change in db - uint16_t PathlossChange_db; - - /// default value is false - uint16_t extendedBSR_Sizes_r10; - /// default value is false - uint16_t extendedPHR_r10; - - //Bj bucket usage per lcid - int16_t Bj[MAX_NUM_LCID]; - // Bucket size per lcid - int16_t bucket_size[MAX_NUM_LCID]; -} UE_SCHEDULING_INFO; -/*!\brief Top level UE MAC structure */ -typedef struct { - uint16_t Node_id; - /// RX frame counter - frame_t rxFrame; - /// RX subframe counter - sub_frame_t rxSubframe; - /// TX frame counter - frame_t txFrame; - /// TX subframe counter - sub_frame_t txSubframe; - /// C-RNTI of UE - uint16_t crnti; - /// C-RNTI of UE before HO - rnti_t crnti_before_ho; ///user id (rnti) of connected UEs - /// uplink active flag - uint8_t ul_active; - /// pointer to RRC PHY configuration - RadioResourceConfigCommonSIB_t *radioResourceConfigCommon; - /// pointer to RACH_ConfigDedicated (NULL when not active, i.e. upon HO completion or T304 expiry) - struct RACH_ConfigDedicated *rach_ConfigDedicated; - /// pointer to RRC PHY configuration - struct PhysicalConfigDedicated *physicalConfigDedicated; - /// pointer to RRC PHY configuration SCEll - struct PhysicalConfigDedicatedSCell_r10 *physicalConfigDedicatedSCell_r10; - /// pointer to TDD Configuration (NULL for FDD) - TDD_Config_t *tdd_Config; - /// Number of adjacent cells to measure - uint8_t n_adj_cells; - /// Array of adjacent physical cell ids - uint32_t adj_cell_id[6]; - /// Pointer to RRC MAC configuration - MAC_MainConfig_t *macConfig; - /// Pointer to RRC Measurement gap configuration - MeasGapConfig_t *measGapConfig; - /// Pointers to LogicalChannelConfig indexed by LogicalChannelIdentity. Note NULL means LCHAN is inactive. - LogicalChannelConfig_t *logicalChannelConfig[MAX_NUM_LCID]; - /// Scheduling Information - UE_SCHEDULING_INFO scheduling_info; - /// Outgoing CCCH pdu for PHY - CCCH_PDU CCCH_pdu; - /// Outgoing RAR pdu for PHY - RAR_PDU RAR_pdu; - /// Incoming DLSCH pdu for PHY - DLSCH_PDU DLSCH_pdu[NUMBER_OF_UE_MAX][2]; - /// number of attempt for rach - uint8_t RA_attempt_number; - /// Random-access procedure flag - uint8_t RA_active; - /// Random-access window counter - int8_t RA_window_cnt; - /// Random-access Msg3 size in bytes - uint8_t RA_Msg3_size; - /// Random-access prachMaskIndex - uint8_t RA_prachMaskIndex; - /// Flag indicating Preamble set (A,B) used for first Msg3 transmission - uint8_t RA_usedGroupA; - /// Random-access Resources - PRACH_RESOURCES_t RA_prach_resources; - /// Random-access PREAMBLE_TRANSMISSION_COUNTER - uint8_t RA_PREAMBLE_TRANSMISSION_COUNTER; - /// Random-access backoff counter - int16_t RA_backoff_cnt; - /// Random-access variable for window calculation (frame of last change in window counter) - uint32_t RA_tx_frame; - /// Random-access variable for window calculation (subframe of last change in window counter) - uint8_t RA_tx_subframe; - /// Random-access Group B maximum path-loss - /// Random-access variable for backoff (frame of last change in backoff counter) - uint32_t RA_backoff_frame; - /// Random-access variable for backoff (subframe of last change in backoff counter) - uint8_t RA_backoff_subframe; - /// Random-access Group B maximum path-loss - uint16_t RA_maxPL; - /// Random-access Contention Resolution Timer active flag - uint8_t RA_contention_resolution_timer_active; - /// Random-access Contention Resolution Timer count value - uint8_t RA_contention_resolution_cnt; - /// power headroom reporitng reconfigured - uint8_t PHR_reconfigured; - /// power headroom state as configured by the higher layers - uint8_t PHR_state; - /// power backoff due to power management (as allowed by P-MPRc) for this cell - uint8_t PHR_reporting_active; - /// power backoff due to power management (as allowed by P-MPRc) for this cell - uint8_t power_backoff_db[NUMBER_OF_eNB_MAX]; - /// BSR report falg management - uint8_t BSR_reporting_active; - /// retxBSR-Timer expires flag - uint8_t retxBSRTimer_expires_flag; - /// periodBSR-Timer expires flag - uint8_t periodBSRTimer_expires_flag; - - /// MBSFN_Subframe Configuration - struct MBSFN_SubframeConfig *mbsfn_SubframeConfig[8]; // FIXME replace 8 by MAX_MBSFN_AREA? - /// number of subframe allocation pattern available for MBSFN sync area - uint8_t num_sf_allocation_pattern; - /// number of active MBSFN area - uint8_t num_active_mbsfn_area; - /// MBSFN Area Info - struct MBSFN_AreaInfo_r9 *mbsfn_AreaInfo[MAX_MBSFN_AREA]; - /// PMCH Config - struct PMCH_Config_r9 *pmch_Config[MAX_PMCH_perMBSFN]; - /// MCCH status - uint8_t mcch_status; - /// MSI status - uint8_t msi_status;// could be an array if there are >1 MCH in one MBSFN area - /// CBA RNTI for each group - uint16_t cba_rnti[NUM_MAX_CBA_GROUP]; - /// last SFN for CBA channel access - uint8_t cba_last_access[NUM_MAX_CBA_GROUP]; - /// total UE scheduler processing time - time_stats_t ue_scheduler; // total - /// UE ULSCH tx processing time inlcuding RLC interface (rlc_data_req) and mac header generation - time_stats_t tx_ulsch_sdu; - /// UE DLSCH rx processing time inlcuding RLC interface (mac_rrc_data_ind or mac_rlc_status_ind+mac_rlc_data_ind) and mac header parser - time_stats_t rx_dlsch_sdu ; - /// UE query for MCH subframe processing time - time_stats_t ue_query_mch; - /// UE MCH rx processing time - time_stats_t rx_mch_sdu; - /// UE BCCH rx processing time including RLC interface (mac_rrc_data_ind) - time_stats_t rx_si; - /// UE PCCH rx processing time including RLC interface (mac_rrc_data_ind) - time_stats_t rx_p; -} UE_MAC_INST; -/*! \brief ID of the neighboring cells used for HO*/ -typedef struct { - uint16_t cell_ids[6]; - uint8_t n_adj_cells; -} neigh_cell_id_t; - -#include "proto.h" -/*@}*/ -#endif /*__LAYER2_MAC_DEFS_H__ */ diff --git a/openair2/LAYER2/MAC/eNB_scheduler.c b/openair2/LAYER2/MAC/eNB_scheduler.c index eef1f9c976282dc4ccfaa652c23f64e337b3bdcb..c46005ee2d5f28935f3dfe6a806e718718ef7fd1 100644 --- a/openair2/LAYER2/MAC/eNB_scheduler.c +++ b/openair2/LAYER2/MAC/eNB_scheduler.c @@ -35,7 +35,6 @@ #include "LAYER2/MAC/mac_extern.h" #include "LAYER2/MAC/mac_proto.h" -#include "LAYER2/NR_MAC_gNB/mac_proto.h" #include "common/utils/LOG/log.h" #include "nfapi/oai_integration/vendor_ext.h" #include "common/utils/LOG/vcd_signal_dumper.h" @@ -89,7 +88,7 @@ void schedule_SRS(module_id_t module_idP, const uint16_t deltaTSFCTabType1[15][2] = { {1, 1}, {1, 2}, {2, 2}, {1, 5}, {2, 5}, {4, 5}, {8, 5}, {3, 5}, {12, 5}, {1, 10}, {2, 10}, {4, 10}, {8, 10}, {351, 10}, {383, 10} }; // Table 5.5.3.3-2 3GPP 36.211 FDD const uint16_t deltaTSFCTabType2[14][2] = { {2, 5}, {6, 5}, {10, 5}, {18, 5}, {14, 5}, {22, 5}, {26, 5}, {30, 5}, {70, 10}, {74, 10}, {194, 10}, {326, 10}, {586, 10}, {210, 10} }; // Table 5.5.3.3-2 3GPP 36.211 TDD eNB_MAC_INST *eNB = RC.mac[module_idP]; - UE_list_t *UE_list = &(eNB->UE_list); + UE_info_t *UE_info = &eNB->UE_info; nfapi_ul_config_request_body_t *ul_req = NULL; UE_sched_ctrl_t *UE_scheduling_control = NULL; COMMON_channels_t *cc = eNB->common_channels; @@ -117,7 +116,7 @@ void schedule_SRS(module_id_t module_idP, if ((1 << tmp) & deltaTSFC) { /* This is an SRS subframe, loop over UEs */ for (UE_id = 0; UE_id < MAX_MOBILES_PER_ENB; UE_id++) { - if (!UE_list->active[UE_id]) { + if (!UE_info->active[UE_id]) { continue; } @@ -126,14 +125,14 @@ void schedule_SRS(module_id_t module_idP, continue; } - if(UE_list->UE_template[CC_id][UE_id].physicalConfigDedicated == NULL) { + if(UE_info->UE_template[CC_id][UE_id].physicalConfigDedicated == NULL) { LOG_E(MAC,"physicalConfigDedicated is null for UE %d\n",UE_id); printf("physicalConfigDedicated is null for UE %d\n",UE_id); return; } /* CDRX condition on Active Time and SRS type-0 report (36.321 5.7) */ - UE_scheduling_control = &(UE_list->UE_sched_ctrl[UE_id]); + UE_scheduling_control = &(UE_info->UE_sched_ctrl[UE_id]); /* Test if Active Time not running since 6+ subframes */ if (UE_scheduling_control->cdrx_configured == TRUE && UE_scheduling_control->in_active_time == FALSE) { @@ -145,7 +144,7 @@ void schedule_SRS(module_id_t module_idP, ul_req = &(eNB->UL_req[CC_id].ul_config_request_body); - if ((soundingRS_UL_ConfigDedicated = UE_list->UE_template[CC_id][UE_id].physicalConfigDedicated->soundingRS_UL_ConfigDedicated) != NULL) { + if ((soundingRS_UL_ConfigDedicated = UE_info->UE_template[CC_id][UE_id].physicalConfigDedicated->soundingRS_UL_ConfigDedicated) != NULL) { if (soundingRS_UL_ConfigDedicated->present == LTE_SoundingRS_UL_ConfigDedicated_PR_setup) { get_srs_pos(&cc[CC_id], soundingRS_UL_ConfigDedicated->choice.setup.srs_ConfigIndex, @@ -161,7 +160,7 @@ void schedule_SRS(module_id_t module_idP, ul_config_pdu->pdu_size = 2 + (uint8_t) (2 + sizeof(nfapi_ul_config_srs_pdu)); ul_config_pdu->srs_pdu.srs_pdu_rel8.tl.tag = NFAPI_UL_CONFIG_REQUEST_SRS_PDU_REL8_TAG; ul_config_pdu->srs_pdu.srs_pdu_rel8.size = (uint8_t)sizeof(nfapi_ul_config_srs_pdu); - ul_config_pdu->srs_pdu.srs_pdu_rel8.rnti = UE_list->UE_template[CC_id][UE_id].rnti; + ul_config_pdu->srs_pdu.srs_pdu_rel8.rnti = UE_info->UE_template[CC_id][UE_id].rnti; ul_config_pdu->srs_pdu.srs_pdu_rel8.srs_bandwidth = soundingRS_UL_ConfigDedicated->choice.setup.srs_Bandwidth; ul_config_pdu->srs_pdu.srs_pdu_rel8.frequency_domain_position = soundingRS_UL_ConfigDedicated->choice.setup.freqDomainPosition; ul_config_pdu->srs_pdu.srs_pdu_rel8.srs_hopping_bandwidth = soundingRS_UL_ConfigDedicated->choice.setup.srs_HoppingBandwidth;; @@ -173,7 +172,7 @@ void schedule_SRS(module_id_t module_idP, ul_req->number_of_pdus++; } // if (((10*frameP+subframeP) % srsPeriodicity) == srsOffset) } // if (soundingRS_UL_ConfigDedicated->present == SoundingRS_UL_ConfigDedicated_PR_setup) - } // if ((soundingRS_UL_ConfigDedicated = UE_list->UE_template[CC_id][UE_id].physicalConfigDedicated->soundingRS_UL_ConfigDedicated)!=NULL) + } // if ((soundingRS_UL_ConfigDedicated = UE_info->UE_template[CC_id][UE_id].physicalConfigDedicated->soundingRS_UL_ConfigDedicated)!=NULL) } // end for loop on UE_id } // if((1<<tmp) & deltaTSFC) } // SRS config not NULL @@ -196,7 +195,7 @@ void schedule_CSI(module_id_t module_idP, uint16_t N_OFFSET_CQI = 0; struct LTE_CQI_ReportPeriodic *cqi_ReportPeriodic = NULL; eNB_MAC_INST *eNB = RC.mac[module_idP]; - UE_list_t *UE_list = &eNB->UE_list; + UE_info_t *UE_info = &eNB->UE_info; COMMON_channels_t *cc = NULL; nfapi_ul_config_request_body_t *ul_req = NULL; UE_sched_ctrl_t *UE_scheduling_control = NULL; @@ -205,7 +204,7 @@ void schedule_CSI(module_id_t module_idP, cc = &eNB->common_channels[CC_id]; for (UE_id = 0; UE_id < MAX_MOBILES_PER_ENB; UE_id++) { - if (UE_list->active[UE_id] == FALSE) { + if (UE_info->active[UE_id] == FALSE) { continue; } @@ -214,7 +213,7 @@ void schedule_CSI(module_id_t module_idP, continue; } - AssertFatal(UE_list->UE_template[CC_id][UE_id].physicalConfigDedicated != NULL, + AssertFatal(UE_info->UE_template[CC_id][UE_id].physicalConfigDedicated != NULL, "physicalConfigDedicated is null for UE %d\n", UE_id); /* @@ -222,7 +221,7 @@ void schedule_CSI(module_id_t module_idP, * Here we consider classic periodic reports on PUCCH without PUSCH simultaneous transmission condition. * TODO: add the handling or test on simultaneous PUCCH/PUSCH transmission */ - UE_scheduling_control = &(UE_list->UE_sched_ctrl[UE_id]); + UE_scheduling_control = &(UE_info->UE_sched_ctrl[UE_id]); if (UE_scheduling_control->cdrx_configured == TRUE) { /* Test if CQI masking activated */ @@ -246,8 +245,8 @@ void schedule_CSI(module_id_t module_idP, ul_req = &(eNB->UL_req[CC_id].ul_config_request_body); - if (UE_list->UE_template[CC_id][UE_id].physicalConfigDedicated->cqi_ReportConfig != NULL) { - cqi_ReportPeriodic = UE_list->UE_template[CC_id][UE_id].physicalConfigDedicated->cqi_ReportConfig->cqi_ReportPeriodic; + if (UE_info->UE_template[CC_id][UE_id].physicalConfigDedicated->cqi_ReportConfig != NULL) { + cqi_ReportPeriodic = UE_info->UE_template[CC_id][UE_id].physicalConfigDedicated->cqi_ReportConfig->cqi_ReportPeriodic; if (cqi_ReportPeriodic != NULL) { /* Rel8 Periodic CSI (CQI/PMI/RI) reporting */ @@ -262,10 +261,10 @@ void schedule_CSI(module_id_t module_idP, ul_config_pdu->pdu_type = NFAPI_UL_CONFIG_UCI_CQI_PDU_TYPE; ul_config_pdu->pdu_size = 2 + (uint8_t) (2 + sizeof(nfapi_ul_config_uci_cqi_pdu)); ul_config_pdu->uci_cqi_pdu.ue_information.ue_information_rel8.tl.tag = NFAPI_UL_CONFIG_REQUEST_UE_INFORMATION_REL8_TAG; - ul_config_pdu->uci_cqi_pdu.ue_information.ue_information_rel8.rnti = UE_list->UE_template[CC_id][UE_id].rnti; + ul_config_pdu->uci_cqi_pdu.ue_information.ue_information_rel8.rnti = UE_info->UE_template[CC_id][UE_id].rnti; ul_config_pdu->uci_cqi_pdu.cqi_information.cqi_information_rel8.tl.tag = NFAPI_UL_CONFIG_REQUEST_CQI_INFORMATION_REL8_TAG; ul_config_pdu->uci_cqi_pdu.cqi_information.cqi_information_rel8.pucch_index = cqi_ReportPeriodic->choice.setup.cqi_PUCCH_ResourceIndex; - ul_config_pdu->uci_cqi_pdu.cqi_information.cqi_information_rel8.dl_cqi_pmi_size = get_rel8_dl_cqi_pmi_size(&UE_list->UE_sched_ctrl[UE_id], CC_id, cc, get_tmode(module_idP, CC_id, UE_id), + ul_config_pdu->uci_cqi_pdu.cqi_information.cqi_information_rel8.dl_cqi_pmi_size = get_rel8_dl_cqi_pmi_size(&UE_info->UE_sched_ctrl[UE_id], CC_id, cc, get_tmode(module_idP, CC_id, UE_id), cqi_ReportPeriodic); ul_req->number_of_pdus++; ul_req->tl.tag = NFAPI_UL_CONFIG_REQUEST_BODY_TAG; @@ -279,7 +278,7 @@ void schedule_CSI(module_id_t module_idP, ul_config_pdu->pdu_type = NFAPI_UL_CONFIG_UCI_CQI_PDU_TYPE; ul_config_pdu->pdu_size = 2 + (uint8_t) (2 + sizeof(nfapi_ul_config_uci_cqi_pdu)); ul_config_pdu->uci_cqi_pdu.ue_information.ue_information_rel8.tl.tag = NFAPI_UL_CONFIG_REQUEST_UE_INFORMATION_REL8_TAG; - ul_config_pdu->uci_cqi_pdu.ue_information.ue_information_rel8.rnti = UE_list->UE_template[CC_id][UE_id].rnti; + ul_config_pdu->uci_cqi_pdu.ue_information.ue_information_rel8.rnti = UE_info->UE_template[CC_id][UE_id].rnti; ul_config_pdu->uci_cqi_pdu.cqi_information.cqi_information_rel8.tl.tag = NFAPI_UL_CONFIG_REQUEST_CQI_INFORMATION_REL8_TAG; ul_config_pdu->uci_cqi_pdu.cqi_information.cqi_information_rel8.pucch_index = cqi_ReportPeriodic->choice.setup.cqi_PUCCH_ResourceIndex; ul_config_pdu->uci_cqi_pdu.cqi_information.cqi_information_rel8.dl_cqi_pmi_size = (cc->p_eNB == 2) ? 1 : 2; @@ -291,7 +290,7 @@ void schedule_CSI(module_id_t module_idP, } // if CSI Periodic is not release state } // if (cqi_ReportPeriodic != NULL) } // if cqi_ReportConfig != NULL - } // for (UE_id=UE_list->head; UE_id>=0; UE_id=UE_list->next[UE_id]) { + } // for (UE_id=UE_info->head; UE_id>=0; UE_id=UE_info->next[UE_id]) { } // for (CC_id=0; CC_id<MAX_NUM_CCs; CC_id++) { } @@ -309,7 +308,7 @@ schedule_SR (module_id_t module_idP, int is_harq = 0; int pdu_list_index = 0; eNB_MAC_INST *eNB = RC.mac[module_idP]; - UE_list_t *UE_list = &eNB->UE_list; + UE_info_t *UE_info = &eNB->UE_info; nfapi_ul_config_request_t *ul_req = NULL; nfapi_ul_config_request_body_t *ul_req_body = NULL; LTE_SchedulingRequestConfig_t *SRconfig = NULL; @@ -319,13 +318,13 @@ schedule_SR (module_id_t module_idP, eNB->UL_req[CC_id].sfn_sf = (frameP << 4) + subframeP; for (int UE_id = 0; UE_id < MAX_MOBILES_PER_ENB; UE_id++) { - if (!UE_list->active[UE_id]) { + if (!UE_info->active[UE_id]) { continue; } - if (UE_list->UE_template[CC_id][UE_id].physicalConfigDedicated == NULL) continue; + if (UE_info->UE_template[CC_id][UE_id].physicalConfigDedicated == NULL) continue; - if ((SRconfig = UE_list->UE_template[CC_id][UE_id].physicalConfigDedicated->schedulingRequestConfig) != NULL) { + if ((SRconfig = UE_info->UE_template[CC_id][UE_id].physicalConfigDedicated->schedulingRequestConfig) != NULL) { if (SRconfig->present == LTE_SchedulingRequestConfig_PR_setup) { if (SRconfig->choice.setup.sr_ConfigIndex <= 4) { // 5 ms SR period if ((subframeP % 5) != SRconfig->choice.setup.sr_ConfigIndex) continue; @@ -337,9 +336,11 @@ schedule_SR (module_id_t module_idP, if ((10 * (frameP & 3) + subframeP) != (SRconfig->choice.setup.sr_ConfigIndex - 35)) continue; } else if (SRconfig->choice.setup.sr_ConfigIndex <= 154) { // 80 ms SR period if ((10 * (frameP & 7) + subframeP) != (SRconfig->choice.setup.sr_ConfigIndex - 75)) continue; + } else if (SRconfig->choice.setup.sr_ConfigIndex <= 156) { // 2ms SR period + if ((subframeP % 2) != (SRconfig->choice.setup.sr_ConfigIndex - 155)) continue; } } // SRconfig->present == SchedulingRequestConfig_PR_setup) - } // SRconfig = UE_list->UE_template[CC_id][UE_id].physicalConfigDedicated->schedulingRequestConfig)!=NULL) + } // SRconfig = UE_info->UE_template[CC_id][UE_id].physicalConfigDedicated->schedulingRequestConfig)!=NULL) /* If we get here there is some PUCCH1 reception to schedule for SR */ ul_req = &(eNB->UL_req[CC_id]); @@ -354,14 +355,14 @@ schedule_SR (module_id_t module_idP, (ul_req_body->ul_config_pdu_list[i].pdu_type == NFAPI_UL_CONFIG_ULSCH_HARQ_PDU_TYPE) || (ul_req_body->ul_config_pdu_list[i].pdu_type == NFAPI_UL_CONFIG_ULSCH_CQI_RI_PDU_TYPE) || (ul_req_body->ul_config_pdu_list[i].pdu_type == NFAPI_UL_CONFIG_ULSCH_CQI_HARQ_RI_PDU_TYPE)) && - (ul_req_body->ul_config_pdu_list[i].ulsch_pdu.ulsch_pdu_rel8.rnti == UE_list->UE_template[CC_id][UE_id].rnti)) { + (ul_req_body->ul_config_pdu_list[i].ulsch_pdu.ulsch_pdu_rel8.rnti == UE_info->UE_template[CC_id][UE_id].rnti)) { skip_ue = 1; pdu_list_index = i; break; } /* If there is already an HARQ pdu, convert to SR_HARQ */ else if ((ul_req_body->ul_config_pdu_list[i].pdu_type == NFAPI_UL_CONFIG_UCI_HARQ_PDU_TYPE) && - (ul_req_body->ul_config_pdu_list[i].uci_harq_pdu.ue_information.ue_information_rel8.rnti == UE_list->UE_template[CC_id][UE_id].rnti)) { + (ul_req_body->ul_config_pdu_list[i].uci_harq_pdu.ue_information.ue_information_rel8.rnti == UE_info->UE_template[CC_id][UE_id].rnti)) { is_harq = 1; pdu_list_index = i; break; @@ -375,20 +376,20 @@ schedule_SR (module_id_t module_idP, frameP, subframeP, UE_id, - UE_list->UE_template[CC_id][UE_id].rnti, + UE_info->UE_template[CC_id][UE_id].rnti, is_harq); /* Check Rel10 or Rel8 SR */ - if ((UE_list-> UE_template[CC_id][UE_id].physicalConfigDedicated->ext2) && - (UE_list->UE_template[CC_id][UE_id].physicalConfigDedicated->ext2->schedulingRequestConfig_v1020) && - (UE_list->UE_template[CC_id][UE_id].physicalConfigDedicated->ext2->schedulingRequestConfig_v1020)) { + if ((UE_info-> UE_template[CC_id][UE_id].physicalConfigDedicated->ext2) && + (UE_info->UE_template[CC_id][UE_id].physicalConfigDedicated->ext2->schedulingRequestConfig_v1020) && + (UE_info->UE_template[CC_id][UE_id].physicalConfigDedicated->ext2->schedulingRequestConfig_v1020)) { sr.sr_information_rel10.tl.tag = NFAPI_UL_CONFIG_REQUEST_SR_INFORMATION_REL10_TAG; sr.sr_information_rel10.number_of_pucch_resources = 1; - sr.sr_information_rel10.pucch_index_p1 = *UE_list->UE_template[CC_id][UE_id].physicalConfigDedicated->ext2->schedulingRequestConfig_v1020->sr_PUCCH_ResourceIndexP1_r10; + sr.sr_information_rel10.pucch_index_p1 = *UE_info->UE_template[CC_id][UE_id].physicalConfigDedicated->ext2->schedulingRequestConfig_v1020->sr_PUCCH_ResourceIndexP1_r10; LOG_D(MAC, "REL10 PUCCH INDEX P1:%d \n", sr.sr_information_rel10.pucch_index_p1); } else { sr.sr_information_rel8.tl.tag = NFAPI_UL_CONFIG_REQUEST_SR_INFORMATION_REL8_TAG; - sr.sr_information_rel8.pucch_index = UE_list->UE_template[CC_id][UE_id].physicalConfigDedicated->schedulingRequestConfig->choice.setup.sr_PUCCH_ResourceIndex; + sr.sr_information_rel8.pucch_index = UE_info->UE_template[CC_id][UE_id].physicalConfigDedicated->schedulingRequestConfig->choice.setup.sr_PUCCH_ResourceIndex; LOG_D(MAC, "REL8 PUCCH INDEX:%d\n", sr.sr_information_rel8.pucch_index); } @@ -401,7 +402,7 @@ schedule_SR (module_id_t module_idP, } else { ul_req_body->ul_config_pdu_list[ul_req_body->number_of_pdus].pdu_type = NFAPI_UL_CONFIG_UCI_SR_PDU_TYPE; ul_req_body->ul_config_pdu_list[ul_req_body->number_of_pdus].uci_sr_pdu.ue_information.ue_information_rel8.tl.tag = NFAPI_UL_CONFIG_REQUEST_UE_INFORMATION_REL8_TAG; - ul_req_body->ul_config_pdu_list[ul_req_body->number_of_pdus].uci_sr_pdu.ue_information.ue_information_rel8.rnti = UE_list->UE_template[CC_id][UE_id].rnti; + ul_req_body->ul_config_pdu_list[ul_req_body->number_of_pdus].uci_sr_pdu.ue_information.ue_information_rel8.rnti = UE_info->UE_template[CC_id][UE_id].rnti; ul_req_body->ul_config_pdu_list[ul_req_body->number_of_pdus].uci_sr_pdu.ue_information.ue_information_rel11.tl.tag = 0; ul_req_body->ul_config_pdu_list[ul_req_body->number_of_pdus].uci_sr_pdu.ue_information.ue_information_rel13.tl.tag = 0; ul_req_body->ul_config_pdu_list[ul_req_body->number_of_pdus].uci_sr_pdu.sr_information = sr; @@ -416,20 +417,20 @@ schedule_SR (module_id_t module_idP, void check_ul_failure(module_id_t module_idP, int CC_id, int UE_id, frame_t frameP, sub_frame_t subframeP) { - UE_list_t *UE_list = &RC.mac[module_idP]->UE_list; + UE_info_t *UE_info = &RC.mac[module_idP]->UE_info; nfapi_dl_config_request_t *DL_req = &RC.mac[module_idP]->DL_req[0]; uint16_t rnti = UE_RNTI(module_idP, UE_id); COMMON_channels_t *cc = RC.mac[module_idP]->common_channels; // check uplink failure - if ((UE_list->UE_sched_ctrl[UE_id].ul_failure_timer > 0) && - (UE_list->UE_sched_ctrl[UE_id].ul_out_of_sync == 0)) { - if (UE_list->UE_sched_ctrl[UE_id].ul_failure_timer == 1) + if ((UE_info->UE_sched_ctrl[UE_id].ul_failure_timer > 0) && + (UE_info->UE_sched_ctrl[UE_id].ul_out_of_sync == 0)) { + if (UE_info->UE_sched_ctrl[UE_id].ul_failure_timer == 1) LOG_I(MAC, "UE %d rnti %x: UL Failure timer %d \n", UE_id, rnti, - UE_list->UE_sched_ctrl[UE_id].ul_failure_timer); + UE_info->UE_sched_ctrl[UE_id].ul_failure_timer); - if (UE_list->UE_sched_ctrl[UE_id].ra_pdcch_order_sent == 0) { - UE_list->UE_sched_ctrl[UE_id].ra_pdcch_order_sent = 1; + if (UE_info->UE_sched_ctrl[UE_id].ra_pdcch_order_sent == 0) { + UE_info->UE_sched_ctrl[UE_id].ra_pdcch_order_sent = 1; // add a format 1A dci for this UE to request an RA procedure (only one UE per subframe) nfapi_dl_config_request_pdu_t *dl_config_pdu = &DL_req[CC_id].dl_config_request_body.dl_config_pdu_list[DL_req[CC_id].dl_config_request_body.number_pdu]; memset((void *) dl_config_pdu, 0,sizeof(nfapi_dl_config_request_pdu_t)); @@ -438,7 +439,7 @@ check_ul_failure(module_id_t module_idP, int CC_id, int UE_id, dl_config_pdu->dci_dl_pdu.dci_dl_pdu_rel8.tl.tag = NFAPI_DL_CONFIG_REQUEST_DCI_DL_PDU_REL8_TAG; dl_config_pdu->dci_dl_pdu.dci_dl_pdu_rel8.dci_format = NFAPI_DL_DCI_FORMAT_1A; dl_config_pdu->dci_dl_pdu.dci_dl_pdu_rel8.aggregation_level = get_aggregation(get_bw_index(module_idP, CC_id), - UE_list->UE_sched_ctrl[UE_id]. + UE_info->UE_sched_ctrl[UE_id]. dl_cqi[CC_id], format1A); dl_config_pdu->dci_dl_pdu.dci_dl_pdu_rel8.rnti = rnti; dl_config_pdu->dci_dl_pdu.dci_dl_pdu_rel8.rnti_type = 1; // CRNTI : see Table 4-10 from SCF082 - nFAPI specifications @@ -454,22 +455,22 @@ check_ul_failure(module_id_t module_idP, int CC_id, int UE_id, LOG_D(MAC, "UE %d rnti %x: sending PDCCH order for RAPROC (failure timer %d), resource_block_coding %d \n", UE_id, rnti, - UE_list->UE_sched_ctrl[UE_id].ul_failure_timer, + UE_info->UE_sched_ctrl[UE_id].ul_failure_timer, dl_config_pdu->dci_dl_pdu. dci_dl_pdu_rel8.resource_block_coding); } else { // ra_pdcch_sent==1 LOG_D(MAC, "UE %d rnti %x: sent PDCCH order for RAPROC waiting (failure timer %d) \n", UE_id, rnti, - UE_list->UE_sched_ctrl[UE_id].ul_failure_timer); + UE_info->UE_sched_ctrl[UE_id].ul_failure_timer); - if ((UE_list->UE_sched_ctrl[UE_id].ul_failure_timer % 80) == 0) UE_list->UE_sched_ctrl[UE_id].ra_pdcch_order_sent = 0; // resend every 8 frames + if ((UE_info->UE_sched_ctrl[UE_id].ul_failure_timer % 80) == 0) UE_info->UE_sched_ctrl[UE_id].ra_pdcch_order_sent = 0; // resend every 8 frames } - UE_list->UE_sched_ctrl[UE_id].ul_failure_timer++; + UE_info->UE_sched_ctrl[UE_id].ul_failure_timer++; // check threshold - if (UE_list->UE_sched_ctrl[UE_id].ul_failure_timer > 4000) { + if (UE_info->UE_sched_ctrl[UE_id].ul_failure_timer > 4000) { // note: probably ul_failure_timer should be less than UE radio link failure time(see T310/N310/N311) if (NODE_IS_DU(RC.rrc[module_idP]->node_type)) { MessageDef *m = itti_alloc_new_message(TASK_MAC_ENB, F1AP_UE_CONTEXT_RELEASE_REQ); @@ -491,17 +492,17 @@ check_ul_failure(module_id_t module_idP, int CC_id, int UE_id, rnti); } - UE_list->UE_sched_ctrl[UE_id].ul_failure_timer = 0; - UE_list->UE_sched_ctrl[UE_id].ul_out_of_sync = 1; + UE_info->UE_sched_ctrl[UE_id].ul_failure_timer = 0; + UE_info->UE_sched_ctrl[UE_id].ul_out_of_sync = 1; } } // ul_failure_timer>0 - UE_list->UE_sched_ctrl[UE_id].uplane_inactivity_timer++; + UE_info->UE_sched_ctrl[UE_id].uplane_inactivity_timer++; - if((U_PLANE_INACTIVITY_VALUE != 0) && (UE_list->UE_sched_ctrl[UE_id].uplane_inactivity_timer > (U_PLANE_INACTIVITY_VALUE * 10))) { + if((U_PLANE_INACTIVITY_VALUE != 0) && (UE_info->UE_sched_ctrl[UE_id].uplane_inactivity_timer > (U_PLANE_INACTIVITY_VALUE * 10))) { LOG_D(MAC,"UE %d rnti %x: U-Plane Failure after repeated PDCCH orders: Triggering RRC \n",UE_id,rnti); mac_eNB_rrc_uplane_failure(module_idP,CC_id,frameP,subframeP,rnti); - UE_list->UE_sched_ctrl[UE_id].uplane_inactivity_timer = 0; + UE_info->UE_sched_ctrl[UE_id].uplane_inactivity_timer = 0; }// time > 60s } @@ -565,7 +566,7 @@ eNB_dlsch_ulsch_scheduler(module_id_t module_idP, int CC_id = 0; int UE_id = -1; eNB_MAC_INST *eNB = RC.mac[module_idP]; - UE_list_t *UE_list = &(eNB->UE_list); + UE_info_t *UE_info = &(eNB->UE_info); COMMON_channels_t *cc = eNB->common_channels; UE_sched_ctrl_t *UE_scheduling_control = NULL; start_meas(&(eNB->eNB_scheduler)); @@ -584,16 +585,16 @@ eNB_dlsch_ulsch_scheduler(module_id_t module_idP, /* Refresh UE list based on UEs dropped by PHY in previous subframe */ for (UE_id = 0; UE_id < MAX_MOBILES_PER_ENB; UE_id++) { - if (UE_list->active[UE_id]) { + if (UE_info->active[UE_id]) { rnti = UE_RNTI(module_idP, UE_id); CC_id = UE_PCCID(module_idP, UE_id); - UE_scheduling_control = &(UE_list->UE_sched_ctrl[UE_id]); + UE_scheduling_control = &(UE_info->UE_sched_ctrl[UE_id]); if (((frameP & 127) == 0) && (subframeP == 0)) { LOG_I(MAC,"UE rnti %x : %s, PHR %d dB DL CQI %d PUSCH SNR %d PUCCH SNR %d\n", rnti, UE_scheduling_control->ul_out_of_sync == 0 ? "in synch" : "out of sync", - UE_list->UE_template[CC_id][UE_id].phr_info, + UE_info->UE_template[CC_id][UE_id].phr_info, UE_scheduling_control->dl_cqi[CC_id], (5 * UE_scheduling_control->pusch_snr[CC_id] - 640) / 10, (5 * UE_scheduling_control->pucch1_snr[CC_id] - 640) / 10); @@ -601,7 +602,7 @@ eNB_dlsch_ulsch_scheduler(module_id_t module_idP, RC.eNB[module_idP][CC_id]->pusch_stats_bsr[UE_id][(frameP * 10) + subframeP] = -63; - if (UE_id == UE_list->head) { + if (UE_id == UE_info->list.head) { VCD_SIGNAL_DUMPER_DUMP_VARIABLE_BY_NAME(VCD_SIGNAL_DUMPER_VARIABLES_UE0_BSR, RC.eNB[module_idP][CC_id]->pusch_stats_bsr[UE_id][(frameP * 10) + subframeP]); } @@ -735,7 +736,7 @@ eNB_dlsch_ulsch_scheduler(module_id_t module_idP, * here for the current subframe. The variable 'UE_scheduling_control->in_active_time' should be updated * ONLY here. The variable can then be used for testing the actual state of the UE for scheduling purpose. */ - UE_template = &(UE_list->UE_template[CC_id][UE_id]); + UE_template = &(UE_info->UE_template[CC_id][UE_id]); /* (a)synchronous HARQ processes handling for Active Time */ for (int harq_process_id = 0; harq_process_id < 8; harq_process_id++) { @@ -981,7 +982,9 @@ eNB_dlsch_ulsch_scheduler(module_id_t module_idP, /* Allocate CCEs for good after scheduling is done */ for (CC_id = 0; CC_id < MAX_NUM_CCs; CC_id++) { if (cc[CC_id].tdd_Config == NULL || !(is_UL_sf(&cc[CC_id],subframeP))) { - allocate_CCEs(module_idP, CC_id, frameP, subframeP, 2); + int rc = allocate_CCEs(module_idP, CC_id, frameP, subframeP, 2); + if (rc < 0) + LOG_E(MAC, "%s() %4d.%d ERROR ALLOCATING CCEs\n", __func__, frameP, subframeP); } } diff --git a/openair2/LAYER2/MAC/eNB_scheduler_RA.c b/openair2/LAYER2/MAC/eNB_scheduler_RA.c index fb765e6dacbfb6a41b18fe4a2483840b570b52e7..d1365b9ac32ee9d0a59d5abf7615b2ca41405669 100644 --- a/openair2/LAYER2/MAC/eNB_scheduler_RA.c +++ b/openair2/LAYER2/MAC/eNB_scheduler_RA.c @@ -587,7 +587,7 @@ generate_Msg4(module_id_t module_idP, { eNB_MAC_INST *mac = RC.mac[module_idP]; COMMON_channels_t *cc = mac->common_channels; - UE_list_t *UE_list = &(mac->UE_list); + UE_info_t *UE_info = &mac->UE_info; int16_t rrc_sdu_length = 0; uint16_t msg4_padding = 0; uint16_t msg4_post_padding = 0; @@ -831,7 +831,7 @@ generate_Msg4(module_id_t module_idP, dl_req_body->number_pdu++; ra->state = WAITMSG4ACK; lcid = 0; - UE_list->UE_sched_ctrl[UE_id].round[CC_idP][ra->harq_pid] = 0; + UE_info->UE_sched_ctrl[UE_id].round[CC_idP][ra->harq_pid] = 0; msg4_header = 1 + 6 + 1; // CR header, CR CE, SDU header AssertFatal((ra->msg4_TBsize - ra->msg4_rrc_sdu_length - msg4_header)>=0, "msg4_TBS %d is too small, change mcs to increase by %d bytes\n",ra->msg4_TBsize,ra->msg4_rrc_sdu_length+msg4_header-ra->msg4_TBsize); @@ -848,7 +848,7 @@ generate_Msg4(module_id_t module_idP, module_idP, CC_idP, frameP, subframeP, ra->msg4_TBsize, ra->msg4_rrc_sdu_length, msg4_header, msg4_padding, msg4_post_padding); DevAssert (UE_id != UE_INDEX_INVALID); // FIXME not sure how to gracefully return // CHECK THIS: &cc[CC_idP].CCCH_pdu.payload[0] - offset = generate_dlsch_header ((unsigned char *) mac->UE_list.DLSCH_pdu[CC_idP][0][(unsigned char) UE_id].payload[0], 1, //num_sdus + offset = generate_dlsch_header ((unsigned char *) mac->UE_info.DLSCH_pdu[CC_idP][0][(unsigned char) UE_id].payload[0], 1, //num_sdus (unsigned short *) &ra->msg4_rrc_sdu_length, // &lcid, // sdu_lcid 255, // no drx @@ -856,7 +856,7 @@ generate_Msg4(module_id_t module_idP, ra->cont_res_id, // contention res id msg4_padding, // no padding msg4_post_padding); - memcpy ((void *) &mac->UE_list.DLSCH_pdu[CC_idP][0][(unsigned char) UE_id].payload[0][(unsigned char) offset], &cc[CC_idP].CCCH_pdu.payload[0], ra->msg4_rrc_sdu_length); + memcpy ((void *) &mac->UE_info.DLSCH_pdu[CC_idP][0][(unsigned char) UE_id].payload[0][(unsigned char) offset], &cc[CC_idP].CCCH_pdu.payload[0], ra->msg4_rrc_sdu_length); // DL request mac->TX_req[CC_idP].sfn_sf = (frameP << 4) + subframeP; TX_req = &mac->TX_req[CC_idP].tx_request_body.tx_pdu_list[mac->TX_req[CC_idP].tx_request_body.number_of_pdus]; @@ -864,7 +864,7 @@ generate_Msg4(module_id_t module_idP, TX_req->pdu_index = mac->pdu_index[CC_idP]++; TX_req->num_segments = 1; TX_req->segments[0].segment_length = ra->msg4_TBsize; - TX_req->segments[0].segment_data = mac->UE_list.DLSCH_pdu[CC_idP][0][(unsigned char) UE_id].payload[0]; + TX_req->segments[0].segment_data = mac->UE_info.DLSCH_pdu[CC_idP][0][(unsigned char) UE_id].payload[0]; mac->TX_req[CC_idP].tx_request_body.number_of_pdus++; // Program ACK/NAK for Msg4 PDSCH int absSF = (frameP * 10) + subframeP; @@ -899,8 +899,8 @@ generate_Msg4(module_id_t module_idP, ul_req_body->number_of_pdus++; T (T_ENB_MAC_UE_DL_PDU_WITH_DATA, T_INT (module_idP), T_INT (CC_idP), T_INT (ra->rnti), T_INT (frameP), T_INT (subframeP), - T_INT (0 /*harq_pid always 0? */ ), T_BUFFER (&mac->UE_list.DLSCH_pdu[CC_idP][0][UE_id].payload[0], ra->msg4_TBsize)); - trace_pdu (DIRECTION_DOWNLINK, (uint8_t *) mac->UE_list.DLSCH_pdu[CC_idP][0][(unsigned char) UE_id].payload[0], + T_INT (0 /*harq_pid always 0? */ ), T_BUFFER (&mac->UE_info.DLSCH_pdu[CC_idP][0][UE_id].payload[0], ra->msg4_TBsize)); + trace_pdu (DIRECTION_DOWNLINK, (uint8_t *) mac->UE_info.DLSCH_pdu[CC_idP][0][(unsigned char) UE_id].payload[0], ra->msg4_rrc_sdu_length, UE_id, 3, UE_RNTI (module_idP, UE_id), mac->frame, mac->subframe, 0, 0); @@ -963,10 +963,10 @@ generate_Msg4(module_id_t module_idP, 1, // tpc, none getRIV(N_RB_DL, first_rb, 4), // resource_block_coding ra->msg4_mcs, // mcs - 1 - UE_list->UE_template[CC_idP][UE_id].oldNDI[ra->harq_pid], + 1 - UE_info->UE_template[CC_idP][UE_id].oldNDI[ra->harq_pid], 0, // rv 0); // vrb_flag - UE_list->UE_template[CC_idP][UE_id].oldNDI[ra->harq_pid] = 1 - UE_list->UE_template[CC_idP][UE_id].oldNDI[ra->harq_pid]; + UE_info->UE_template[CC_idP][UE_id].oldNDI[ra->harq_pid] = 1 - UE_info->UE_template[CC_idP][UE_id].oldNDI[ra->harq_pid]; LOG_D(MAC, "Frame %d, subframe %d: Msg4 DCI pdu_num %d (rnti %x,rnti_type %d,harq_pid %d, resource_block_coding (%p) %d\n", frameP, subframeP, dl_req_body->number_pdu, @@ -1000,7 +1000,7 @@ generate_Msg4(module_id_t module_idP, lcid = 0; // put HARQ process round to 0 ra->harq_pid = frame_subframe2_dl_harq_pid(cc->tdd_Config,frameP,subframeP); - UE_list->UE_sched_ctrl[UE_id].round[CC_idP][ra->harq_pid] = 0; + UE_info->UE_sched_ctrl[UE_id].round[CC_idP][ra->harq_pid] = 0; if ((ra->msg4_TBsize - rrc_sdu_length - msg4_header) <= 2) { msg4_padding = ra->msg4_TBsize - rrc_sdu_length - msg4_header; @@ -1018,7 +1018,7 @@ generate_Msg4(module_id_t module_idP, DevAssert(UE_id != UE_INDEX_INVALID); // FIXME not sure how to gracefully return // CHECK THIS: &cc[CC_idP].CCCH_pdu.payload[0] int num_sdus = rrc_sdu_length > 0 ? 1 : 0; - offset = generate_dlsch_header((unsigned char *) mac->UE_list.DLSCH_pdu[CC_idP][0][(unsigned char) UE_id].payload[0], + offset = generate_dlsch_header((unsigned char *) mac->UE_info.DLSCH_pdu[CC_idP][0][(unsigned char) UE_id].payload[0], num_sdus, //num_sdus (unsigned short *) &rrc_sdu_length, // &lcid, // sdu_lcid @@ -1027,10 +1027,14 @@ generate_Msg4(module_id_t module_idP, ra->cont_res_id, // contention res id msg4_padding, // no padding msg4_post_padding); - memcpy((void *) &mac->UE_list.DLSCH_pdu[CC_idP][0][(unsigned char)UE_id].payload[0][(unsigned char)offset], + memcpy((void *) &mac->UE_info.DLSCH_pdu[CC_idP][0][(unsigned char)UE_id].payload[0][(unsigned char)offset], &cc[CC_idP].CCCH_pdu.payload[0], rrc_sdu_length); // DLSCH Config - fill_nfapi_dlsch_config(mac, dl_req_body, ra->msg4_TBsize, mac->pdu_index[CC_idP], ra->rnti, 2, // resource_allocation_type : format 1A/1B/1D + fill_nfapi_dlsch_config(&dl_req_body->dl_config_pdu_list[dl_req_body->number_pdu], + ra->msg4_TBsize, + mac->pdu_index[CC_idP], + ra->rnti, + 2, // resource_allocation_type : format 1A/1B/1D 0, // virtual_resource_block_assignment_flag : localized getRIV(N_RB_DL, first_rb, 4), // resource_block_coding : RIV, 4 PRB 2, // modulation: QPSK @@ -1049,6 +1053,7 @@ generate_Msg4(module_id_t module_idP, (cc->p_eNB == 1) ? 1 : 2, // transmission mode 1, // num_bf_prb_per_subband 1); // num_bf_vector + dl_req_body->number_pdu++; LOG_D(MAC, "Filled DLSCH config, pdu number %d, non-dci pdu_index %d\n", dl_req_body->number_pdu, mac->pdu_index[CC_idP]); @@ -1058,7 +1063,7 @@ generate_Msg4(module_id_t module_idP, (frameP * 10) + subframeP, rrc_sdu_length+offset, mac->pdu_index[CC_idP], - mac->UE_list. + mac->UE_info. DLSCH_pdu[CC_idP][0][(unsigned char)UE_id].payload[0]); mac->pdu_index[CC_idP]++; dl_req->sfn_sf = mac->TX_req[CC_idP].sfn_sf; @@ -1074,11 +1079,11 @@ generate_Msg4(module_id_t module_idP, T(T_ENB_MAC_UE_DL_PDU_WITH_DATA, T_INT(module_idP), T_INT(CC_idP), T_INT(ra->rnti), T_INT(frameP), T_INT(subframeP), T_INT(0 /*harq_pid always 0? */ ), - T_BUFFER(&mac->UE_list.DLSCH_pdu[CC_idP][0][UE_id]. + T_BUFFER(&mac->UE_info.DLSCH_pdu[CC_idP][0][UE_id]. payload[0], ra->msg4_TBsize)); trace_pdu(DIRECTION_DOWNLINK, (uint8_t *) mac-> - UE_list.DLSCH_pdu[CC_idP][0][(unsigned char)UE_id].payload[0], + UE_info.DLSCH_pdu[CC_idP][0][(unsigned char)UE_id].payload[0], rrc_sdu_length, UE_id, WS_C_RNTI, UE_RNTI(module_idP, UE_id), mac->frame, mac->subframe, 0, 0); @@ -1116,14 +1121,14 @@ check_Msg4_retransmission(module_id_t module_idP, int CC_idP, int first_rb; int N_RB_DL; nfapi_dl_config_request_pdu_t *dl_config_pdu; - UE_list_t *UE_list = &mac->UE_list; + UE_info_t *UE_info = &mac->UE_info; nfapi_dl_config_request_t *dl_req; nfapi_dl_config_request_body_t *dl_req_body; int round; // check HARQ status and retransmit if necessary UE_id = find_UE_id(module_idP, ra->rnti); AssertFatal(UE_id >= 0, "Can't find UE for t-crnti\n"); - round = UE_list->UE_sched_ctrl[UE_id].round[CC_idP][ra->harq_pid]; + round = UE_info->UE_sched_ctrl[UE_id].round[CC_idP][ra->harq_pid]; vrb_map = cc[CC_idP].vrb_map; dl_req = &mac->DL_req[CC_idP]; dl_req_body = &dl_req->dl_config_request_body; @@ -1156,7 +1161,7 @@ check_Msg4_retransmission(module_id_t module_idP, int CC_idP, 1, // tpc, none getRIV(N_RB_DL, first_rb, 4), // resource_block_coding ra->msg4_mcs, // mcs - UE_list->UE_template[CC_idP][UE_id].oldNDI[ra->harq_pid], + UE_info->UE_template[CC_idP][UE_id].oldNDI[ra->harq_pid], round & 3, // rv 0); // vrb_flag @@ -1173,7 +1178,8 @@ check_Msg4_retransmission(module_id_t module_idP, int CC_idP, // DLSCH Config //DJP - fix this pdu_index = -1 LOG_D(MAC, "check_Msg4_retransmission() before fill_nfapi_dlsch_config() with pdu_index = -1 \n"); - fill_nfapi_dlsch_config(mac, dl_req_body, ra->msg4_TBsize, + fill_nfapi_dlsch_config(&dl_req_body->dl_config_pdu_list[dl_req_body->number_pdu], + ra->msg4_TBsize, -1 /* retransmission, no pdu_index */ , ra->rnti, 2, // resource_allocation_type : format 1A/1B/1D @@ -1195,6 +1201,7 @@ check_Msg4_retransmission(module_id_t module_idP, int CC_idP, (cc->p_eNB == 1) ? 1 : 2, // transmission mode 1, // num_bf_prb_per_subband 1); // num_bf_vector + dl_req_body->number_pdu++; if(RC.mac[module_idP]->scheduler_mode == SCHED_MODE_FAIR_RR) { set_dl_ue_select_msg4(CC_idP, 4, UE_id, ra->rnti); @@ -1226,8 +1233,8 @@ check_Msg4_retransmission(module_id_t module_idP, int CC_idP, LOG_D(MAC,"[eNB %d][RAPROC] Frame %d, Subframe %d: state:IDLE\n", module_idP, frameP, subframeP); UE_id = find_UE_id(module_idP, ra->rnti); DevAssert(UE_id != -1); - mac->UE_list.UE_template[UE_PCCID(module_idP, UE_id)][UE_id].configured = TRUE; - mac->UE_list.UE_template[UE_PCCID(module_idP, UE_id)][UE_id].pusch_repetition_levels=ra->pusch_repetition_levels; + mac->UE_info.UE_template[UE_PCCID(module_idP, UE_id)][UE_id].configured = TRUE; + mac->UE_info.UE_template[UE_PCCID(module_idP, UE_id)][UE_id].pusch_repetition_levels=ra->pusch_repetition_levels; cancel_ra_proc(module_idP, CC_idP, frameP, ra->rnti); } } diff --git a/openair2/LAYER2/MAC/eNB_scheduler_dlsch.c b/openair2/LAYER2/MAC/eNB_scheduler_dlsch.c index eba4bdcee992525d6e1ef420111962c3ed90c1ef..7621994ab2e1f247011f7ea7d03db1ef298d32be 100644 --- a/openair2/LAYER2/MAC/eNB_scheduler_dlsch.c +++ b/openair2/LAYER2/MAC/eNB_scheduler_dlsch.c @@ -86,31 +86,6 @@ add_ue_dlsch_info(module_id_t module_idP, return; } -//------------------------------------------------------------------------------ -int -schedule_next_dlue(module_id_t module_idP, - int CC_id, - sub_frame_t subframeP) -//------------------------------------------------------------------------------ -{ - int next_ue; - UE_list_t *UE_list = &RC.mac[module_idP]->UE_list; - - for (next_ue = UE_list->head; next_ue >= 0; next_ue = UE_list->next[next_ue]) { - if (eNB_dlsch_info[module_idP][CC_id][next_ue].status == S_DL_WAITING) { - return next_ue; - } - } - - for (next_ue = UE_list->head; next_ue >= 0; next_ue = UE_list->next[next_ue]) { - if (eNB_dlsch_info[module_idP][CC_id][next_ue].status == S_DL_BUFFERED) { - eNB_dlsch_info[module_idP][CC_id][next_ue].status = S_DL_WAITING; - } - } - - return (-1); //next_ue; -} - //------------------------------------------------------------------------------ int generate_dlsch_header(unsigned char *mac_header, @@ -317,12 +292,12 @@ set_ul_DAI(int module_idP, //------------------------------------------------------------------------------ { eNB_MAC_INST *eNB = RC.mac[module_idP]; - UE_list_t *UE_list = &eNB->UE_list; + UE_info_t *UE_info = &eNB->UE_info; unsigned char DAI; COMMON_channels_t *cc = &eNB->common_channels[CC_idP]; if (cc->tdd_Config != NULL) { //TDD - DAI = (UE_list->UE_template[CC_idP][UE_idP].DAI - 1) & 3; + DAI = (UE_info->UE_template[CC_idP][UE_idP].DAI - 1) & 3; LOG_D(MAC, "[eNB %d] CC_id %d Frame %d, subframe %d: DAI %d for UE %d\n", module_idP, CC_idP, @@ -341,20 +316,20 @@ set_ul_DAI(int module_idP, switch (subframeP) { case 0: case 1: - UE_list->UE_template[CC_idP][UE_idP].DAI_ul[7] = DAI; + UE_info->UE_template[CC_idP][UE_idP].DAI_ul[7] = DAI; break; case 4: - UE_list->UE_template[CC_idP][UE_idP].DAI_ul[8] = DAI; + UE_info->UE_template[CC_idP][UE_idP].DAI_ul[8] = DAI; break; case 5: case 6: - UE_list->UE_template[CC_idP][UE_idP].DAI_ul[2] = DAI; + UE_info->UE_template[CC_idP][UE_idP].DAI_ul[2] = DAI; break; case 9: - UE_list->UE_template[CC_idP][UE_idP].DAI_ul[3] = DAI; + UE_info->UE_template[CC_idP][UE_idP].DAI_ul[3] = DAI; break; } @@ -362,30 +337,30 @@ set_ul_DAI(int module_idP, case 2: // if ((subframeP==3)||(subframeP==8)) - // UE_list->UE_template[CC_idP][UE_idP].DAI_ul = DAI; + // UE_info->UE_template[CC_idP][UE_idP].DAI_ul = DAI; break; case 3: //if ((subframeP==6)||(subframeP==8)||(subframeP==0)) { // LOG_D(MAC,"schedule_ue_spec: setting UL DAI to %d for subframeP %d => %d\n",DAI,subframeP, ((subframeP+8)%10)>>1); - // UE_list->UE_template[CC_idP][UE_idP].DAI_ul[((subframeP+8)%10)>>1] = DAI; + // UE_info->UE_template[CC_idP][UE_idP].DAI_ul[((subframeP+8)%10)>>1] = DAI; //} switch (subframeP) { case 5: case 6: case 1: - UE_list->UE_template[CC_idP][UE_idP].DAI_ul[2] = DAI; + UE_info->UE_template[CC_idP][UE_idP].DAI_ul[2] = DAI; break; case 7: case 8: - UE_list->UE_template[CC_idP][UE_idP].DAI_ul[3] = DAI; + UE_info->UE_template[CC_idP][UE_idP].DAI_ul[3] = DAI; break; case 9: case 0: - UE_list->UE_template[CC_idP][UE_idP].DAI_ul[4] = DAI; + UE_info->UE_template[CC_idP][UE_idP].DAI_ul[4] = DAI; break; default: @@ -396,17 +371,17 @@ set_ul_DAI(int module_idP, case 4: // if ((subframeP==8)||(subframeP==9)) - // UE_list->UE_template[CC_idP][UE_idP].DAI_ul = DAI; + // UE_info->UE_template[CC_idP][UE_idP].DAI_ul = DAI; break; case 5: // if (subframeP==8) - // UE_list->UE_template[CC_idP][UE_idP].DAI_ul = DAI; + // UE_info->UE_template[CC_idP][UE_idP].DAI_ul = DAI; break; case 6: // if ((subframeP==1)||(subframeP==4)||(subframeP==6)||(subframeP==9)) - // UE_list->UE_template[CC_idP][UE_idP].DAI_ul = DAI; + // UE_info->UE_template[CC_idP][UE_idP].DAI_ul = DAI; break; default: @@ -417,20 +392,129 @@ set_ul_DAI(int module_idP, return; } +void ue_rrc_release(rnti_t rnti) { + if(rrc_release_info.num_UEs == 0 || rlc_am_mui.rrc_mui_num == 0) { + return; + } + + while(pthread_mutex_trylock(&rrc_release_freelist)) { + /* spin... */ + } + + uint16_t release_total = 0; + + for (uint16_t n = 0; n < NUMBER_OF_UE_MAX; n++) { + RRC_release_ctrl_t *release_ctrl = &rrc_release_info.RRC_release_ctrl[n]; + if(release_ctrl->flag == 0) + continue; + + release_total++; + if(release_ctrl->flag == 1 && release_ctrl->rnti == rnti) { + for(uint16_t mui_num = 0; mui_num < rlc_am_mui.rrc_mui_num; mui_num++) { + if(release_ctrl->rrc_eNB_mui == rlc_am_mui.rrc_mui[mui_num]) { + release_ctrl->flag = 3; + LOG_D(MAC, + "DLSCH Release send:index %d rnti %x mui %d mui_num %d flag 1->3\n", + n, rnti, rlc_am_mui.rrc_mui[mui_num], mui_num); + break; + } + } + } + + if(release_ctrl->flag == 2 && release_ctrl->rnti == rnti) { + for (uint16_t mui_num = 0; mui_num < rlc_am_mui.rrc_mui_num; mui_num++) { + if(release_ctrl->rrc_eNB_mui == rlc_am_mui.rrc_mui[mui_num]) { + release_ctrl->flag = 4; + LOG_D(MAC, "DLSCH Release send:index %d rnti %x mui %d mui_num %d flag 2->4\n", + n, + rnti, + rlc_am_mui.rrc_mui[mui_num], + mui_num); + break; + } + } + } + + if(release_total >= rrc_release_info.num_UEs) + break; + } + + pthread_mutex_unlock(&rrc_release_freelist); +} + +void check_ra_rnti_mui(module_id_t mod_id, int CC_id, frame_t f, sub_frame_t sf, rnti_t rnti) { + LTE_TDD_Config_t *tdd_config = RC.mac[mod_id]->common_channels[CC_id].tdd_Config; + int harq_pid = frame_subframe2_dl_harq_pid(tdd_config, f, sf); + RA_t *ra = &RC.mac[mod_id]->common_channels[CC_id].ra[0]; + for (uint8_t ra_ii = 0; ra_ii < NB_RA_PROC_MAX; ra_ii++, ra++) { + if ((ra->rnti == rnti) && (ra->state == MSGCRNTI)) { + for (uint16_t mui_num = 0; mui_num < rlc_am_mui.rrc_mui_num; mui_num++) { + if (ra->crnti_rrc_mui == rlc_am_mui.rrc_mui[mui_num]) { + ra->crnti_harq_pid = harq_pid; + ra->state = MSGCRNTI_ACK; + break; + } + } + } + } +} + //------------------------------------------------------------------------------ void schedule_dlsch(module_id_t module_idP, frame_t frameP, sub_frame_t subframeP, int *mbsfn_flag) { - int i = 0; - slice_info_t *sli = &RC.mac[module_idP]->slice_info; - memset(sli->rballoc_sub, 0, sizeof(sli->rballoc_sub)); - - for (i = 0; i < sli->n_dl; i++) { - // Run each enabled slice-specific schedulers one by one - sli->dl[i].sched_cb(module_idP, - i, - frameP, - subframeP, - mbsfn_flag/*, dl_info*/); + if (is_pmch_subframe(frameP, subframeP, &RC.eNB[module_idP][0]->frame_parms)) + return; + + for (int CC_id = 0; CC_id < RC.nb_mac_CC[module_idP]; CC_id++) { + // for TDD: check that we have to act here, otherwise skip + COMMON_channels_t *cc = &RC.mac[module_idP]->common_channels[CC_id]; + if (cc->tdd_Config) { + int tdd_sfa = cc->tdd_Config->subframeAssignment; + + switch (subframeP) { + case 0: + // always continue + break; + + case 1: + case 2: + continue; + + case 3: + if (tdd_sfa != 2 && tdd_sfa != 5) + continue; + break; + + case 4: + if (tdd_sfa != 1 && tdd_sfa != 2 && tdd_sfa != 4 && tdd_sfa != 5) + continue; + break; + + case 5: + break; + + case 6: + case 7: + if (tdd_sfa != 3 && tdd_sfa != 4 && tdd_sfa != 5) + continue; + break; + + case 8: + if (tdd_sfa != 2 && tdd_sfa != 3 && tdd_sfa != 4 && tdd_sfa != 5) + continue; + break; + + case 9: + if (tdd_sfa == 0) + continue; + break; + } + } + + if (mbsfn_flag[CC_id] != 0) + continue; + + schedule_ue_spec(module_idP, CC_id, frameP, subframeP); } } @@ -454,138 +538,35 @@ void getRepetition(UE_TEMPLATE *pue_template,unsigned int *maxRep, unsigned int */ void schedule_ue_spec(module_id_t module_idP, - int slice_idxP, + int CC_id, frame_t frameP, - sub_frame_t subframeP, - int *mbsfn_flag) + sub_frame_t subframeP) //------------------------------------------------------------------------------ { - int CC_id; - int UE_id; - int aggregation; - mac_rlc_status_resp_t rlc_status; - int ta_len = 0; - unsigned char sdu_lcids[NB_RB_MAX]; - int lcid, offset, num_sdus = 0; - int nb_rb, nb_rb_temp, nb_available_rb; - uint16_t sdu_lengths[NB_RB_MAX]; - int TBS, j, padding = 0, post_padding = 0; - rnti_t rnti; unsigned char dlsch_buffer[MAX_DLSCH_PAYLOAD_BYTES]; - int round_DL = 0; - int harq_pid = 0; - uint16_t release_num; - uint8_t ra_ii; - eNB_UE_STATS *eNB_UE_stats = NULL; - UE_TEMPLATE *ue_template = NULL; - eNB_STATS *eNB_stats = NULL; - RRC_release_ctrl_t *release_ctrl = NULL; - DLSCH_PDU *dlsch_pdu = NULL; - RA_t *ra = NULL; - int sdu_length_total = 0; eNB_MAC_INST *eNB = RC.mac[module_idP]; COMMON_channels_t *cc = eNB->common_channels; - UE_list_t *UE_list = &eNB->UE_list; - int continue_flag = 0; - int32_t snr, target_snr; - int tpc = 1; - UE_sched_ctrl_t *ue_sched_ctrl; - int mcs; - int i; - int min_rb_unit[NFAPI_CC_MAX]; - int N_RB_DL[NFAPI_CC_MAX]; - int total_nb_available_rb[NFAPI_CC_MAX]; - int N_RBG[NFAPI_CC_MAX]; - nfapi_dl_config_request_body_t *dl_req; - nfapi_dl_config_request_pdu_t *dl_config_pdu; - int tdd_sfa; - int ta_update; - int header_length_last; - int header_length_total; - rrc_eNB_ue_context_t *ue_contextP = NULL; - int nb_mac_CC = RC.nb_mac_CC[module_idP]; - long dl_Bandwidth; - - if(is_pmch_subframe(frameP,subframeP,&RC.eNB[module_idP][0]->frame_parms)){ - //LOG_E(MAC,"Frame[%d] SF:%d This SF should not be allocated\n",frameP,subframeP); - return ; - } - + UE_info_t *UE_info = &eNB->UE_info; + const int dl_Bandwidth = cc[CC_id].mib->message.dl_Bandwidth; + const int N_RB_DL = to_prb(dl_Bandwidth); + const int N_RBG = to_rbg(eNB->common_channels[CC_id].mib->message.dl_Bandwidth); + int total_nb_available_rb = N_RB_DL; + nfapi_dl_config_request_body_t *dl_req = &eNB->DL_req[CC_id].dl_config_request_body; start_meas(&eNB->schedule_dlsch); VCD_SIGNAL_DUMPER_DUMP_FUNCTION_BY_NAME(VCD_SIGNAL_DUMPER_FUNCTIONS_SCHEDULE_DLSCH, VCD_FUNCTION_IN); - // for TDD: check that we have to act here, otherwise return - if (cc[0].tdd_Config) { - tdd_sfa = cc[0].tdd_Config->subframeAssignment; - - switch (subframeP) { - case 0: - // always continue - break; - - case 1: - case 2: - return; - - case 3: - if (tdd_sfa != 2 && tdd_sfa != 5) - return; - - break; - - case 4: - if (tdd_sfa != 1 && tdd_sfa != 2 && tdd_sfa != 4 && tdd_sfa != 5) - return; - - break; - - case 5: - break; - - case 6: - case 7: - if (tdd_sfa != 3 && tdd_sfa != 4 && tdd_sfa != 5) - return; - - break; - - case 8: - if (tdd_sfa != 2 && tdd_sfa != 3 && tdd_sfa != 4 && tdd_sfa != 5) - return; - - break; - - case 9: - if (tdd_sfa == 0) - return; - - break; - } - } + for (int i = 0; i < N_RB_DL; i++) + if (cc[CC_id].vrb_map[i] != 0) + total_nb_available_rb--; - aggregation = 2; - - for (CC_id = 0, eNB_stats = &eNB->eNB_stats[0]; CC_id < nb_mac_CC; CC_id++, eNB_stats++) { - dl_Bandwidth = cc[CC_id].mib->message.dl_Bandwidth; - N_RB_DL[CC_id] = to_prb(dl_Bandwidth); - min_rb_unit[CC_id] = get_min_rb_unit(module_idP, CC_id); - // get number of PRBs less those used by common channels - total_nb_available_rb[CC_id] = N_RB_DL[CC_id]; - - for (i = 0; i < N_RB_DL[CC_id]; i++) - if (cc[CC_id].vrb_map[i] != 0) - total_nb_available_rb[CC_id]--; - - N_RBG[CC_id] = to_rbg(dl_Bandwidth); - // store the global enb stats: - eNB_stats->num_dlactive_UEs = UE_list->num_UEs; - eNB_stats->available_prbs = total_nb_available_rb[CC_id]; - eNB_stats->total_available_prbs += total_nb_available_rb[CC_id]; - eNB_stats->dlsch_bytes_tx = 0; - eNB_stats->dlsch_pdus_tx = 0; - } + // store the global enb stats: + eNB->eNB_stats[CC_id].num_dlactive_UEs = UE_info->num_UEs; + eNB->eNB_stats[CC_id].available_prbs = total_nb_available_rb; + eNB->eNB_stats[CC_id].total_available_prbs += total_nb_available_rb; + eNB->eNB_stats[CC_id].dlsch_bytes_tx = 0; + eNB->eNB_stats[CC_id].dlsch_pdus_tx = 0; // CALLING Pre_Processor for downlink scheduling // (Returns estimation of RBs required by each UE and the allocation on sub-band) @@ -593,1257 +574,624 @@ schedule_ue_spec(module_id_t module_idP, VCD_FUNCTION_IN); start_meas(&eNB->schedule_dlsch_preprocessor); dlsch_scheduler_pre_processor(module_idP, - slice_idxP, + CC_id, frameP, - subframeP, - mbsfn_flag, - eNB->slice_info.rballoc_sub); + subframeP); stop_meas(&eNB->schedule_dlsch_preprocessor); VCD_SIGNAL_DUMPER_DUMP_FUNCTION_BY_NAME(VCD_SIGNAL_DUMPER_FUNCTIONS_DLSCH_PREPROCESSOR, VCD_FUNCTION_OUT); - if (RC.mac[module_idP]->slice_info.interslice_share_active) { - dlsch_scheduler_interslice_multiplexing(module_idP, - frameP, - subframeP, - eNB->slice_info.rballoc_sub); - /* the interslice multiplexing re-sorts the UE_list for the slices it tries - * to multiplex, so we need to sort it for the current slice again */ - sort_UEs(module_idP, - slice_idxP, - frameP, - subframeP); - } - - for (CC_id = 0; CC_id < nb_mac_CC; CC_id++) { - LOG_D(MAC, "doing schedule_ue_spec for CC_id %d\n", - CC_id); - dl_req = &eNB->DL_req[CC_id].dl_config_request_body; - - if (mbsfn_flag[CC_id] > 0) - continue; - - for (UE_id = UE_list->head; UE_id >= 0; UE_id = UE_list->next[UE_id]) { - LOG_D(MAC, "doing schedule_ue_spec for CC_id %d UE %d\n", - CC_id, - UE_id); - continue_flag = 0; // reset the flag to allow allocation for the remaining UEs - rnti = UE_RNTI(module_idP, UE_id); - ue_sched_ctrl = &UE_list->UE_sched_ctrl[UE_id]; - ue_template = &UE_list->UE_template[CC_id][UE_id]; - - if (ue_template->rach_resource_type > 0) { - continue_flag = 1; - } - - if (&(UE_list->eNB_UE_stats[CC_id][UE_id]) == NULL) { - LOG_D(MAC, "[eNB] Cannot find eNB_UE_stats\n"); - continue_flag = 1; - } else { - eNB_UE_stats = &(UE_list->eNB_UE_stats[CC_id][UE_id]); - } - - if (continue_flag != 1) { - switch (get_tmode(module_idP, - CC_id, - UE_id)) { - case 1: - case 2: - case 7: - aggregation = get_aggregation(get_bw_index(module_idP, - CC_id), - ue_sched_ctrl->dl_cqi[CC_id], - format1); - break; - - case 3: - aggregation = get_aggregation(get_bw_index(module_idP, - CC_id), - ue_sched_ctrl->dl_cqi[CC_id], - format2A); - break; - - default: - AssertFatal(1==0,"Unsupported transmission mode %d\n", get_tmode(module_idP, CC_id, UE_id)); - aggregation = 2; - break; - } - } - - /* if (continue_flag != 1 */ - if (ue_sched_ctrl->pre_nb_available_rbs[CC_id] == 0 || // no RBs allocated - CCE_allocation_infeasible(module_idP, - CC_id, - 1, - subframeP, - aggregation, - rnti)) { - LOG_D(MAC, "[eNB %d] Frame %d : no RB allocated for UE %d on CC_id %d: continue \n", - module_idP, - frameP, - UE_id, - CC_id); - continue_flag = 1; //to next user (there might be rbs availiable for other UEs in TM5 - } - - // If TDD - if (cc[CC_id].tdd_Config != NULL) { //TDD - set_ue_dai(subframeP, - UE_id, - CC_id, - cc[CC_id].tdd_Config->subframeAssignment, - UE_list); - // update UL DAI after DLSCH scheduling - set_ul_DAI(module_idP, - UE_id, - CC_id, - frameP, - subframeP); - } - - if (continue_flag == 1) { - add_ue_dlsch_info(module_idP, - CC_id, - UE_id, - subframeP, - S_DL_NONE, - rnti); - continue; - } - - nb_available_rb = ue_sched_ctrl->pre_nb_available_rbs[CC_id]; - harq_pid = frame_subframe2_dl_harq_pid(cc->tdd_Config, - frameP, - subframeP); - round_DL = ue_sched_ctrl->round[CC_id][harq_pid]; - eNB_UE_stats->crnti = rnti; - eNB_UE_stats->rrc_status = mac_eNB_get_rrc_status(module_idP, rnti); - eNB_UE_stats->harq_pid = harq_pid; - eNB_UE_stats->harq_round = round_DL; - - if (eNB_UE_stats->rrc_status < RRC_RECONFIGURED) { - ue_sched_ctrl->uplane_inactivity_timer = 0; - } - - if (eNB_UE_stats->rrc_status < RRC_CONNECTED) { - LOG_D(MAC, "UE %d is not in RRC_CONNECTED\n", UE_id); - continue; - } - - header_length_total = 0; - sdu_length_total = 0; - num_sdus = 0; - - /* - DevCheck(((eNB_UE_stats->dl_cqi < MIN_CQI_VALUE) || - (eNB_UE_stats->dl_cqi > MAX_CQI_VALUE)), - eNB_UE_stats->dl_cqi, MIN_CQI_VALUE, MAX_CQI_VALUE); - */ - if (NFAPI_MODE != NFAPI_MONOLITHIC) { - eNB_UE_stats->dlsch_mcs1 = cqi_to_mcs[ue_sched_ctrl->dl_cqi[CC_id]]; - } else { // this operation is also done in the preprocessor - eNB_UE_stats->dlsch_mcs1 = cmin(eNB_UE_stats->dlsch_mcs1, - eNB->slice_info.dl[slice_idxP].maxmcs); // cmin(eNB_UE_stats->dlsch_mcs1, openair_daq_vars.target_ue_dl_mcs); - } - - // Store stats - // eNB_UE_stats->dl_cqi= eNB_UE_stats->dl_cqi; - - // Initializing the rb allocation indicator for each UE - for (j = 0; j < N_RBG[CC_id]; j++) { - ue_template->rballoc_subband[harq_pid][j] = 0; - } - - LOG_D(MAC, "[eNB %d] Frame %d: Scheduling UE %d on CC_id %d (rnti %x, harq_pid %d, round %d, rb %d, cqi %d, mcs %d, rrc %d)\n", - module_idP, - frameP, - UE_id, - CC_id, - rnti, - harq_pid, - round_DL, - nb_available_rb, - ue_sched_ctrl->dl_cqi[CC_id], - eNB_UE_stats->dlsch_mcs1, - eNB_UE_stats->rrc_status); - - /* Process retransmission */ - if (round_DL != 8) { - // get freq_allocation - nb_rb = ue_template->nb_rb[harq_pid]; - TBS = get_TBS_DL(ue_template->oldmcs1[harq_pid], - nb_rb); - - if (nb_rb <= nb_available_rb) { - /* CDRX */ - ue_sched_ctrl->harq_rtt_timer[CC_id][harq_pid] = 1; // restart HARQ RTT timer - - if (ue_sched_ctrl->cdrx_configured) { - ue_sched_ctrl->drx_retransmission_timer[harq_pid] = 0; // stop drx retransmission - - /* - * Note: contrary to the spec drx_retransmission_timer[harq_pid] is reset not stop. - */ - if (harq_pid == 0) { - VCD_SIGNAL_DUMPER_DUMP_VARIABLE_BY_NAME(VCD_SIGNAL_DUMPER_VARIABLES_DRX_RETRANSMISSION_HARQ0, (unsigned long) ue_sched_ctrl->drx_retransmission_timer[0]); - } - } - - if (cc[CC_id].tdd_Config != NULL) { - ue_template->DAI++; - update_ul_dci(module_idP, - CC_id, - rnti, - ue_template->DAI, - subframeP); - LOG_D(MAC, "DAI update: CC_id %d subframeP %d: UE %d, DAI %d\n", - CC_id, - subframeP, - UE_id, - ue_template->DAI); - } - - if (nb_rb == ue_sched_ctrl->pre_nb_available_rbs[CC_id]) { - for (j = 0; j < N_RBG[CC_id]; j++) { // for indicating the rballoc for each sub-band - ue_template->rballoc_subband[harq_pid][j] = ue_sched_ctrl->rballoc_sub_UE[CC_id][j]; - } - } else { - nb_rb_temp = nb_rb; - j = 0; - - while ((nb_rb_temp > 0) && (j < N_RBG[CC_id])) { - if (ue_sched_ctrl->rballoc_sub_UE[CC_id][j] == 1) { - if (ue_template->rballoc_subband[harq_pid][j]) - LOG_W(MAC, "WARN: rballoc_subband not free for retrans?\n"); - - ue_template->rballoc_subband[harq_pid][j] = ue_sched_ctrl->rballoc_sub_UE[CC_id][j]; - nb_rb_temp -= min_rb_unit[CC_id]; - - if ((j == N_RBG[CC_id] - 1) && (N_RB_DL[CC_id] == 25 || N_RB_DL[CC_id] == 50)) - nb_rb_temp++; - } - - j++; - } - } - - nb_available_rb -= nb_rb; - - switch (get_tmode(module_idP, CC_id, UE_id)) { - case 1: - case 2: - case 7: - default: - LOG_D(MAC, "retransmission DL_REQ: rnti:%x\n", - rnti); - dl_config_pdu = &dl_req->dl_config_pdu_list[dl_req->number_pdu]; - memset((void *) dl_config_pdu, - 0, - sizeof(nfapi_dl_config_request_pdu_t)); - dl_config_pdu->pdu_type = NFAPI_DL_CONFIG_DCI_DL_PDU_TYPE; - dl_config_pdu->pdu_size = (uint8_t) (2 + sizeof(nfapi_dl_config_dci_dl_pdu)); - dl_config_pdu->dci_dl_pdu.dci_dl_pdu_rel8.tl.tag = NFAPI_DL_CONFIG_REQUEST_DCI_DL_PDU_REL8_TAG; - dl_config_pdu->dci_dl_pdu.dci_dl_pdu_rel8.dci_format = NFAPI_DL_DCI_FORMAT_1; - dl_config_pdu->dci_dl_pdu.dci_dl_pdu_rel8.aggregation_level = - get_aggregation(get_bw_index(module_idP, - CC_id), - ue_sched_ctrl->dl_cqi[CC_id], - format1); - dl_config_pdu->dci_dl_pdu.dci_dl_pdu_rel8.rnti = rnti; - dl_config_pdu->dci_dl_pdu.dci_dl_pdu_rel8.rnti_type = 1; // CRNTI: see Table 4-10 from SCF082 - nFAPI specifications - dl_config_pdu->dci_dl_pdu.dci_dl_pdu_rel8.transmission_power = 6000; // equal to RS power - dl_config_pdu->dci_dl_pdu.dci_dl_pdu_rel8.harq_process = harq_pid; - dl_config_pdu->dci_dl_pdu.dci_dl_pdu_rel8.tpc = 1; // Don't adjust power when retransmitting - dl_config_pdu->dci_dl_pdu.dci_dl_pdu_rel8.new_data_indicator_1 = ue_template->oldNDI[harq_pid]; - dl_config_pdu->dci_dl_pdu.dci_dl_pdu_rel8.mcs_1 = ue_template->oldmcs1[harq_pid]; - dl_config_pdu->dci_dl_pdu.dci_dl_pdu_rel8.redundancy_version_1 = round_DL & 3; - - // TDD - if (cc[CC_id].tdd_Config != NULL) { - dl_config_pdu->dci_dl_pdu.dci_dl_pdu_rel8.downlink_assignment_index = (ue_template->DAI - 1) & 3; - LOG_D(MAC, "[eNB %d] Retransmission CC_id %d : harq_pid %d, round %d, dai %d, mcs %d\n", - module_idP, - CC_id, - harq_pid, - round_DL, - ue_template->DAI - 1, - ue_template->oldmcs1[harq_pid]); - } else { - LOG_D(MAC, "[eNB %d] Retransmission CC_id %d : harq_pid %d, round %d, mcs %d\n", - module_idP, - CC_id, - harq_pid, - round_DL, - ue_template->oldmcs1[harq_pid]); - } - - if (!CCE_allocation_infeasible(module_idP, - CC_id, - 1, - subframeP, - dl_config_pdu->dci_dl_pdu.dci_dl_pdu_rel8.aggregation_level, - rnti)) { - dl_req->number_dci++; - dl_req->number_pdu++; - dl_req->tl.tag = NFAPI_DL_CONFIG_REQUEST_BODY_TAG; - eNB->DL_req[CC_id].sfn_sf = frameP<<4 | subframeP; - eNB->DL_req[CC_id].header.message_id = NFAPI_DL_CONFIG_REQUEST; - fill_nfapi_dlsch_config(eNB, - dl_req, - TBS, - -1, // retransmission, no pdu_index - rnti, - 0, // type 0 allocation from 7.1.6 in 36.213 - 0, // virtual_resource_block_assignment_flag, unused here - 0, // resource_block_coding, to be filled in later - getQm(ue_template->oldmcs1[harq_pid]), - round_DL & 3, // redundancy version - 1, // transport blocks - 0, // transport block to codeword swap flag - cc[CC_id].p_eNB == 1 ? 0 : 1, // transmission_scheme - 1, // number of layers - 1, // number of subbands - // uint8_t codebook_index, - 4, // UE category capacity - ue_template->physicalConfigDedicated->pdsch_ConfigDedicated->p_a, - 0, // delta_power_offset for TM5 - 0, // ngap - 0, // nprb - cc[CC_id].p_eNB == 1 ? 1 : 2, // transmission mode - 0, //number of PRBs treated as one subband, not used here - 0); // number of beamforming vectors, not used here - LOG_D(MAC, "Filled NFAPI configuration for DCI/DLSCH %d, retransmission round %d\n", - eNB->pdu_index[CC_id], - round_DL); - program_dlsch_acknak(module_idP, - CC_id, - UE_id, - frameP, - subframeP, - dl_config_pdu->dci_dl_pdu.dci_dl_pdu_rel8.cce_idx); - // No TX request for retransmission (check if null request for FAPI) - } else { - LOG_W(MAC, "Frame %d, Subframe %d: Dropping DLSCH allocation for UE %d\%x, infeasible CCE allocation\n", - frameP, - subframeP, - UE_id, - rnti); - } - } - - add_ue_dlsch_info(module_idP, - CC_id, UE_id, - subframeP, - S_DL_SCHEDULED, - rnti); - //eNB_UE_stats->dlsch_trials[round]++; - eNB_UE_stats->num_retransmission += 1; - eNB_UE_stats->rbs_used_retx = nb_rb; - eNB_UE_stats->total_rbs_used_retx += nb_rb; - eNB_UE_stats->dlsch_mcs2 = eNB_UE_stats->dlsch_mcs1; - } else { - LOG_D(MAC, - "[eNB %d] Frame %d CC_id %d : don't schedule UE %d, its retransmission takes more resources than we have\n", - module_idP, - frameP, - CC_id, - UE_id); - } - } else { - /* This is a potentially new SDU opportunity */ - rlc_status.bytes_in_buffer = 0; - // Now check RLC information to compute number of required RBs - // get maximum TBS size for RLC request - TBS = get_TBS_DL(eNB_UE_stats->dlsch_mcs1, - nb_available_rb); - - // add the length for all the control elements (timing adv, drx, etc) : header + payload - - if (ue_sched_ctrl->ta_timer == 0) { - ta_update = ue_sched_ctrl->ta_update; - - /* if we send TA then set timer to not send it for a while */ - if (ta_update != 31) { - ue_sched_ctrl->ta_timer = 20; - } - - /* reset ta_update */ - ue_sched_ctrl->ta_update = 31; - } else { - ta_update = 31; - } - - ta_len = (ta_update != 31) ? 2 : 0; - - // RLC data on DCCH - if (TBS - ta_len - header_length_total - sdu_length_total - 3 > 0) { - rlc_status = mac_rlc_status_ind(module_idP, - rnti, - module_idP, - frameP, - subframeP, - ENB_FLAG_YES, - MBMS_FLAG_NO, - DCCH, - TBS - ta_len - header_length_total - sdu_length_total - 3, 0, 0 - ); - sdu_lengths[0] = 0; - - if (rlc_status.bytes_in_buffer > 0) { - LOG_D(MAC, "[eNB %d] SFN/SF %d.%d, DL-DCCH->DLSCH CC_id %d, Requesting %d bytes from RLC (RRC message)\n", - module_idP, - frameP, - subframeP, - CC_id, - TBS - ta_len - header_length_total - sdu_length_total - 3); - sdu_lengths[0] = mac_rlc_data_req(module_idP, - rnti, - module_idP, - frameP, - ENB_FLAG_YES, - MBMS_FLAG_NO, - DCCH, - TBS, //not used - (char *)&dlsch_buffer[0], 0, 0 - ); - - if((rrc_release_info.num_UEs > 0) && (rlc_am_mui.rrc_mui_num > 0)) { - while(pthread_mutex_trylock(&rrc_release_freelist)) { - /* spin... */ - } - - uint16_t release_total = 0; - - for (release_num = 0, release_ctrl = &rrc_release_info.RRC_release_ctrl[0]; - release_num < NUMBER_OF_UE_MAX; - release_num++, release_ctrl++) { - if(release_ctrl->flag > 0) { - release_total++; - } else { - continue; - } - - if(release_ctrl->flag == 1) { - if(release_ctrl->rnti == rnti) { - for(uint16_t mui_num = 0; mui_num < rlc_am_mui.rrc_mui_num; mui_num++) { - if(release_ctrl->rrc_eNB_mui == rlc_am_mui.rrc_mui[mui_num]) { - release_ctrl->flag = 3; - LOG_D(MAC,"DLSCH Release send:index %d rnti %x mui %d mui_num %d flag 1->3\n", - release_num, - rnti, - rlc_am_mui.rrc_mui[mui_num], - mui_num); - break; - } - } - } - } - - if(release_ctrl->flag == 2) { - if(release_ctrl->rnti == rnti) { - for (uint16_t mui_num = 0; mui_num < rlc_am_mui.rrc_mui_num; mui_num++) { - if(release_ctrl->rrc_eNB_mui == rlc_am_mui.rrc_mui[mui_num]) { - release_ctrl->flag = 4; - LOG_D(MAC, "DLSCH Release send:index %d rnti %x mui %d mui_num %d flag 2->4\n", - release_num, - rnti, - rlc_am_mui.rrc_mui[mui_num], - mui_num); - break; - } - } - } - } - - if(release_total >= rrc_release_info.num_UEs) - break; - } - - pthread_mutex_unlock(&rrc_release_freelist); - } - - for (ra_ii = 0, ra = &eNB->common_channels[CC_id].ra[0]; ra_ii < NB_RA_PROC_MAX; ra_ii++, ra++) { - if ((ra->rnti == rnti) && (ra->state == MSGCRNTI)) { - for (uint16_t mui_num = 0; mui_num < rlc_am_mui.rrc_mui_num; mui_num++) { - if (ra->crnti_rrc_mui == rlc_am_mui.rrc_mui[mui_num]) { - ra->crnti_harq_pid = harq_pid; - ra->state = MSGCRNTI_ACK; - break; - } - } - } - } - - T(T_ENB_MAC_UE_DL_SDU, - T_INT(module_idP), - T_INT(CC_id), - T_INT(rnti), - T_INT(frameP), - T_INT(subframeP), - T_INT(harq_pid), - T_INT(DCCH), - T_INT(sdu_lengths[0])); - LOG_D(MAC, "[eNB %d][DCCH] CC_id %d Got %d bytes from RLC\n", - module_idP, - CC_id, - sdu_lengths[0]); - sdu_length_total = sdu_lengths[0]; - sdu_lcids[0] = DCCH; - eNB_UE_stats->lcid_sdu[0] = DCCH; - eNB_UE_stats->sdu_length_tx[DCCH] = sdu_lengths[0]; - eNB_UE_stats->num_pdu_tx[DCCH] += 1; - eNB_UE_stats->num_bytes_tx[DCCH] += sdu_lengths[0]; - header_length_last = 1 + 1 + (sdu_lengths[0] >= 128); - header_length_total += header_length_last; - num_sdus = 1; -#ifdef DEBUG_eNB_SCHEDULER - LOG_T(MAC, "[eNB %d][DCCH] CC_id %d Got %d bytes :", - module_idP, - CC_id, - sdu_lengths[0]); - - for (j = 0; j < sdu_lengths[0]; ++j) { - LOG_T(MAC, "%x ", - dlsch_buffer[j]); - } - - LOG_T(MAC, "\n"); -#endif - } - } - - // RLC data on DCCH1 - if (TBS - ta_len - header_length_total - sdu_length_total - 3 > 0) { - rlc_status = mac_rlc_status_ind(module_idP, - rnti, - module_idP, - frameP, - subframeP, - ENB_FLAG_YES, - MBMS_FLAG_NO, - DCCH + 1, - TBS - ta_len - header_length_total - sdu_length_total - 3, 0, 0 - ); - // DCCH SDU - sdu_lengths[num_sdus] = 0; - - if (rlc_status.bytes_in_buffer > 0) { - LOG_D(MAC, "[eNB %d], Frame %d, DCCH1->DLSCH, CC_id %d, Requesting %d bytes from RLC (RRC message)\n", - module_idP, frameP, CC_id, - TBS - ta_len - header_length_total - sdu_length_total - 3); - sdu_lengths[num_sdus] += mac_rlc_data_req(module_idP, - rnti, - module_idP, - frameP, - ENB_FLAG_YES, - MBMS_FLAG_NO, DCCH + 1, - TBS, //not used - (char *) &dlsch_buffer[sdu_length_total], 0, 0 - ); - T(T_ENB_MAC_UE_DL_SDU, - T_INT(module_idP), - T_INT(CC_id), - T_INT(rnti), - T_INT(frameP), - T_INT(subframeP), - T_INT(harq_pid), - T_INT(DCCH + 1), - T_INT(sdu_lengths[num_sdus])); - sdu_lcids[num_sdus] = DCCH1; - sdu_length_total += sdu_lengths[num_sdus]; - eNB_UE_stats->lcid_sdu[num_sdus] = DCCH1; - eNB_UE_stats->sdu_length_tx[DCCH1] = sdu_lengths[num_sdus]; - eNB_UE_stats->num_pdu_tx[DCCH1] += 1; - eNB_UE_stats->num_bytes_tx[DCCH1] += sdu_lengths[num_sdus]; - header_length_last = 1 + 1 + (sdu_lengths[num_sdus] >= 128); - header_length_total += header_length_last; - num_sdus++; -#ifdef DEBUG_eNB_SCHEDULER - LOG_T(MAC, "[eNB %d][DCCH1] CC_id %d Got %d bytes :", - module_idP, - CC_id, - sdu_lengths[num_sdus]); - - for (j = 0; j < sdu_lengths[num_sdus]; ++j) { - LOG_T(MAC, "%x ", - dlsch_buffer[j]); - } - - LOG_T(MAC, "\n"); -#endif - } - } - - // TODO: lcid has to be sorted before the actual allocation (similar struct as ue_list). - for (lcid = NB_RB_MAX - 1; lcid >= DTCH; lcid--) { - // TODO: check if the lcid is active - LOG_D(MAC, "[eNB %d], Frame %d, DTCH%d->DLSCH, Checking RLC status (tbs %d, len %d)\n", - module_idP, - frameP, - lcid, - TBS, - TBS - ta_len - header_length_total - sdu_length_total - 3); - - if (TBS - ta_len - header_length_total - sdu_length_total - 3 > 0) { - rlc_status = mac_rlc_status_ind(module_idP, - rnti, - module_idP, - frameP, - subframeP, - ENB_FLAG_YES, - MBMS_FLAG_NO, - lcid, - TBS - ta_len - header_length_total - sdu_length_total - 3, 0, 0 - ); - - if (rlc_status.bytes_in_buffer > 0) { - LOG_D(MAC, "[eNB %d][USER-PLANE DEFAULT DRB] Frame %d : DTCH->DLSCH, Requesting %d bytes from RLC (lcid %d total hdr len %d)\n", - module_idP, - frameP, - TBS - ta_len - header_length_total - sdu_length_total - 3, - lcid, - header_length_total); - sdu_lengths[num_sdus] = mac_rlc_data_req(module_idP, - rnti, - module_idP, - frameP, - ENB_FLAG_YES, - MBMS_FLAG_NO, - lcid, - TBS, //not used - (char *) &dlsch_buffer[sdu_length_total], 0, 0 - ); - T(T_ENB_MAC_UE_DL_SDU, - T_INT(module_idP), - T_INT(CC_id), - T_INT(rnti), - T_INT(frameP), - T_INT(subframeP), - T_INT(harq_pid), - T_INT(lcid), - T_INT(sdu_lengths[num_sdus])); - LOG_D(MAC, "[eNB %d][USER-PLANE DEFAULT DRB] Got %d bytes for DTCH %d \n", - module_idP, - sdu_lengths[num_sdus], - lcid); - sdu_lcids[num_sdus] = lcid; - sdu_length_total += sdu_lengths[num_sdus]; - eNB_UE_stats->num_pdu_tx[lcid]++; - eNB_UE_stats->lcid_sdu[num_sdus] = lcid; - eNB_UE_stats->sdu_length_tx[lcid] = sdu_lengths[num_sdus]; - eNB_UE_stats->num_bytes_tx[lcid] += sdu_lengths[num_sdus]; - header_length_last = 1 + 1 + (sdu_lengths[num_sdus] >= 128); - header_length_total += header_length_last; - num_sdus++; - ue_sched_ctrl->uplane_inactivity_timer = 0; - // reset RRC inactivity timer after uplane activity - ue_contextP = rrc_eNB_get_ue_context(RC.rrc[module_idP], rnti); - - if (ue_contextP != NULL) { - ue_contextP->ue_context.ue_rrc_inactivity_timer = 1; - } else { - LOG_E(MAC, "[eNB %d] CC_id %d Couldn't find the context associated to UE (RNTI %d) and reset RRC inactivity timer\n", - module_idP, - CC_id, - rnti); - } - } // end if (rlc_status.bytes_in_buffer > 0) - } else { // no TBS left - break; // break for (lcid = NB_RB_MAX - 1; lcid >= DTCH; lcid--) - } - } - - /* Last header does not have length field */ - if (header_length_total) { - header_length_total -= header_length_last; - header_length_total++; - } - - // there is at least one SDU or TA command - // if (num_sdus > 0 ){ - if (ta_len + sdu_length_total + header_length_total > 0) { - // Now compute number of required RBs for total sdu length - // Assume RAH format 2 - mcs = eNB_UE_stats->dlsch_mcs1; - - if (mcs == 0) { - nb_rb = 4; // don't let the TBS get too small - } else { - nb_rb = min_rb_unit[CC_id]; - } - - TBS = get_TBS_DL(mcs, nb_rb); - - while (TBS < sdu_length_total + header_length_total + ta_len) { - nb_rb += min_rb_unit[CC_id]; // - - if (nb_rb > nb_available_rb) { // if we've gone beyond the maximum number of RBs - // (can happen if N_RB_DL is odd) - TBS = get_TBS_DL(eNB_UE_stats->dlsch_mcs1, - nb_available_rb); - nb_rb = nb_available_rb; - break; - } - - TBS = get_TBS_DL(eNB_UE_stats->dlsch_mcs1, - nb_rb); - } - - if (nb_rb == ue_sched_ctrl->pre_nb_available_rbs[CC_id]) { - for (j = 0; j < N_RBG[CC_id]; ++j) { // for indicating the rballoc for each sub-band - ue_template->rballoc_subband[harq_pid][j] = ue_sched_ctrl->rballoc_sub_UE[CC_id][j]; - } - } else { - nb_rb_temp = nb_rb; - j = 0; - - while ((nb_rb_temp > 0) && (j < N_RBG[CC_id])) { - if (ue_sched_ctrl->rballoc_sub_UE[CC_id][j] == 1) { - ue_template->rballoc_subband[harq_pid][j] = ue_sched_ctrl->rballoc_sub_UE[CC_id][j]; - - if ((j == N_RBG[CC_id] - 1) && ((N_RB_DL[CC_id] == 25) || (N_RB_DL[CC_id] == 50))) { - nb_rb_temp = nb_rb_temp - min_rb_unit[CC_id] + 1; - } else { - nb_rb_temp = nb_rb_temp - min_rb_unit[CC_id]; - } - } - - j++; - } - } - - // decrease mcs until TBS falls below required length - while ((TBS > sdu_length_total + header_length_total + ta_len) && (mcs > 0)) { - mcs--; - TBS = get_TBS_DL(mcs, - nb_rb); - } - - // if we have decreased too much or we don't have enough RBs, increase MCS - while (TBS < sdu_length_total + header_length_total + ta_len && - ((ue_sched_ctrl->dl_pow_off[CC_id] > 0 && mcs < 28) || (ue_sched_ctrl->dl_pow_off[CC_id] == 0 && mcs <= 15))) { - mcs++; - TBS = get_TBS_DL(mcs, - nb_rb); - } - - LOG_D(MAC, "dlsch_mcs before and after the rate matching = (%d, %d)\n", - eNB_UE_stats->dlsch_mcs1, - mcs); -#ifdef DEBUG_eNB_SCHEDULER - LOG_D(MAC, "[eNB %d] CC_id %d Generated DLSCH header (mcs %d, TBS %d, nb_rb %d)\n", - module_idP, - CC_id, - mcs, TBS, - nb_rb); - // msg("[MAC][eNB ] Reminder of DLSCH with random data %d %d %d %d \n", - // TBS, sdu_length_total, offset, TBS-sdu_length_total-offset); -#endif + for (int UE_id = UE_info->list.head; UE_id >= 0; UE_id = UE_info->list.next[UE_id]) { + LOG_D(MAC, "doing schedule_ue_spec for CC_id %d UE %d\n", + CC_id, + UE_id); + UE_sched_ctrl_t *ue_sched_ctrl = &UE_info->UE_sched_ctrl[UE_id]; + UE_TEMPLATE *ue_template = &UE_info->UE_template[CC_id][UE_id]; + eNB_UE_STATS *eNB_UE_stats = &UE_info->eNB_UE_stats[CC_id][UE_id]; + const rnti_t rnti = ue_template->rnti; + + // If TDD + if (cc[CC_id].tdd_Config != NULL) { //TDD + set_ue_dai(subframeP, + UE_id, + CC_id, + cc[CC_id].tdd_Config->subframeAssignment, + UE_info); + // update UL DAI after DLSCH scheduling + set_ul_DAI(module_idP, + UE_id, + CC_id, + frameP, + subframeP); + } - if (TBS - header_length_total - sdu_length_total - ta_len <= 2) { - padding = TBS - header_length_total - sdu_length_total - ta_len; - post_padding = 0; - } else { - padding = 0; - post_padding = 1; - } + ue_rrc_release(rnti); + check_ra_rnti_mui(module_idP, CC_id, frameP, subframeP, rnti); - offset = generate_dlsch_header((unsigned char *) UE_list->DLSCH_pdu[CC_id][0][UE_id].payload[0], - num_sdus, //num_sdus - sdu_lengths, // - sdu_lcids, - 255, // no drx - ta_update, // timing advance - NULL, // contention res id - padding, - post_padding); + if (ue_sched_ctrl->pre_nb_available_rbs[CC_id] == 0) { // no RBs allocated + LOG_D(MAC, "%d.%d: no RBs allocated for UE %d on CC_id %d\n", + frameP, + subframeP, + UE_id, + CC_id); + continue; + } - //#ifdef DEBUG_eNB_SCHEDULER - if (ta_update != 31) { - LOG_D(MAC, - "[eNB %d][DLSCH] Frame %d Generate header for UE_id %d on CC_id %d: sdu_length_total %d, num_sdus %d, sdu_lengths[0] %d, sdu_lcids[0] %d => payload offset %d,timing advance value : %d, padding %d,post_padding %d,(mcs %d, TBS %d, nb_rb %d),header_length %d\n", - module_idP, - frameP, - UE_id, - CC_id, - sdu_length_total, - num_sdus, - sdu_lengths[0], - sdu_lcids[0], - offset, - ta_update, - padding, - post_padding, - mcs, - TBS, - nb_rb, - header_length_total); - } + int dci_dl_pdu_idx = ue_sched_ctrl->pre_dci_dl_pdu_idx; + if (dci_dl_pdu_idx < 0) { + dci_dl_pdu_idx = CCE_try_allocate_dlsch( + module_idP, CC_id, subframeP, UE_id, ue_sched_ctrl->dl_cqi[CC_id]); + if (dci_dl_pdu_idx < 0) { + LOG_W(MAC, "%d.%d: Dropping Allocation for RNTI 0x%04x/UE %d\n", + frameP, + subframeP, + rnti, + UE_id); + continue; + } + } - //#endif -#ifdef DEBUG_eNB_SCHEDULER - LOG_T(MAC, "[eNB %d] First 16 bytes of DLSCH : \n"); + /* verify it is the right UE */ + nfapi_dl_config_request_pdu_t *dci = &dl_req->dl_config_pdu_list[dci_dl_pdu_idx]; + nfapi_dl_config_request_pdu_t *dlsch = &dl_req->dl_config_pdu_list[dci_dl_pdu_idx + 1]; + if (dci->pdu_type != NFAPI_DL_CONFIG_DCI_DL_PDU_TYPE + || dci->dci_dl_pdu.dci_dl_pdu_rel8.rnti != rnti + || dlsch->pdu_type != NFAPI_DL_CONFIG_DLSCH_PDU_TYPE + || dlsch->dlsch_pdu.dlsch_pdu_rel8.rnti != rnti) { + LOG_E(MAC, "illegal dl_config_pdu_list index %d for UE %d/RNTI %04x\n", + dci_dl_pdu_idx, + UE_id, + rnti); + continue; + } - for (i = 0; i < 16; i++) { - LOG_T(MAC, "%x.", - dlsch_buffer[i]); - } + const int harq_pid = frame_subframe2_dl_harq_pid(cc->tdd_Config, + frameP, + subframeP); + const int round_DL = ue_sched_ctrl->round[CC_id][harq_pid]; + eNB_UE_stats->crnti = rnti; + eNB_UE_stats->rrc_status = mac_eNB_get_rrc_status(module_idP, rnti); + eNB_UE_stats->harq_pid = harq_pid; + eNB_UE_stats->harq_round = round_DL; + + if (eNB_UE_stats->rrc_status < RRC_RECONFIGURED) { + ue_sched_ctrl->uplane_inactivity_timer = 0; + } - LOG_T(MAC, "\n"); -#endif - // cycle through SDUs and place in dlsch_buffer - dlsch_pdu = &UE_list->DLSCH_pdu[CC_id][0][UE_id]; - memcpy(&dlsch_pdu->payload[0][offset], - dlsch_buffer, - sdu_length_total); - // memcpy(RC.mac[0].DLSCH_pdu[0][0].payload[0][offset],dcch_buffer,sdu_lengths[0]); - - // fill remainder of DLSCH with 0 - for (j = 0; j < (TBS - sdu_length_total - offset); j++) { - dlsch_pdu->payload[0][offset + sdu_length_total + j] = 0; - } + LOG_D(MAC, "[eNB %d] Frame %d: Scheduling UE %d on CC_id %d (rnti %x, harq_pid %d, round %d, rb %d, cqi %d, mcs %d, rrc %d)\n", + module_idP, + frameP, + UE_id, + CC_id, + rnti, + harq_pid, + round_DL, + ue_sched_ctrl->pre_nb_available_rbs[CC_id], + ue_sched_ctrl->dl_cqi[CC_id], + eNB_UE_stats->dlsch_mcs1, + eNB_UE_stats->rrc_status); + + /* Process retransmission */ + if (round_DL != 8) { + // get freq_allocation + const int nb_rb = ue_template->nb_rb[harq_pid]; + int TBS = get_TBS_DL(ue_template->oldmcs1[harq_pid], nb_rb); + const uint32_t rbc = allocate_prbs_sub( + nb_rb, N_RB_DL, N_RBG, ue_sched_ctrl->rballoc_sub_UE[CC_id]); + + if (nb_rb > ue_sched_ctrl->pre_nb_available_rbs[CC_id]) { + LOG_D(MAC, + "[eNB %d] Frame %d CC_id %d : don't schedule UE %d, its retransmission takes more resources than we have\n", + module_idP, + frameP, + CC_id, + UE_id); + continue; + } - trace_pdu(DIRECTION_DOWNLINK, - (uint8_t *) dlsch_pdu->payload[0], - TBS, - module_idP, - WS_C_RNTI, - UE_RNTI(module_idP, - UE_id), - eNB->frame, - eNB->subframe, - 0, - 0); - T(T_ENB_MAC_UE_DL_PDU_WITH_DATA, - T_INT(module_idP), - T_INT(CC_id), - T_INT(rnti), - T_INT(frameP), - T_INT(subframeP), - T_INT(harq_pid), - T_BUFFER(dlsch_pdu->payload[0], - TBS)); - ue_template->nb_rb[harq_pid] = nb_rb; - add_ue_dlsch_info(module_idP, - CC_id, - UE_id, - subframeP, - S_DL_SCHEDULED, - rnti); - // store stats - eNB->eNB_stats[CC_id].dlsch_bytes_tx += sdu_length_total; - eNB->eNB_stats[CC_id].dlsch_pdus_tx += 1; - eNB_UE_stats->rbs_used = nb_rb; - eNB_UE_stats->num_mac_sdu_tx = num_sdus; - eNB_UE_stats->total_rbs_used += nb_rb; - eNB_UE_stats->dlsch_mcs2 = mcs; - eNB_UE_stats->TBS = TBS; - eNB_UE_stats->overhead_bytes = TBS - sdu_length_total; - eNB_UE_stats->total_sdu_bytes += sdu_length_total; - eNB_UE_stats->total_pdu_bytes += TBS; - eNB_UE_stats->total_num_pdus += 1; - - if (cc[CC_id].tdd_Config != NULL) { // TDD - ue_template->DAI++; - update_ul_dci(module_idP, - CC_id, - rnti, - ue_template->DAI, - subframeP); - } + /* CDRX */ + ue_sched_ctrl->harq_rtt_timer[CC_id][harq_pid] = 1; // restart HARQ RTT timer - // do PUCCH power control - // this is the snr - // unit is not dBm, it's special from nfapi - // converting to dBm - snr = (5 * ue_sched_ctrl->pucch1_snr[CC_id] - 640) / 10; - target_snr = eNB->puCch10xSnr / 10; - // this assumes accumulated tpc - // make sure that we are only sending a tpc update once a frame, otherwise the control loop will freak out - int32_t framex10psubframe = ue_template->pucch_tpc_tx_frame * 10 + ue_template->pucch_tpc_tx_subframe; - - if (framex10psubframe + 10 <= (frameP * 10) + subframeP || //normal case - (framex10psubframe > (frameP * 10) + subframeP && 10240 - framex10psubframe + (frameP * 10) + subframeP >= 10)) //frame wrap-around - if (ue_sched_ctrl->pucch1_cqi_update[CC_id] == 1) { - ue_sched_ctrl->pucch1_cqi_update[CC_id] = 0; - ue_template->pucch_tpc_tx_frame = frameP; - ue_template->pucch_tpc_tx_subframe = subframeP; + if (ue_sched_ctrl->cdrx_configured) { + ue_sched_ctrl->drx_retransmission_timer[harq_pid] = 0; // stop drx retransmission - if (snr > target_snr + 4) { - tpc = 0; //-1 - } else if (snr < target_snr - 4) { - tpc = 2; //+1 - } else { - tpc = 1; //0 - } + /* + * Note: contrary to the spec drx_retransmission_timer[harq_pid] is reset not stop. + */ + if (harq_pid == 0) { + VCD_SIGNAL_DUMPER_DUMP_VARIABLE_BY_NAME(VCD_SIGNAL_DUMPER_VARIABLES_DRX_RETRANSMISSION_HARQ0, (unsigned long) ue_sched_ctrl->drx_retransmission_timer[0]); + } + } - LOG_D(MAC, "[eNB %d] DLSCH scheduler: frame %d, subframe %d, harq_pid %d, tpc %d, snr/target snr %d/%d (normal case)\n", - module_idP, - frameP, - subframeP, - harq_pid, - tpc, - snr, - target_snr); - } // Po_PUCCH has been updated - else { - tpc = 1; //0 - } // time to do TPC update - else { - tpc = 1; //0 - } + if (cc[CC_id].tdd_Config != NULL) { + ue_template->DAI++; + update_ul_dci(module_idP, + CC_id, + rnti, + ue_template->DAI, + subframeP); + LOG_D(MAC, "DAI update: CC_id %d subframeP %d: UE %d, DAI %d\n", + CC_id, + subframeP, + UE_id, + ue_template->DAI); + } - dl_config_pdu = &dl_req->dl_config_pdu_list[dl_req->number_pdu]; - memset((void *) dl_config_pdu, - 0, - sizeof(nfapi_dl_config_request_pdu_t)); - dl_config_pdu->pdu_type = NFAPI_DL_CONFIG_DCI_DL_PDU_TYPE; + nfapi_dl_config_request_pdu_t *dl_config_pdu = &dl_req->dl_config_pdu_list[dci_dl_pdu_idx]; + switch (get_tmode(module_idP, CC_id, UE_id)) { + case 1: + case 2: + case 7: + default: + LOG_D(MAC, "retransmission DL_REQ: rnti:%x\n", + rnti); dl_config_pdu->pdu_size = (uint8_t) (2 + sizeof(nfapi_dl_config_dci_dl_pdu)); dl_config_pdu->dci_dl_pdu.dci_dl_pdu_rel8.dci_format = NFAPI_DL_DCI_FORMAT_1; - dl_config_pdu->dci_dl_pdu.dci_dl_pdu_rel8.aggregation_level = - get_aggregation(get_bw_index(module_idP, - CC_id), - ue_sched_ctrl->dl_cqi[CC_id], - format1); - dl_config_pdu->dci_dl_pdu.dci_dl_pdu_rel8.tl.tag = NFAPI_DL_CONFIG_REQUEST_DCI_DL_PDU_REL8_TAG; - dl_config_pdu->dci_dl_pdu.dci_dl_pdu_rel8.rnti = rnti; - dl_config_pdu->dci_dl_pdu.dci_dl_pdu_rel8.rnti_type = 1; // CRNTI : see Table 4-10 from SCF082 - nFAPI specifications - dl_config_pdu->dci_dl_pdu.dci_dl_pdu_rel8.transmission_power = 6000; // equal to RS power + dl_config_pdu->dci_dl_pdu.dci_dl_pdu_rel8.rnti_type = 1; // CRNTI: see Table 4-10 from SCF082 - nFAPI specifications + dl_config_pdu->dci_dl_pdu.dci_dl_pdu_rel8.transmission_power = 6000; // equal to RS power dl_config_pdu->dci_dl_pdu.dci_dl_pdu_rel8.harq_process = harq_pid; - dl_config_pdu->dci_dl_pdu.dci_dl_pdu_rel8.tpc = tpc; // dont adjust power when retransmitting - dl_config_pdu->dci_dl_pdu.dci_dl_pdu_rel8.new_data_indicator_1 = 1 - ue_template->oldNDI[harq_pid]; - dl_config_pdu->dci_dl_pdu.dci_dl_pdu_rel8.mcs_1 = mcs; - dl_config_pdu->dci_dl_pdu.dci_dl_pdu_rel8.redundancy_version_1 = 0; - //deactivate second codeword - dl_config_pdu->dci_dl_pdu.dci_dl_pdu_rel8.mcs_2 = 0; - dl_config_pdu->dci_dl_pdu.dci_dl_pdu_rel8.redundancy_version_2 = 1; - - if (cc[CC_id].tdd_Config != NULL) { //TDD + dl_config_pdu->dci_dl_pdu.dci_dl_pdu_rel8.tpc = 1; // Don't adjust power when retransmitting + dl_config_pdu->dci_dl_pdu.dci_dl_pdu_rel8.new_data_indicator_1 = ue_template->oldNDI[harq_pid]; + dl_config_pdu->dci_dl_pdu.dci_dl_pdu_rel8.mcs_1 = ue_template->oldmcs1[harq_pid]; + dl_config_pdu->dci_dl_pdu.dci_dl_pdu_rel8.redundancy_version_1 = round_DL & 3; + dl_config_pdu->dci_dl_pdu.dci_dl_pdu_rel8.resource_block_coding = rbc; + dl_config_pdu->dci_dl_pdu.dci_dl_pdu_rel8.resource_allocation_type = 0; + + // TDD + if (cc[CC_id].tdd_Config != NULL) { dl_config_pdu->dci_dl_pdu.dci_dl_pdu_rel8.downlink_assignment_index = (ue_template->DAI - 1) & 3; - LOG_D(MAC, "[eNB %d] Initial transmission CC_id %d : harq_pid %d, dai %d, mcs %d\n", + LOG_D(MAC, "[eNB %d] Retransmission CC_id %d : harq_pid %d, round %d, dai %d, mcs %d\n", module_idP, CC_id, harq_pid, - (ue_template->DAI - 1), - mcs); + round_DL, + ue_template->DAI - 1, + ue_template->oldmcs1[harq_pid]); } else { - LOG_D(MAC, "[eNB %d] Initial transmission CC_id %d : harq_pid %d, mcs %d\n", + LOG_D(MAC, "[eNB %d] Retransmission CC_id %d : harq_pid %d, round %d, mcs %d\n", module_idP, CC_id, harq_pid, - mcs); + round_DL, + ue_template->oldmcs1[harq_pid]); } - LOG_D(MAC, "Checking feasibility pdu %d (new sdu)\n", - dl_req->number_pdu); - - if (!CCE_allocation_infeasible(module_idP, - CC_id, - 1, - subframeP, - dl_config_pdu->dci_dl_pdu.dci_dl_pdu_rel8.aggregation_level, - rnti)) { - ue_sched_ctrl->round[CC_id][harq_pid] = 0; - dl_req->number_dci++; - dl_req->number_pdu++; - dl_req->tl.tag = NFAPI_DL_CONFIG_REQUEST_BODY_TAG; - eNB->DL_req[CC_id].sfn_sf = frameP << 4 | subframeP; - eNB->DL_req[CC_id].header.message_id = NFAPI_DL_CONFIG_REQUEST; - /* CDRX */ - ue_sched_ctrl->harq_rtt_timer[CC_id][harq_pid] = 1; // restart HARQ RTT timer - - if (ue_sched_ctrl->cdrx_configured) { - ue_sched_ctrl->drx_inactivity_timer = 1; // restart drx inactivity timer when new transmission - ue_sched_ctrl->drx_retransmission_timer[harq_pid] = 0; // stop drx retransmission - /* - * Note: contrary to the spec drx_retransmission_timer[harq_pid] is reset not stop. - */ - VCD_SIGNAL_DUMPER_DUMP_VARIABLE_BY_NAME(VCD_SIGNAL_DUMPER_VARIABLES_DRX_INACTIVITY, (unsigned long) ue_sched_ctrl->drx_inactivity_timer); - - if (harq_pid == 0) { - VCD_SIGNAL_DUMPER_DUMP_VARIABLE_BY_NAME(VCD_SIGNAL_DUMPER_VARIABLES_DRX_RETRANSMISSION_HARQ0, (unsigned long) ue_sched_ctrl->drx_retransmission_timer[0]); - } - } - - // Toggle NDI for next time - LOG_D(MAC, "CC_id %d Frame %d, subframeP %d: Toggling Format1 NDI for UE %d (rnti %x/%d) oldNDI %d\n", - CC_id, - frameP, - subframeP, - UE_id, - rnti, - harq_pid, - ue_template->oldNDI[harq_pid]); - ue_template->oldNDI[harq_pid] = 1 - ue_template->oldNDI[harq_pid]; - ue_template->oldmcs1[harq_pid] = mcs; - ue_template->oldmcs2[harq_pid] = 0; - AssertFatal(ue_template->physicalConfigDedicated != NULL, "physicalConfigDedicated is NULL\n"); - AssertFatal(ue_template->physicalConfigDedicated->pdsch_ConfigDedicated != NULL, - "physicalConfigDedicated->pdsch_ConfigDedicated is NULL\n"); - fill_nfapi_dlsch_config(eNB, - dl_req, - TBS, - eNB->pdu_index[CC_id], - rnti, - 0, // type 0 allocation from 7.1.6 in 36.213 - 0, // virtual_resource_block_assignment_flag, unused here - 0, // resource_block_coding, to be filled in later - getQm(mcs), - 0, // redundancy version - 1, // transport blocks - 0, // transport block to codeword swap flag - cc[CC_id].p_eNB == 1 ? 0 : 1, // transmission_scheme - 1, // number of layers - 1, // number of subbands - // uint8_t codebook_index, - 4, // UE category capacity - ue_template->physicalConfigDedicated->pdsch_ConfigDedicated->p_a, - 0, // delta_power_offset for TM5 - 0, // ngap - 0, // nprb - cc[CC_id].p_eNB == 1 ? 1 : 2, // transmission mode - 0, //number of PRBs treated as one subband, not used here - 0); // number of beamforming vectors, not used here - eNB->TX_req[CC_id].sfn_sf = fill_nfapi_tx_req(&eNB->TX_req[CC_id].tx_request_body, - (frameP * 10) + subframeP, - TBS, - eNB->pdu_index[CC_id], - dlsch_pdu->payload[0]); - LOG_D(MAC, "Filled NFAPI configuration for DCI/DLSCH/TXREQ %d, new SDU\n", - eNB->pdu_index[CC_id]); - eNB->pdu_index[CC_id]++; - program_dlsch_acknak(module_idP, - CC_id, - UE_id, - frameP, - subframeP, - dl_config_pdu->dci_dl_pdu.dci_dl_pdu_rel8.cce_idx); - } else { - LOG_W(MAC, "Frame %d, Subframe %d: Dropping DLSCH allocation for UE %d/%x, infeasible CCE allocations\n", - frameP, - subframeP, - UE_id, - rnti); - } - } else { // There is no data from RLC or MAC header, so don't schedule - } + dl_req->tl.tag = NFAPI_DL_CONFIG_REQUEST_BODY_TAG; + eNB->DL_req[CC_id].sfn_sf = frameP<<4 | subframeP; + eNB->DL_req[CC_id].header.message_id = NFAPI_DL_CONFIG_REQUEST; + fill_nfapi_dlsch_config(&dl_req->dl_config_pdu_list[dci_dl_pdu_idx + 1], + TBS, + -1, // retransmission, no pdu_index + rnti, + 0, // type 0 allocation from 7.1.6 in 36.213 + 0, // virtual_resource_block_assignment_flag, unused here + rbc, // resource_block_coding + getQm(ue_template->oldmcs1[harq_pid]), + round_DL & 3, // redundancy version + 1, // transport blocks + 0, // transport block to codeword swap flag + cc[CC_id].p_eNB == 1 ? 0 : 1, // transmission_scheme + 1, // number of layers + 1, // number of subbands + // uint8_t codebook_index, + 4, // UE category capacity + ue_template->physicalConfigDedicated->pdsch_ConfigDedicated->p_a, + 0, // delta_power_offset for TM5 + 0, // ngap + 0, // nprb + cc[CC_id].p_eNB == 1 ? 1 : 2, // transmission mode + 0, //number of PRBs treated as one subband, not used here + 0); // number of beamforming vectors, not used here + LOG_D(MAC, "Filled NFAPI configuration for DCI/DLSCH %d, retransmission round %d\n", + eNB->pdu_index[CC_id], + round_DL); + program_dlsch_acknak(module_idP, + CC_id, + UE_id, + frameP, + subframeP, + dl_config_pdu->dci_dl_pdu.dci_dl_pdu_rel8.cce_idx); + // No TX request for retransmission (check if null request for FAPI) } - if (cc[CC_id].tdd_Config != NULL) { // TDD - set_ul_DAI(module_idP, - UE_id, - CC_id, - frameP, - subframeP); - } - } // UE_id loop - } // CC_id loop + //eNB_UE_stats->dlsch_trials[round]++; + eNB_UE_stats->num_retransmission += 1; + eNB_UE_stats->rbs_used_retx = nb_rb; + eNB_UE_stats->total_rbs_used_retx += nb_rb; + eNB_UE_stats->dlsch_mcs2 = eNB_UE_stats->dlsch_mcs1; + } else { + // Now check RLC information to compute number of required RBs + // get maximum TBS size for RLC request + const int nb_rb = ue_sched_ctrl->pre_nb_available_rbs[CC_id]; + int TBS = get_TBS_DL(eNB_UE_stats->dlsch_mcs1, nb_rb); + const uint32_t rbc = allocate_prbs_sub(nb_rb, N_RB_DL, N_RBG, ue_sched_ctrl->rballoc_sub_UE[CC_id]); - fill_DLSCH_dci(module_idP, - frameP, - subframeP, - mbsfn_flag); - stop_meas(&eNB->schedule_dlsch); - VCD_SIGNAL_DUMPER_DUMP_FUNCTION_BY_NAME(VCD_SIGNAL_DUMPER_FUNCTIONS_SCHEDULE_DLSCH, - VCD_FUNCTION_OUT); -} + // add the length for all the control elements (timing adv, drx, etc) : header + payload -//------------------------------------------------------------------------------ -void -dlsch_scheduler_interslice_multiplexing(module_id_t Mod_id, - int frameP, - sub_frame_t subframeP, - uint8_t rballoc_sub[NFAPI_CC_MAX][N_RBG_MAX]) -//------------------------------------------------------------------------------ -{ - // FIXME: I'm prototyping the algorithm, so there may be arrays and variables that carry redundant information here and in pre_processor_results struct. - int UE_id, CC_id, rbg, i; - int N_RB_DL, min_rb_unit, tm; - int owned, used; - eNB_MAC_INST *eNB = RC.mac[Mod_id]; - int nb_mac_CC = RC.nb_mac_CC[Mod_id]; - UE_list_t *UE_list = &eNB->UE_list; - slice_info_t *sli = &eNB->slice_info; - UE_sched_ctrl_t *ue_sched_ctl; - COMMON_channels_t *cc; - int N_RBG[NFAPI_CC_MAX]; - int slice_sorted_list[MAX_NUM_SLICES]; - int slice_idx; - int8_t free_rbgs_map[NFAPI_CC_MAX][N_RBG_MAX]; - int has_traffic[NFAPI_CC_MAX][MAX_NUM_SLICES]; - uint8_t allocation_mask[NFAPI_CC_MAX][N_RBG_MAX]; - uint16_t (*nb_rbs_remaining)[MAX_MOBILES_PER_ENB]; - uint16_t (*nb_rbs_required)[MAX_MOBILES_PER_ENB]; - uint8_t (*MIMO_mode_indicator)[N_RBG_MAX]; - - // Initialize the free RBGs map - // free_rbgs_map[CC_id][rbg] = -1 if RBG is allocated, - // otherwise it contains the id of the slice it belongs to. - // (Information about slicing must be retained to deal with isolation). - // FIXME: This method does not consider RBGs that are free and belong to no slices - for (CC_id = 0; CC_id < nb_mac_CC; CC_id++) { - cc = &eNB->common_channels[CC_id]; - N_RBG[CC_id] = to_rbg(cc->mib->message.dl_Bandwidth); - - for (rbg = 0; rbg < N_RBG[CC_id]; rbg++) { - for (i = 0; i < sli->n_dl; ++i) { - owned = sli->pre_processor_results[i].slice_allocation_mask[CC_id][rbg]; - - if (owned) { - used = rballoc_sub[CC_id][rbg]; - free_rbgs_map[CC_id][rbg] = used ? -1 : i; - break; - } - } - } - } + if (ue_sched_ctrl->ta_timer) + ue_sched_ctrl->ta_timer--; - // Find out which slices need other resources. - // FIXME: I don't think is really needed since we check nb_rbs_remaining later - for (CC_id = 0; CC_id < nb_mac_CC; CC_id++) { - for (i = 0; i < sli->n_dl; i++) { - has_traffic[CC_id][i] = 0; + int ta_update = 31; + if (ue_sched_ctrl->ta_timer == 0) { + ta_update = ue_sched_ctrl->ta_update; - for (UE_id = 0; UE_id < MAX_MOBILES_PER_ENB; UE_id++) { - if (sli->pre_processor_results[i].nb_rbs_remaining[CC_id][UE_id] > 0) { - has_traffic[CC_id][i] = 1; - break; + /* if we send TA then set timer to not send it for a while */ + if (ta_update != 31) { + ue_sched_ctrl->ta_timer = 20; } + + /* reset ta_update */ + ue_sched_ctrl->ta_update = 31; } - } - } - slice_priority_sort(Mod_id, - slice_sorted_list); + int ta_len = (ta_update != 31) ? 2 : 0; - // MULTIPLEXING - // This part is an adaptation of dlsch_scheduler_pre_processor_allocate() code - for (CC_id = 0; CC_id < nb_mac_CC; ++CC_id) { - N_RB_DL = to_prb(eNB->common_channels[CC_id].mib->message.dl_Bandwidth); - min_rb_unit = get_min_rb_unit(Mod_id, - CC_id); - for (i = 0; i < sli->n_dl; ++i) { - slice_idx = slice_sorted_list[i]; + int num_sdus = 0; + uint16_t sdu_lengths[NB_RB_MAX]; + int sdu_length_total = 0; + int header_length_total = 0; + int header_length_last = 0; + unsigned char sdu_lcids[NB_RB_MAX]; + for (int i = 0; i < ue_sched_ctrl->dl_lc_num; ++i) { + const int lcid = ue_sched_ctrl->dl_lc_ids[i]; // will match DCCH, DCCH1, DTCH - if (has_traffic[CC_id][slice_idx] == 0) continue; + if (TBS - ta_len - header_length_total - sdu_length_total - 3 <= 0) + break; - // Build an ad-hoc allocation mask fo the slice - for (rbg = 0; rbg < N_RBG[CC_id]; ++rbg) { - if (free_rbgs_map[CC_id][rbg] == -1) { - // RBG is already allocated - allocation_mask[CC_id][rbg] = 0; + if (ue_sched_ctrl->dl_lc_bytes[i] == 0) // no data in this LC! continue; - } - if (sli->dl[free_rbgs_map[CC_id][rbg]].isol == 1) { - // RBG belongs to an isolated slice - allocation_mask[CC_id][rbg] = 0; - continue; + LOG_D(MAC, "[eNB %d] SFN/SF %d.%d, LC%d->DLSCH CC_id %d, Requesting %d bytes from RLC (RRC message)\n", + module_idP, + frameP, + subframeP, + lcid, + CC_id, + TBS - ta_len - header_length_total - sdu_length_total - 3); + + sdu_lengths[num_sdus] = mac_rlc_data_req(module_idP, + rnti, + module_idP, + frameP, + ENB_FLAG_YES, + MBMS_FLAG_NO, + lcid, + TBS - ta_len - header_length_total - sdu_length_total - 3, + (char *)&dlsch_buffer[sdu_length_total], + 0, + 0 + ); + +#ifdef DEBUG_eNB_SCHEDULER + LOG_T(MAC, "[eNB %d][%d] CC_id %d Got %d bytes :", + module_idP, + lcid, + CC_id, + sdu_lengths[num_sdus]); + for (int j = 0; j < sdu_lengths[num_sdus]; ++j) + LOG_T(MAC, "%x ", dlsch_buffer[sdu_length_total + j]); + LOG_T(MAC, "\n"); +#endif + + T(T_ENB_MAC_UE_DL_SDU, + T_INT(module_idP), + T_INT(CC_id), + T_INT(rnti), + T_INT(frameP), + T_INT(subframeP), + T_INT(harq_pid), + T_INT(lcid), + T_INT(sdu_lengths[num_sdus])); + LOG_D(MAC, "[eNB %d][LC %d] CC_id %d Got %d bytes from RLC\n", + module_idP, + lcid, + CC_id, + sdu_lengths[num_sdus]); + sdu_lcids[num_sdus] = lcid; + sdu_length_total += sdu_lengths[num_sdus]; + eNB_UE_stats->num_pdu_tx[lcid] += 1; + eNB_UE_stats->lcid_sdu[num_sdus] = lcid; + eNB_UE_stats->sdu_length_tx[lcid] = sdu_lengths[num_sdus]; + eNB_UE_stats->num_bytes_tx[lcid] += sdu_lengths[num_sdus]; + header_length_last = 1 + 1 + (sdu_lengths[num_sdus] >= 128); + header_length_total += header_length_last; + num_sdus += 1; + + if (lcid >= 3) { // if this is DTCH + ue_sched_ctrl->uplane_inactivity_timer = 0; + + // reset RRC inactivity timer after uplane activity + rrc_eNB_ue_context_t *ue_contextP = rrc_eNB_get_ue_context(RC.rrc[module_idP], rnti); + if (ue_contextP == NULL) + LOG_E(MAC, "[eNB %d] CC_id %d Couldn't find the context associated to UE (RNTI %d) and reset RRC inactivity timer\n", + module_idP, + CC_id, + rnti); + ue_contextP->ue_context.ue_rrc_inactivity_timer = 1; } + } - // RBG is free - allocation_mask[CC_id][rbg] = 1; + /* Last header does not have length field */ + if (header_length_total) { + header_length_total -= header_length_last; + header_length_total++; } - // Sort UE again - // (UE list gets sorted every time pre_processor is called so it is probably dirty at this point) - // FIXME: There is only one UE_list for all slices, so it must be sorted again each time we use it - sort_UEs(Mod_id, - slice_idx, - frameP, - subframeP); - nb_rbs_remaining = sli->pre_processor_results[slice_idx].nb_rbs_remaining; - nb_rbs_required = sli->pre_processor_results[slice_idx].nb_rbs_required; - MIMO_mode_indicator = sli->pre_processor_results[slice_idx].MIMO_mode_indicator; + // there is at least one SDU or TA command + if (ta_len + sdu_length_total + header_length_total > 0) { + // Now compute number of required RBs for total sdu length + // Assume RAH format 2 + int mcs = eNB_UE_stats->dlsch_mcs1; + + /* TODO make special function */ + // decrease mcs until TBS falls below required length + while ((TBS > sdu_length_total + header_length_total + ta_len) && (mcs > 0)) { + mcs--; + TBS = get_TBS_DL(mcs, nb_rb); + } + + // if we have decreased too much or we don't have enough RBs, increase MCS + while (TBS < sdu_length_total + header_length_total + ta_len && mcs < 28) { + // the second part of this condition is useless since dl_pow_off is + // always 2? + //&& ((ue_sched_ctrl->dl_pow_off[CC_id] > 0 && mcs < 28) || (ue_sched_ctrl->dl_pow_off[CC_id] == 0 && mcs <= 15))) { + mcs++; + TBS = get_TBS_DL(mcs, + nb_rb); + } - // Allocation - for (UE_id = UE_list->head; UE_id >= 0; UE_id = UE_list->next[UE_id]) { - ue_sched_ctl = &UE_list->UE_sched_ctrl[UE_id]; - tm = get_tmode(Mod_id, - CC_id, - UE_id); + LOG_D(MAC, "dlsch_mcs before and after the rate matching = (%d, %d), TBS %d, nb_rb %d\n", + eNB_UE_stats->dlsch_mcs1, mcs, TBS, nb_rb); - for (rbg = 0; rbg < N_RBG[CC_id]; ++rbg) { - // FIXME: I think that some of these checks are redundant - if (allocation_mask[CC_id][rbg] == 0) continue; + int post_padding = TBS - header_length_total - sdu_length_total - ta_len > 2; + int padding = post_padding ? 0 : TBS - header_length_total - sdu_length_total - ta_len; - if (rballoc_sub[CC_id][rbg] != 0) continue; + const int offset = generate_dlsch_header((unsigned char *) UE_info->DLSCH_pdu[CC_id][0][UE_id].payload[0], + num_sdus, //num_sdus + sdu_lengths, // + sdu_lcids, + 255, // no drx + ta_update, // timing advance + NULL, // contention res id + padding, + post_padding); - if (ue_sched_ctl->rballoc_sub_UE[CC_id][rbg] != 0) continue; + //#ifdef DEBUG_eNB_SCHEDULER + if (ta_update != 31) { + LOG_D(MAC, + "[eNB %d][DLSCH] Frame %d Generate header for UE_id %d on CC_id %d: sdu_length_total %d, num_sdus %d, sdu_lengths[0] %d, sdu_lcids[0] %d => payload offset %d,timing advance value : %d, padding %d,post_padding %d,(mcs %d, TBS %d, nb_rb %d),header_length %d\n", + module_idP, + frameP, + UE_id, + CC_id, + sdu_length_total, + num_sdus, + sdu_lengths[0], + sdu_lcids[0], + offset, + ta_update, + padding, + post_padding, + mcs, + TBS, + nb_rb, + header_length_total); + } - if (nb_rbs_remaining[CC_id][UE_id] <= 0) continue; + //#endif +#ifdef DEBUG_eNB_SCHEDULER + LOG_T(MAC, "[eNB %d] First 16 bytes of DLSCH : \n"); - if (ue_sched_ctl->pre_nb_available_rbs[CC_id] >= nb_rbs_required[CC_id][UE_id]) continue; + for (int i = 0; i < 16; i++) { + LOG_T(MAC, "%x.", + dlsch_buffer[i]); + } - if (ue_sched_ctl->dl_pow_off[CC_id] == 0) continue; + LOG_T(MAC, "\n"); +#endif + // cycle through SDUs and place in dlsch_buffer + DLSCH_PDU *dlsch_pdu = &UE_info->DLSCH_pdu[CC_id][0][UE_id]; + memcpy(&dlsch_pdu->payload[0][offset], dlsch_buffer, sdu_length_total); - if ((rbg == N_RBG[CC_id] - 1) && ((N_RB_DL == 25) || (N_RB_DL == 50))) { - // Allocating last, smaller RBG - if (nb_rbs_remaining[CC_id][UE_id] >= min_rb_unit - 1) { - rballoc_sub[CC_id][rbg] = 1; - free_rbgs_map[CC_id][rbg] = -1; - ue_sched_ctl->rballoc_sub_UE[CC_id][rbg] = 1; - MIMO_mode_indicator[CC_id][rbg] = 1; + // fill remainder of DLSCH with 0 + for (int j = 0; j < TBS - sdu_length_total - offset; j++) { + dlsch_pdu->payload[0][offset + sdu_length_total + j] = 0; + } - if (tm == 5) { - ue_sched_ctl->dl_pow_off[CC_id] = 1; - } + trace_pdu(DIRECTION_DOWNLINK, + (uint8_t *) dlsch_pdu->payload[0], + TBS, + module_idP, + WS_C_RNTI, + UE_RNTI(module_idP, + UE_id), + eNB->frame, + eNB->subframe, + 0, + 0); + T(T_ENB_MAC_UE_DL_PDU_WITH_DATA, + T_INT(module_idP), + T_INT(CC_id), + T_INT(rnti), + T_INT(frameP), + T_INT(subframeP), + T_INT(harq_pid), + T_BUFFER(dlsch_pdu->payload[0], + TBS)); + ue_template->nb_rb[harq_pid] = nb_rb; + // store stats + eNB->eNB_stats[CC_id].dlsch_bytes_tx += sdu_length_total; + eNB->eNB_stats[CC_id].dlsch_pdus_tx += 1; + eNB_UE_stats->rbs_used = nb_rb; + eNB_UE_stats->num_mac_sdu_tx = num_sdus; + eNB_UE_stats->total_rbs_used += nb_rb; + eNB_UE_stats->dlsch_mcs2 = mcs; + eNB_UE_stats->TBS = TBS; + eNB_UE_stats->overhead_bytes = TBS - sdu_length_total; + eNB_UE_stats->total_sdu_bytes += sdu_length_total; + eNB_UE_stats->total_pdu_bytes += TBS; + eNB_UE_stats->total_num_pdus += 1; + + if (cc[CC_id].tdd_Config != NULL) { // TDD + ue_template->DAI++; + update_ul_dci(module_idP, + CC_id, + rnti, + ue_template->DAI, + subframeP); + } - nb_rbs_remaining[CC_id][UE_id] -= (min_rb_unit - 1); - ue_sched_ctl->pre_nb_available_rbs[CC_id] += (min_rb_unit - 1); + // do PUCCH power control + // this is the snr + // unit is not dBm, it's special from nfapi + // converting to dBm + int snr = (5 * ue_sched_ctrl->pucch1_snr[CC_id] - 640) / 10; + int target_snr = eNB->puCch10xSnr / 10; + // this assumes accumulated tpc + // make sure that we are only sending a tpc update once a frame, otherwise the control loop will freak out + int32_t framex10psubframe = ue_template->pucch_tpc_tx_frame * 10 + ue_template->pucch_tpc_tx_subframe; + + int tpc = 1; + if (framex10psubframe + 10 <= (frameP * 10) + subframeP || //normal case + (framex10psubframe > (frameP * 10) + subframeP && 10240 - framex10psubframe + (frameP * 10) + subframeP >= 10)) { //frame wrap-around + if (ue_sched_ctrl->pucch1_cqi_update[CC_id] == 1) { + ue_sched_ctrl->pucch1_cqi_update[CC_id] = 0; + ue_template->pucch_tpc_tx_frame = frameP; + ue_template->pucch_tpc_tx_subframe = subframeP; + + if (snr > target_snr + 4) { + tpc = 0; //-1 + } else if (snr < target_snr - 4) { + tpc = 2; //+1 + } else { + tpc = 1; //0 } - } else { - // Allocating a standard-sized RBG - if (nb_rbs_remaining[CC_id][UE_id] >= min_rb_unit) { - rballoc_sub[CC_id][rbg] = 1; - free_rbgs_map[CC_id][rbg] = -1; - ue_sched_ctl->rballoc_sub_UE[CC_id][rbg] = 1; - MIMO_mode_indicator[CC_id][rbg] = 1; - - if (tm == 5) { - ue_sched_ctl->dl_pow_off[CC_id] = 1; - } - nb_rbs_remaining[CC_id][UE_id] -= min_rb_unit; - ue_sched_ctl->pre_nb_available_rbs[CC_id] += min_rb_unit; - } - } + LOG_D(MAC, "[eNB %d] DLSCH scheduler: frame %d, subframe %d, harq_pid %d, tpc %d, snr/target snr %d/%d (normal case)\n", + module_idP, + frameP, + subframeP, + harq_pid, + tpc, + snr, + target_snr); + } // Po_PUCCH has been updated } - } - } - } - return; -} + nfapi_dl_config_request_pdu_t *dl_config_pdu = &dl_req->dl_config_pdu_list[dci_dl_pdu_idx]; + dl_config_pdu->pdu_size = (uint8_t) (2 + sizeof(nfapi_dl_config_dci_dl_pdu)); + dl_config_pdu->dci_dl_pdu.dci_dl_pdu_rel8.dci_format = NFAPI_DL_DCI_FORMAT_1; + dl_config_pdu->dci_dl_pdu.dci_dl_pdu_rel8.rnti_type = 1; // CRNTI : see Table 4-10 from SCF082 - nFAPI specifications + dl_config_pdu->dci_dl_pdu.dci_dl_pdu_rel8.transmission_power = 6000; // equal to RS power + dl_config_pdu->dci_dl_pdu.dci_dl_pdu_rel8.harq_process = harq_pid; + dl_config_pdu->dci_dl_pdu.dci_dl_pdu_rel8.tpc = tpc; // dont adjust power when retransmitting + dl_config_pdu->dci_dl_pdu.dci_dl_pdu_rel8.new_data_indicator_1 = 1 - ue_template->oldNDI[harq_pid]; + dl_config_pdu->dci_dl_pdu.dci_dl_pdu_rel8.mcs_1 = mcs; + dl_config_pdu->dci_dl_pdu.dci_dl_pdu_rel8.redundancy_version_1 = 0; + //deactivate second codeword + dl_config_pdu->dci_dl_pdu.dci_dl_pdu_rel8.mcs_2 = 0; + dl_config_pdu->dci_dl_pdu.dci_dl_pdu_rel8.redundancy_version_2 = 1; + dl_config_pdu->dci_dl_pdu.dci_dl_pdu_rel8.resource_block_coding = rbc; + dl_config_pdu->dci_dl_pdu.dci_dl_pdu_rel8.resource_allocation_type = 0; + + if (cc[CC_id].tdd_Config != NULL) { //TDD + dl_config_pdu->dci_dl_pdu.dci_dl_pdu_rel8.downlink_assignment_index = (ue_template->DAI - 1) & 3; + LOG_D(MAC, "[eNB %d] Initial transmission CC_id %d : harq_pid %d, dai %d, mcs %d\n", + module_idP, + CC_id, + harq_pid, + (ue_template->DAI - 1), + mcs); + } else { + LOG_D(MAC, "[eNB %d] Initial transmission CC_id %d : harq_pid %d, mcs %d\n", + module_idP, + CC_id, + harq_pid, + mcs); + } -//------------------------------------------------------------------------------ -void dlsch_scheduler_qos_multiplexing(module_id_t Mod_id, int frameP, sub_frame_t subframeP) -//------------------------------------------------------------------------------ -{ - // int UE_id; - int CC_id, i; - // UE_list_t *UE_list = &RC.mac[Mod_id]->UE_list; - slice_info_t *sli = &RC.mac[Mod_id]->slice_info; - //UE_sched_ctrl *ue_sched_ctl; - - for (CC_id = 0; CC_id < RC.nb_mac_CC[Mod_id]; CC_id++) { - for (i = 0; i < sli->n_dl; i++) { - // Sort UE again - // FIXME: There is only one UE_list for all slices, so it must be sorted again each time we use it - sort_UEs(Mod_id, - (uint8_t)i, - frameP, - subframeP); - /* - for (UE_id = UE_list->head; UE_id >= 0; UE_id = UE_list->next[UE_id]) { - //ue_sched_ctl = &UE_list->UE_sched_ctrl[UE_id]; - // TODO: Do something here - // ue_sched_ctl->pre_nb_available_rbs[CC_id]; + LOG_D(MAC, "Checking feasibility pdu %d (new sdu)\n", + dl_req->number_pdu); + + ue_sched_ctrl->round[CC_id][harq_pid] = 0; + dl_req->tl.tag = NFAPI_DL_CONFIG_REQUEST_BODY_TAG; + eNB->DL_req[CC_id].sfn_sf = frameP << 4 | subframeP; + eNB->DL_req[CC_id].header.message_id = NFAPI_DL_CONFIG_REQUEST; + /* CDRX */ + ue_sched_ctrl->harq_rtt_timer[CC_id][harq_pid] = 1; // restart HARQ RTT timer + + if (ue_sched_ctrl->cdrx_configured) { + ue_sched_ctrl->drx_inactivity_timer = 1; // restart drx inactivity timer when new transmission + ue_sched_ctrl->drx_retransmission_timer[harq_pid] = 0; // stop drx retransmission + /* + * Note: contrary to the spec drx_retransmission_timer[harq_pid] is reset not stop. + */ + VCD_SIGNAL_DUMPER_DUMP_VARIABLE_BY_NAME(VCD_SIGNAL_DUMPER_VARIABLES_DRX_INACTIVITY, (unsigned long) ue_sched_ctrl->drx_inactivity_timer); + + if (harq_pid == 0) { + VCD_SIGNAL_DUMPER_DUMP_VARIABLE_BY_NAME(VCD_SIGNAL_DUMPER_VARIABLES_DRX_RETRANSMISSION_HARQ0, (unsigned long) ue_sched_ctrl->drx_retransmission_timer[0]); + } + } + + // Toggle NDI for next time + LOG_D(MAC, "CC_id %d Frame %d, subframeP %d: Toggling Format1 NDI for UE %d (rnti %x/%d) oldNDI %d\n", + CC_id, + frameP, + subframeP, + UE_id, + rnti, + harq_pid, + ue_template->oldNDI[harq_pid]); + ue_template->oldNDI[harq_pid] = 1 - ue_template->oldNDI[harq_pid]; + ue_template->oldmcs1[harq_pid] = mcs; + ue_template->oldmcs2[harq_pid] = 0; + AssertFatal(ue_template->physicalConfigDedicated != NULL, "physicalConfigDedicated is NULL\n"); + AssertFatal(ue_template->physicalConfigDedicated->pdsch_ConfigDedicated != NULL, + "physicalConfigDedicated->pdsch_ConfigDedicated is NULL\n"); + fill_nfapi_dlsch_config(&dl_req->dl_config_pdu_list[dci_dl_pdu_idx + 1], + TBS, + eNB->pdu_index[CC_id], + rnti, + 0, // type 0 allocation from 7.1.6 in 36.213 + 0, // virtual_resource_block_assignment_flag, unused here + rbc,// resource_block_coding + getQm(mcs), + 0, // redundancy version + 1, // transport blocks + 0, // transport block to codeword swap flag + cc[CC_id].p_eNB == 1 ? 0 : 1, // transmission_scheme + 1, // number of layers + 1, // number of subbands + // uint8_t codebook_index, + 4, // UE category capacity + ue_template->physicalConfigDedicated->pdsch_ConfigDedicated->p_a, + 0, // delta_power_offset for TM5 + 0, // ngap + 0, // nprb + cc[CC_id].p_eNB == 1 ? 1 : 2, // transmission mode + 0, //number of PRBs treated as one subband, not used here + 0); // number of beamforming vectors, not used here + eNB->TX_req[CC_id].sfn_sf = fill_nfapi_tx_req(&eNB->TX_req[CC_id].tx_request_body, + (frameP * 10) + subframeP, + TBS, + eNB->pdu_index[CC_id], + dlsch_pdu->payload[0]); + LOG_D(MAC, "Filled NFAPI configuration for DCI/DLSCH/TXREQ %d, new SDU\n", + eNB->pdu_index[CC_id]); + eNB->pdu_index[CC_id]++; + program_dlsch_acknak(module_idP, + CC_id, + UE_id, + frameP, + subframeP, + dl_config_pdu->dci_dl_pdu.dci_dl_pdu_rel8.cce_idx); } - */ } - } + } // UE_id loop + stop_meas(&eNB->schedule_dlsch); + VCD_SIGNAL_DUMPER_DUMP_FUNCTION_BY_NAME(VCD_SIGNAL_DUMPER_FUNCTIONS_SCHEDULE_DLSCH, + VCD_FUNCTION_OUT); } //------------------------------------------------------------------------------ @@ -1886,7 +1234,7 @@ schedule_ue_spec_br(module_id_t module_idP, unsigned char dlsch_buffer[MAX_DLSCH_PAYLOAD_BYTES]; eNB_MAC_INST *mac = RC.mac[module_idP]; COMMON_channels_t *cc = mac->common_channels; - UE_list_t *UE_list = &mac->UE_list; + UE_info_t *UE_info = &mac->UE_info; UE_TEMPLATE *UE_template = NULL; UE_sched_ctrl_t *ue_sched_ctl = NULL; nfapi_dl_config_request_pdu_t *dl_config_pdu = NULL; @@ -1951,7 +1299,7 @@ schedule_ue_spec_br(module_id_t module_idP, } } - for (UE_id = UE_list->head; UE_id >= 0; UE_id = UE_list->next[UE_id]) { + for (UE_id = UE_info->list.head; UE_id >= 0; UE_id = UE_info->list.next[UE_id]) { int harq_pid = 0; rnti = UE_RNTI(module_idP, UE_id); @@ -1959,8 +1307,8 @@ schedule_ue_spec_br(module_id_t module_idP, continue; } - ue_sched_ctl = &(UE_list->UE_sched_ctrl[UE_id]); - UE_template = &(UE_list->UE_template[CC_id][UE_id]); + ue_sched_ctl = &UE_info->UE_sched_ctrl[UE_id]; + UE_template = &UE_info->UE_template[CC_id][UE_id]; if (UE_template->rach_resource_type == 0) { continue; @@ -2031,7 +1379,6 @@ schedule_ue_spec_br(module_id_t module_idP, ENB_FLAG_YES, MBMS_FLAG_NO, DCCH, - (TBS-ta_len-header_len_dcch), 0, 0); // transport block set size sdu_lengths[0] = 0; @@ -2049,7 +1396,7 @@ schedule_ue_spec_br(module_id_t module_idP, ENB_FLAG_YES, MBMS_FLAG_NO, DCCH, - TBS, //not used + TBS-ta_len-header_len_dcch, (char *)&dlsch_buffer[0], 0, 0); @@ -2068,8 +1415,8 @@ schedule_ue_spec_br(module_id_t module_idP, sdu_lengths[0]); sdu_length_total = sdu_lengths[0]; sdu_lcids[0] = DCCH; - UE_list->eNB_UE_stats[CC_id][UE_id].num_pdu_tx[DCCH]+=1; - UE_list->eNB_UE_stats[CC_id][UE_id].num_bytes_tx[DCCH]+=sdu_lengths[0]; + UE_info->eNB_UE_stats[CC_id][UE_id].num_pdu_tx[DCCH]+=1; + UE_info->eNB_UE_stats[CC_id][UE_id].num_bytes_tx[DCCH]+=sdu_lengths[0]; num_sdus = 1; } else { header_len_dcch = 0; @@ -2087,7 +1434,6 @@ schedule_ue_spec_br(module_id_t module_idP, ENB_FLAG_YES, MBMS_FLAG_NO, DCCH + 1, - (TBS-ta_len-header_len_dcch-sdu_length_total), 0, 0); // transport block set size less allocations for timing advance and DCCH SDU sdu_lengths[num_sdus] = 0; @@ -2105,7 +1451,7 @@ schedule_ue_spec_br(module_id_t module_idP, ENB_FLAG_YES, MBMS_FLAG_NO, DCCH+1, - TBS, //not used + TBS-ta_len-header_len_dcch-sdu_length_total, (char *)&dlsch_buffer[sdu_length_total], 0, 0); @@ -2121,8 +1467,8 @@ schedule_ue_spec_br(module_id_t module_idP, sdu_lcids[num_sdus] = DCCH1; sdu_length_total += sdu_lengths[num_sdus]; header_len_dcch += 2; - UE_list->eNB_UE_stats[CC_id][UE_id].num_pdu_tx[DCCH1] += 1; - UE_list->eNB_UE_stats[CC_id][UE_id].num_bytes_tx[DCCH1] += sdu_lengths[num_sdus]; + UE_info->eNB_UE_stats[CC_id][UE_id].num_pdu_tx[DCCH1] += 1; + UE_info->eNB_UE_stats[CC_id][UE_id].num_bytes_tx[DCCH1] += sdu_lengths[num_sdus]; num_sdus++; } } @@ -2152,7 +1498,6 @@ schedule_ue_spec_br(module_id_t module_idP, ENB_FLAG_YES, MBMS_FLAG_NO, lcid, - TBS - ta_len - header_len_dcch - sdu_length_total - header_len_dtch, 0, 0); @@ -2183,7 +1528,7 @@ schedule_ue_spec_br(module_id_t module_idP, ENB_FLAG_YES, MBMS_FLAG_NO, lcid, - TBS, //not used + TBS - ta_len - header_len_dcch - sdu_length_total - header_len_dtch, (char *) &dlsch_buffer[sdu_length_total], 0, 0); @@ -2274,7 +1619,7 @@ schedule_ue_spec_br(module_id_t module_idP, post_padding = TBS - sdu_length_total - header_len_dcch - header_len_dtch - ta_len; // 1 is for the postpadding header } - offset = generate_dlsch_header((unsigned char *)UE_list->DLSCH_pdu[CC_id][0][UE_id].payload[0], + offset = generate_dlsch_header((unsigned char *)UE_info->DLSCH_pdu[CC_id][0][UE_id].payload[0], num_sdus, //num_sdus sdu_lengths, // sdu_lcids, @@ -2307,15 +1652,15 @@ schedule_ue_spec_br(module_id_t module_idP, } /* Cycle through SDUs and place in dlsch_buffer */ - memcpy(&UE_list->DLSCH_pdu[CC_id][0][UE_id].payload[0][offset], dlsch_buffer, sdu_length_total); + memcpy(&UE_info->DLSCH_pdu[CC_id][0][UE_id].payload[0][offset], dlsch_buffer, sdu_length_total); /* Fill remainder of DLSCH with random data */ for (j = 0; j < (TBS - sdu_length_total - offset); j++) { - UE_list->DLSCH_pdu[CC_id][0][UE_id].payload[0][offset + sdu_length_total + j] = (char)(taus()&0xff); + UE_info->DLSCH_pdu[CC_id][0][UE_id].payload[0][offset + sdu_length_total + j] = (char)(taus()&0xff); } trace_pdu(DIRECTION_DOWNLINK, - (uint8_t *)UE_list->DLSCH_pdu[CC_id][0][UE_id].payload[0], + (uint8_t *)UE_info->DLSCH_pdu[CC_id][0][UE_id].payload[0], TBS, module_idP, 3, @@ -2331,7 +1676,7 @@ schedule_ue_spec_br(module_id_t module_idP, T_INT(frameP), T_INT(subframeP), T_INT(harq_pid), - T_BUFFER(UE_list->DLSCH_pdu[CC_id][0][UE_id].payload[0], TBS)); + T_BUFFER(UE_info->DLSCH_pdu[CC_id][0][UE_id].payload[0], TBS)); /* Do PUCCH power control */ /* This is the snr */ /* unit is not dBm, it's special from nfapi, convert to dBm */ @@ -2339,15 +1684,15 @@ schedule_ue_spec_br(module_id_t module_idP, target_snr = mac->puCch10xSnr / 10; /* This assumes accumulated tpc */ /* Make sure that we are only sending a tpc update once a frame, otherwise the control loop will freak out */ - int32_t framex10psubframe = UE_list->UE_template[CC_id][UE_id].pucch_tpc_tx_frame * 10 + UE_list->UE_template[CC_id][UE_id].pucch_tpc_tx_subframe; + int32_t framex10psubframe = UE_info->UE_template[CC_id][UE_id].pucch_tpc_tx_frame * 10 + UE_info->UE_template[CC_id][UE_id].pucch_tpc_tx_subframe; if (((framex10psubframe + 10) <= (frameP * 10 + subframeP)) || // normal case ((framex10psubframe > (frameP * 10 + subframeP)) && (((10240 - framex10psubframe +frameP * 10 + subframeP) >= 10)))) { // frame wrap-around if (ue_sched_ctl->pucch1_cqi_update[CC_id] == 1) { ue_sched_ctl->pucch1_cqi_update[CC_id] = 0; - UE_list->UE_template[CC_id][UE_id].pucch_tpc_tx_frame = frameP; - UE_list->UE_template[CC_id][UE_id].pucch_tpc_tx_subframe = subframeP; + UE_info->UE_template[CC_id][UE_id].pucch_tpc_tx_frame = frameP; + UE_info->UE_template[CC_id][UE_id].pucch_tpc_tx_subframe = subframeP; if (snr > target_snr + 4) { tpc = 0; //-1 @@ -2481,7 +1826,7 @@ schedule_ue_spec_br(module_id_t module_idP, TX_req->pdu_index = mac->pdu_index[CC_id]++; TX_req->num_segments = 1; TX_req->segments[0].segment_length = TX_req->pdu_length; - TX_req->segments[0].segment_data = mac->UE_list.DLSCH_pdu[CC_id][0][(unsigned char) UE_id].payload[0]; + TX_req->segments[0].segment_data = mac->UE_info.DLSCH_pdu[CC_id][0][(unsigned char) UE_id].payload[0]; mac->TX_req[CC_id].tx_request_body.number_of_pdus++; ackNAK_absSF = absSF + 4; ul_req = &mac->UL_req_tmp[CC_id][ackNAK_absSF % 10].ul_config_request_body; @@ -2515,9 +1860,9 @@ schedule_ue_spec_br(module_id_t module_idP, T_INT (frameP), T_INT (subframeP), T_INT (0 /* harq_pid always 0? */ ), - T_BUFFER (&mac->UE_list.DLSCH_pdu[CC_id][0][UE_id].payload[0], TX_req->pdu_length)); + T_BUFFER (&mac->UE_info.DLSCH_pdu[CC_id][0][UE_id].payload[0], TX_req->pdu_length)); trace_pdu(1, - (uint8_t *) mac->UE_list.DLSCH_pdu[CC_id][0][(unsigned char) UE_id].payload[0], + (uint8_t *) mac->UE_info.DLSCH_pdu[CC_id][0][(unsigned char) UE_id].payload[0], TX_req->pdu_length, UE_id, 3, @@ -2530,101 +1875,6 @@ schedule_ue_spec_br(module_id_t module_idP, } // end loop on UE_id } -//------------------------------------------------------------------------------ -void -fill_DLSCH_dci(module_id_t module_idP, - frame_t frameP, - sub_frame_t subframeP, - int *mbsfn_flagP) -//------------------------------------------------------------------------------ -{ - // loop over all allocated UEs and compute frequency allocations for PDSCH - int UE_id = -1; - uint8_t /* first_rb, */ nb_rb = 3; - rnti_t rnti; - //unsigned char *vrb_map; - uint8_t rballoc_sub[25]; - //uint8_t number_of_subbands=13; - //unsigned char round; - unsigned char harq_pid; - int i; - int CC_id; - eNB_MAC_INST *eNB = RC.mac[module_idP]; - UE_list_t *UE_list = &eNB->UE_list; - int N_RBG; - int N_RB_DL; - COMMON_channels_t *cc; - eNB_DLSCH_INFO *dlsch_info; - UE_TEMPLATE *ue_template; - start_meas(&eNB->fill_DLSCH_dci); - VCD_SIGNAL_DUMPER_DUMP_FUNCTION_BY_NAME(VCD_SIGNAL_DUMPER_FUNCTIONS_FILL_DLSCH_DCI, - VCD_FUNCTION_IN); - - for (CC_id = 0; CC_id < RC.nb_mac_CC[module_idP]; CC_id++) { - LOG_D(MAC, "Doing fill DCI for CC_id %d\n", - CC_id); - - if (mbsfn_flagP[CC_id] > 0) - continue; - - cc = &eNB->common_channels[CC_id]; - N_RBG = to_rbg(cc->mib->message.dl_Bandwidth); - N_RB_DL = to_prb(cc->mib->message.dl_Bandwidth); - - // UE specific DCIs - for (UE_id = UE_list->head; UE_id >= 0; UE_id = UE_list->next[UE_id]) { - dlsch_info = &eNB_dlsch_info[module_idP][CC_id][UE_id]; - LOG_T(MAC, "CC_id %d, UE_id: %d => status %d\n", - CC_id, - UE_id, - dlsch_info->status); - - if (dlsch_info->status == S_DL_SCHEDULED) { - // clear scheduling flag - dlsch_info->status = S_DL_WAITING; - rnti = UE_RNTI(module_idP, UE_id); - harq_pid = frame_subframe2_dl_harq_pid(cc->tdd_Config,frameP, - subframeP); - ue_template = &UE_list->UE_template[CC_id][UE_id]; - nb_rb = ue_template->nb_rb[harq_pid]; - - /// Synchronizing rballoc with rballoc_sub - for (i = 0; i < N_RBG; i++) { - rballoc_sub[i] = ue_template->rballoc_subband[harq_pid][i]; - } - - nfapi_dl_config_request_body_t *dl_config_request_body = &RC.mac[module_idP]->DL_req[CC_id].dl_config_request_body; - nfapi_dl_config_request_pdu_t *dl_config_pdu; - - for (i = 0; i < dl_config_request_body->number_pdu; i++) { - dl_config_pdu = &dl_config_request_body->dl_config_pdu_list[i]; - - if (dl_config_pdu->pdu_type == NFAPI_DL_CONFIG_DCI_DL_PDU_TYPE && - dl_config_pdu->dci_dl_pdu.dci_dl_pdu_rel8.rnti == rnti && - dl_config_pdu->dci_dl_pdu.dci_dl_pdu_rel8.dci_format != 1) { - dl_config_pdu->dci_dl_pdu.dci_dl_pdu_rel8.resource_block_coding = allocate_prbs_sub(nb_rb, - N_RB_DL, - N_RBG, - rballoc_sub); - dl_config_pdu->dci_dl_pdu.dci_dl_pdu_rel8.resource_allocation_type = 0; - } else if (dl_config_pdu->pdu_type == NFAPI_DL_CONFIG_DLSCH_PDU_TYPE && - dl_config_pdu->dlsch_pdu.dlsch_pdu_rel8.rnti == rnti && - dl_config_pdu->dlsch_pdu.dlsch_pdu_rel8.resource_allocation_type == 0) { - dl_config_pdu->dlsch_pdu.dlsch_pdu_rel8.resource_block_coding = allocate_prbs_sub(nb_rb, - N_RB_DL, - N_RBG, - rballoc_sub); - } - } - } - } - } - - stop_meas(&eNB->fill_DLSCH_dci); - VCD_SIGNAL_DUMPER_DUMP_FUNCTION_BY_NAME(VCD_SIGNAL_DUMPER_FUNCTIONS_FILL_DLSCH_DCI, - VCD_FUNCTION_OUT); -} - //------------------------------------------------------------------------------ unsigned char *get_dlsch_sdu(module_id_t module_idP, int CC_id, @@ -2661,7 +1911,7 @@ unsigned char *get_dlsch_sdu(module_id_t module_idP, CC_id, rntiP, UE_id); - return ((unsigned char *) &eNB->UE_list.DLSCH_pdu[CC_id][TBindex][UE_id].payload[0]); + return ((unsigned char *) &eNB->UE_info.DLSCH_pdu[CC_id][TBindex][UE_id].payload[0]); } LOG_E(MAC, "[eNB %d] Frame %d: CC_id %d UE with RNTI %x does not exist\n", @@ -2706,61 +1956,61 @@ set_ue_dai(sub_frame_t subframeP, int UE_id, uint8_t CC_id, uint8_t tdd_config, - UE_list_t *UE_list) + UE_info_t *UE_info) //------------------------------------------------------------------------------ { switch (tdd_config) { case 0: if (subframeP == 0 || subframeP == 1 || subframeP == 3 || subframeP == 5 || subframeP == 6 || subframeP == 8) { - UE_list->UE_template[CC_id][UE_id].DAI = 0; + UE_info->UE_template[CC_id][UE_id].DAI = 0; } break; case 1: if (subframeP == 0 || subframeP == 4 || subframeP == 5 || subframeP == 9) { - UE_list->UE_template[CC_id][UE_id].DAI = 0; + UE_info->UE_template[CC_id][UE_id].DAI = 0; } break; case 2: if (subframeP == 4 || subframeP == 5) { - UE_list->UE_template[CC_id][UE_id].DAI = 0; + UE_info->UE_template[CC_id][UE_id].DAI = 0; } break; case 3: if (subframeP == 5 || subframeP == 7 || subframeP == 9) { - UE_list->UE_template[CC_id][UE_id].DAI = 0; + UE_info->UE_template[CC_id][UE_id].DAI = 0; } break; case 4: if (subframeP == 0 || subframeP == 6) { - UE_list->UE_template[CC_id][UE_id].DAI = 0; + UE_info->UE_template[CC_id][UE_id].DAI = 0; } break; case 5: if (subframeP == 9) { - UE_list->UE_template[CC_id][UE_id].DAI = 0; + UE_info->UE_template[CC_id][UE_id].DAI = 0; } break; case 6: if (subframeP == 0 || subframeP == 1 || subframeP == 5 || subframeP == 6 || subframeP == 9) { - UE_list->UE_template[CC_id][UE_id].DAI = 0; + UE_info->UE_template[CC_id][UE_id].DAI = 0; } break; default: - UE_list->UE_template[CC_id][UE_id].DAI = 0; + UE_info->UE_template[CC_id][UE_id].DAI = 0; LOG_I(MAC, "unknown TDD config %d\n", tdd_config); break; @@ -3158,37 +2408,3 @@ schedule_PCH(module_id_t module_idP, stop_meas(&eNB->schedule_pch); return; } - -static int -slice_priority_compare(const void *_a, - const void *_b, - void *_c) { - const int slice_id1 = *(const int *) _a; - const int slice_id2 = *(const int *) _b; - const module_id_t Mod_id = *(int *) _c; - const slice_info_t *sli = &RC.mac[Mod_id]->slice_info; - - if (sli->dl[slice_id1].prio > sli->dl[slice_id2].prio) { - return -1; - } - - return 1; -} - -void -slice_priority_sort(module_id_t Mod_id, - int slice_list[MAX_NUM_SLICES]) { - int i; - int n_dl = RC.mac[Mod_id]->slice_info.n_dl; - - for (i = 0; i < n_dl; i++) { - slice_list[i] = i; - } - - qsort_r(slice_list, - n_dl, - sizeof(int), - slice_priority_compare, - &Mod_id); - return; -} diff --git a/openair2/LAYER2/MAC/eNB_scheduler_fairRR.c b/openair2/LAYER2/MAC/eNB_scheduler_fairRR.c index f47f88ca4de2b3cc5148669f886a96fe367a3b0c..00fd40109db819a754e3bbf9ad79810df59b0641 100644 --- a/openair2/LAYER2/MAC/eNB_scheduler_fairRR.c +++ b/openair2/LAYER2/MAC/eNB_scheduler_fairRR.c @@ -120,7 +120,7 @@ void pre_scd_nb_rbs_required( module_id_t module_idP, if(N_RB_DL==100) step_size=4; memset(nb_rbs_required, 0, sizeof(uint16_t)*MAX_NUM_CCs*NUMBER_OF_UE_MAX); - UE_list_t *UE_list = &RC.mac[module_idP]->UE_list; + UE_info_t *UE_info = &RC.mac[module_idP]->UE_info; for (UE_id = 0; UE_id <NUMBER_OF_UE_MAX; UE_id++) { if (pre_scd_activeUE[UE_id] != TRUE) @@ -134,7 +134,7 @@ void pre_scd_nb_rbs_required( module_id_t module_idP, for (lc_id = DCCH; lc_id <= DTCH; lc_id++) { rlc_status = mac_rlc_status_ind(module_idP, rnti, module_idP, frameP, subframeP, - ENB_FLAG_YES, MBMS_FLAG_NO, lc_id, 0,0, 0 + ENB_FLAG_YES, MBMS_FLAG_NO, lc_id, 0, 0 ); UE_template.dl_buffer_total += rlc_status.bytes_in_buffer; //storing the total dlsch buffer } @@ -144,7 +144,7 @@ void pre_scd_nb_rbs_required( module_id_t module_idP, // Calculate the number of RBs required by each UE on the basis of logical channel's buffer //update CQI information across component carriers eNB_UE_stats = &pre_scd_eNB_UE_stats[CC_id][UE_id]; - eNB_UE_stats->dlsch_mcs1 = cqi_to_mcs[UE_list->UE_sched_ctrl[UE_id].dl_cqi[CC_id]]; + eNB_UE_stats->dlsch_mcs1 = cqi_to_mcs[UE_info->UE_sched_ctrl[UE_id].dl_cqi[CC_id]]; if (UE_template.dl_buffer_total > 0) { nb_rbs_required[CC_id][UE_id] = search_rbs_required(eNB_UE_stats->dlsch_mcs1, UE_template.dl_buffer_total, N_RB_DL, step_size); @@ -175,7 +175,7 @@ void dlsch_scheduler_pre_ue_select_fairRR( DLSCH_UE_SELECT dlsch_ue_select[MAX_NUM_CCs]) { eNB_MAC_INST *eNB = RC.mac[module_idP]; COMMON_channels_t *cc = eNB->common_channels; - UE_list_t *UE_list = &eNB->UE_list; + UE_info_t *UE_info = &eNB->UE_info; UE_sched_ctrl_t *ue_sched_ctl; uint8_t CC_id; int UE_id; @@ -208,7 +208,7 @@ void dlsch_scheduler_pre_ue_select_fairRR( DL_req = &eNB->DL_req[CC_id].dl_config_request_body; for (UE_id = 0; UE_id < NUMBER_OF_UE_MAX; UE_id++) { - if (UE_list->active[UE_id] == FALSE) { + if (UE_info->active[UE_id] == FALSE) { continue; } @@ -222,12 +222,12 @@ void dlsch_scheduler_pre_ue_select_fairRR( continue; } - ue_sched_ctl = &UE_list->UE_sched_ctrl[UE_id]; + ue_sched_ctl = &UE_info->UE_sched_ctrl[UE_id]; harq_pid = frame_subframe2_dl_harq_pid(cc[CC_id].tdd_Config,frameP,subframeP); round = ue_sched_ctl->round[CC_id][harq_pid]; if (round != 8) { // retransmission - if(UE_list->UE_template[CC_id][UE_id].nb_rb[harq_pid] == 0) { + if(UE_info->UE_template[CC_id][UE_id].nb_rb[harq_pid] == 0) { continue; } @@ -266,7 +266,7 @@ void dlsch_scheduler_pre_ue_select_fairRR( dl_config_pdu->dci_dl_pdu.dci_dl_pdu_rel8.rnti_type = (format_flag == 0)?2:1; dl_config_pdu->dci_dl_pdu.dci_dl_pdu_rel8.aggregation_level = aggregation; DL_req->number_pdu++; - nb_rbs_required[CC_id][UE_id] = UE_list->UE_template[CC_id][UE_id].nb_rb[harq_pid]; + nb_rbs_required[CC_id][UE_id] = UE_info->UE_template[CC_id][UE_id].nb_rb[harq_pid]; // Insert DLSCH(retransmission) UE into selected UE list dlsch_ue_select[CC_id].list[dlsch_ue_select[CC_id].ue_num].UE_id = UE_id; dlsch_ue_select[CC_id].list[dlsch_ue_select[CC_id].ue_num].ue_priority = SCH_DL_RETRANS; @@ -284,7 +284,7 @@ void dlsch_scheduler_pre_ue_select_fairRR( UE_id, CC_id, cc[CC_id].tdd_Config->subframeAssignment, - UE_list); + UE_info); // update UL DAI after DLSCH scheduling set_ul_DAI(module_idP,UE_id,CC_id,frameP,subframeP); } @@ -324,7 +324,7 @@ void dlsch_scheduler_pre_ue_select_fairRR( break; } - if (UE_list->active[UE_id] == FALSE) { + if (UE_info->active[UE_id] == FALSE) { continue; } @@ -337,7 +337,7 @@ void dlsch_scheduler_pre_ue_select_fairRR( continue; } - ue_sched_ctl = &UE_list->UE_sched_ctrl[UE_id]; + ue_sched_ctl = &UE_info->UE_sched_ctrl[UE_id]; for(i = 0; i<dlsch_ue_select[CC_id].ue_num; i++) { if(dlsch_ue_select[CC_id].list[i].UE_id == UE_id) { @@ -408,7 +408,7 @@ void dlsch_scheduler_pre_ue_select_fairRR( UE_id, CC_id, cc[CC_id].tdd_Config->subframeAssignment, - UE_list); + UE_info); // update UL DAI after DLSCH scheduling set_ul_DAI(module_idP,UE_id,CC_id,frameP,subframeP); } @@ -448,7 +448,7 @@ void dlsch_scheduler_pre_ue_select_fairRR( break; } - if (UE_list->active[UE_id] == FALSE) { + if (UE_info->active[UE_id] == FALSE) { continue; } @@ -461,7 +461,7 @@ void dlsch_scheduler_pre_ue_select_fairRR( continue; } - ue_sched_ctl = &UE_list->UE_sched_ctrl[UE_id]; + ue_sched_ctl = &UE_info->UE_sched_ctrl[UE_id]; for(i = 0; i<dlsch_ue_select[CC_id].ue_num; i++) { if(dlsch_ue_select[CC_id].list[i].UE_id == UE_id) { @@ -532,7 +532,7 @@ void dlsch_scheduler_pre_ue_select_fairRR( UE_id, CC_id, cc[CC_id].tdd_Config->subframeAssignment, - UE_list); + UE_info); // update UL DAI after DLSCH scheduling set_ul_DAI(module_idP,UE_id,CC_id,frameP,subframeP); } @@ -558,7 +558,331 @@ void dlsch_scheduler_pre_ue_select_fairRR( return; } +void dlsch_scheduler_pre_processor_reset_fairRR( + module_id_t module_idP, + frame_t frameP, + sub_frame_t subframeP, + int min_rb_unit[NFAPI_CC_MAX], + uint16_t nb_rbs_required[NFAPI_CC_MAX][MAX_MOBILES_PER_ENB], + uint8_t rballoc_sub[NFAPI_CC_MAX][N_RBG_MAX], + uint8_t MIMO_mode_indicator[NFAPI_CC_MAX][N_RBG_MAX]) { + int UE_id; + uint8_t CC_id; + int i, j; + UE_info_t *UE_info; + UE_sched_ctrl_t *ue_sched_ctl; + int N_RB_DL, RBGsize, RBGsize_last; + int N_RBG[NFAPI_CC_MAX]; + rnti_t rnti; + uint8_t *vrb_map; + COMMON_channels_t *cc; + + // + for (CC_id = 0; CC_id < RC.nb_mac_CC[module_idP]; CC_id++) { + // initialize harq_pid and round + cc = &RC.mac[module_idP]->common_channels[CC_id]; + N_RBG[CC_id] = to_rbg(cc->mib->message.dl_Bandwidth); + min_rb_unit[CC_id] = get_min_rb_unit(module_idP, CC_id); + + for (UE_id = 0; UE_id < MAX_MOBILES_PER_ENB; ++UE_id) { + UE_info = &RC.mac[module_idP]->UE_info; + ue_sched_ctl = &UE_info->UE_sched_ctrl[UE_id]; + rnti = UE_RNTI(module_idP, UE_id); + + if (rnti == NOT_A_RNTI) + continue; + + if (UE_info->active[UE_id] != TRUE) + continue; + + LOG_D(MAC, "Running preprocessor for UE %d (%x)\n", UE_id, rnti); + + // initialize harq_pid and round + if (ue_sched_ctl->ta_timer) + ue_sched_ctl->ta_timer--; + + /* + eNB_UE_stats *eNB_UE_stats; + + if (eNB_UE_stats == NULL) + return; + + + mac_xface->get_ue_active_harq_pid(module_idP,CC_id,rnti, + frameP,subframeP, + &ue_sched_ctl->harq_pid[CC_id], + &ue_sched_ctl->round[CC_id], + openair_harq_DL); + + + if (ue_sched_ctl->ta_timer == 0) { + + // WE SHOULD PROTECT the eNB_UE_stats with a mutex here ... + + ue_sched_ctl->ta_timer = 20; // wait 20 subframes before taking TA measurement from PHY + switch (N_RB_DL) { + case 6: + ue_sched_ctl->ta_update = eNB_UE_stats->timing_advance_update; + break; + + case 15: + ue_sched_ctl->ta_update = eNB_UE_stats->timing_advance_update/2; + break; + + case 25: + ue_sched_ctl->ta_update = eNB_UE_stats->timing_advance_update/4; + break; + + case 50: + ue_sched_ctl->ta_update = eNB_UE_stats->timing_advance_update/8; + break; + case 75: + ue_sched_ctl->ta_update = eNB_UE_stats->timing_advance_update/12; + break; + + case 100: + ue_sched_ctl->ta_update = eNB_UE_stats->timing_advance_update/16; + break; + } + // clear the update in case PHY does not have a new measurement after timer expiry + eNB_UE_stats->timing_advance_update = 0; + } + else { + ue_sched_ctl->ta_timer--; + ue_sched_ctl->ta_update =0; // don't trigger a timing advance command + } + + + if (UE_id==0) { + VCD_SIGNAL_DUMPER_DUMP_VARIABLE_BY_NAME(VCD_SIGNAL_DUMPER_VARIABLES_UE0_TIMING_ADVANCE,ue_sched_ctl->ta_update); + } + */ + nb_rbs_required[CC_id][UE_id] = 0; + ue_sched_ctl->pre_nb_available_rbs[CC_id] = 0; + ue_sched_ctl->dl_pow_off[CC_id] = 2; + + for (i = 0; i < N_RBG[CC_id]; i++) { + ue_sched_ctl->rballoc_sub_UE[CC_id][i] = 0; + } + } + + N_RB_DL = to_prb(RC.mac[module_idP]->common_channels[CC_id].mib->message.dl_Bandwidth); + + switch (N_RB_DL) { + case 6: + RBGsize = 1; + RBGsize_last = 1; + break; + + case 15: + RBGsize = 2; + RBGsize_last = 1; + break; + + case 25: + RBGsize = 2; + RBGsize_last = 1; + break; + + case 50: + RBGsize = 3; + RBGsize_last = 2; + break; + + case 75: + RBGsize = 4; + RBGsize_last = 3; + break; + + case 100: + RBGsize = 4; + RBGsize_last = 4; + break; + + default: + AssertFatal(1 == 0, "unsupported RBs (%d)\n", N_RB_DL); + } + + vrb_map = RC.mac[module_idP]->common_channels[CC_id].vrb_map; + + // Initialize Subbands according to VRB map + for (i = 0; i < N_RBG[CC_id]; i++) { + int rb_size = i == N_RBG[CC_id] - 1 ? RBGsize_last : RBGsize; + + // for SI-RNTI,RA-RNTI and P-RNTI allocations + for (j = 0; j < rb_size; j++) { + if (vrb_map[j + (i*RBGsize)] != 0) { + rballoc_sub[CC_id][i] = 1; + LOG_D(MAC, "Frame %d, subframe %d : vrb %d allocated\n", frameP, subframeP, j + (i*RBGsize)); + break; + } + } + + //LOG_D(MAC, "Frame %d Subframe %d CC_id %d RBG %i : rb_alloc %d\n", + //frameP, subframeP, CC_id, i, rballoc_sub[CC_id][i]); + MIMO_mode_indicator[CC_id][i] = 2; + } + } +} + +// This function returns the estimated number of RBs required by each UE for downlink scheduling +void assign_rbs_required_fairRR( + module_id_t Mod_id, + frame_t frameP, + sub_frame_t subframe, + uint16_t nb_rbs_required[NFAPI_CC_MAX][MAX_MOBILES_PER_ENB]) { + uint16_t TBS = 0; + int UE_id, n, i, j, CC_id, pCCid, tmp; + UE_info_t *UE_info = &RC.mac[Mod_id]->UE_info; + eNB_UE_STATS *eNB_UE_stats, *eNB_UE_stats_i, *eNB_UE_stats_j; + int N_RB_DL; + + // clear rb allocations across all CC_id + for (UE_id = 0; UE_id < MAX_MOBILES_PER_ENB; UE_id++) { + if (UE_info->active[UE_id] != TRUE) + continue; + + pCCid = UE_PCCID(Mod_id, UE_id); + + // update CQI information across component carriers + for (n = 0; n < UE_info->numactiveCCs[UE_id]; n++) { + CC_id = UE_info->ordered_CCids[n][UE_id]; + eNB_UE_stats = &UE_info->eNB_UE_stats[CC_id][UE_id]; + eNB_UE_stats->dlsch_mcs1 = cqi_to_mcs[UE_info->UE_sched_ctrl[UE_id].dl_cqi[CC_id]]; + } + + // provide the list of CCs sorted according to MCS + for (i = 0; i < UE_info->numactiveCCs[UE_id]; ++i) { + eNB_UE_stats_i = + &UE_info->eNB_UE_stats[UE_info->ordered_CCids[i][UE_id]][UE_id]; + + for (j = i + 1; j < UE_info->numactiveCCs[UE_id]; j++) { + DevAssert(j < NFAPI_CC_MAX); + eNB_UE_stats_j = + &UE_info->eNB_UE_stats[UE_info->ordered_CCids[j][UE_id]][UE_id]; + + if (eNB_UE_stats_j->dlsch_mcs1 > eNB_UE_stats_i->dlsch_mcs1) { + tmp = UE_info->ordered_CCids[i][UE_id]; + UE_info->ordered_CCids[i][UE_id] = UE_info->ordered_CCids[j][UE_id]; + UE_info->ordered_CCids[j][UE_id] = tmp; + } + } + } + + if (UE_info->UE_template[pCCid][UE_id].dl_buffer_total > 0) { + LOG_D(MAC, "[preprocessor] assign RB for UE %d\n", UE_id); + + for (i = 0; i < UE_info->numactiveCCs[UE_id]; i++) { + CC_id = UE_info->ordered_CCids[i][UE_id]; + eNB_UE_stats = &UE_info->eNB_UE_stats[CC_id][UE_id]; + const int min_rb_unit = get_min_rb_unit(Mod_id, CC_id); + + if (eNB_UE_stats->dlsch_mcs1 == 0) { + nb_rbs_required[CC_id][UE_id] = 4; // don't let the TBS get too small + } else { + nb_rbs_required[CC_id][UE_id] = min_rb_unit; + } + + TBS = get_TBS_DL(eNB_UE_stats->dlsch_mcs1, nb_rbs_required[CC_id][UE_id]); + LOG_D(MAC, + "[preprocessor] start RB assignement for UE %d CC_id %d dl " + "buffer %d (RB unit %d, MCS %d, TBS %d) \n", + UE_id, + CC_id, + UE_info->UE_template[pCCid][UE_id].dl_buffer_total, + nb_rbs_required[CC_id][UE_id], + eNB_UE_stats->dlsch_mcs1, + TBS); + N_RB_DL = to_prb(RC.mac[Mod_id]->common_channels[CC_id].mib->message.dl_Bandwidth); + + /* calculating required number of RBs for each UE */ + while (TBS < UE_info->UE_template[pCCid][UE_id].dl_buffer_total) { + nb_rbs_required[CC_id][UE_id] += min_rb_unit; + + if (nb_rbs_required[CC_id][UE_id] > N_RB_DL) { + TBS = get_TBS_DL(eNB_UE_stats->dlsch_mcs1, N_RB_DL); + nb_rbs_required[CC_id][UE_id] = N_RB_DL; + break; + } + + TBS = get_TBS_DL(eNB_UE_stats->dlsch_mcs1, + nb_rbs_required[CC_id][UE_id]); + } // end of while + + LOG_D(MAC, + "[eNB %d] Frame %d: UE %d on CC %d: RB unit %d, nb_required RB " + "%d (TBS %d, mcs %d)\n", + Mod_id, + frameP, + UE_id, + CC_id, + min_rb_unit, + nb_rbs_required[CC_id][UE_id], + TBS, + eNB_UE_stats->dlsch_mcs1); + } + } + } +} + +void dlsch_scheduler_pre_processor_allocate_fairRR( + module_id_t Mod_id, + int UE_id, + uint8_t CC_id, + int N_RBG, + uint16_t nb_rbs_required[NFAPI_CC_MAX][MAX_MOBILES_PER_ENB], + uint16_t nb_rbs_remaining[NFAPI_CC_MAX][MAX_MOBILES_PER_ENB], + uint8_t rballoc_sub[NFAPI_CC_MAX][N_RBG_MAX]) { + int i; + UE_info_t *UE_info = &RC.mac[Mod_id]->UE_info; + UE_sched_ctrl_t *ue_sched_ctl = &UE_info->UE_sched_ctrl[UE_id]; + int N_RB_DL = + to_prb(RC.mac[Mod_id]->common_channels[CC_id].mib->message.dl_Bandwidth); + const int min_rb_unit = get_min_rb_unit(Mod_id, CC_id); + + for (i = 0; i < N_RBG; i++) { + if (rballoc_sub[CC_id][i] != 0) + continue; + + if (ue_sched_ctl->rballoc_sub_UE[CC_id][i] != 0) + continue; + + if (nb_rbs_remaining[CC_id][UE_id] <= 0) + continue; + + if (ue_sched_ctl->pre_nb_available_rbs[CC_id] + >= nb_rbs_required[CC_id][UE_id]) + continue; + + if (ue_sched_ctl->dl_pow_off[CC_id] == 0) + continue; + + if ((i == N_RBG - 1) && ((N_RB_DL == 25) || (N_RB_DL == 50))) { + // Allocating last, smaller RBG + if (nb_rbs_remaining[CC_id][UE_id] >= min_rb_unit - 1) { + rballoc_sub[CC_id][i] = 1; + ue_sched_ctl->rballoc_sub_UE[CC_id][i] = 1; + + nb_rbs_remaining[CC_id][UE_id] = + nb_rbs_remaining[CC_id][UE_id] - min_rb_unit + 1; + ue_sched_ctl->pre_nb_available_rbs[CC_id] = + ue_sched_ctl->pre_nb_available_rbs[CC_id] + min_rb_unit - 1; + } + } else { + // Allocating a standard-sized RBG + if (nb_rbs_remaining[CC_id][UE_id] >= min_rb_unit) { + rballoc_sub[CC_id][i] = 1; + ue_sched_ctl->rballoc_sub_UE[CC_id][i] = 1; + + nb_rbs_remaining[CC_id][UE_id] = + nb_rbs_remaining[CC_id][UE_id] - min_rb_unit; + ue_sched_ctl->pre_nb_available_rbs[CC_id] = + ue_sched_ctl->pre_nb_available_rbs[CC_id] + min_rb_unit; + } + } + } +} // This function assigns pre-available RBS to each UE in specified sub-bands before scheduling is done void dlsch_scheduler_pre_processor_fairRR (module_id_t Mod_id, @@ -570,9 +894,8 @@ void dlsch_scheduler_pre_processor_fairRR (module_id_t Mod_id, uint16_t temp_total_rbs_count; unsigned char temp_total_ue_count; unsigned char MIMO_mode_indicator[MAX_NUM_CCs][N_RBG_MAX]; - uint8_t slice_allocation[MAX_NUM_CCs][N_RBG_MAX]; int UE_id, i; - uint16_t j,c; + uint16_t j; uint16_t nb_rbs_required[MAX_NUM_CCs][MAX_MOBILES_PER_ENB]; uint16_t nb_rbs_required_remaining[MAX_NUM_CCs][MAX_MOBILES_PER_ENB]; // uint16_t nb_rbs_required_remaining_1[MAX_NUM_CCs][NUMBER_OF_UE_MAX]; @@ -581,7 +904,7 @@ void dlsch_scheduler_pre_processor_fairRR (module_id_t Mod_id, int min_rb_unit[MAX_NUM_CCs]; // uint16_t r1=0; uint8_t CC_id; - UE_list_t *UE_list = &RC.mac[Mod_id]->UE_list; + UE_info_t *UE_info = &RC.mac[Mod_id]->UE_info; int N_RB_DL; UE_sched_ctrl_t *ue_sched_ctl; // int rrc_status = RRC_IDLE; @@ -607,29 +930,27 @@ void dlsch_scheduler_pre_processor_fairRR (module_id_t Mod_id, min_rb_unit[CC_id] = get_min_rb_unit(Mod_id, CC_id); for (i = 0; i < NUMBER_OF_UE_MAX; i++) { - if (UE_list->active[i] != TRUE) + if (UE_info->active[i] != TRUE) continue; UE_id = i; // Initialize scheduling information for all active UEs - dlsch_scheduler_pre_processor_reset(Mod_id, - 0, - frameP, - subframeP, - min_rb_unit, - (uint16_t (*)[MAX_MOBILES_PER_ENB])nb_rbs_required, - rballoc_sub, - MIMO_mode_indicator, - mbsfn_flag); + dlsch_scheduler_pre_processor_reset_fairRR( + Mod_id, + frameP, + subframeP, + min_rb_unit, + (uint16_t(*)[MAX_MOBILES_PER_ENB])nb_rbs_required, + rballoc_sub, + MIMO_mode_indicator); } } #if (!defined(PRE_SCD_THREAD)) - // Store the DLSCH buffer for each logical channel - store_dlsch_buffer(Mod_id,0, frameP, subframeP); + // Store the DLSCH buffer for each logical channel and for PCCID (assume 0) + store_dlsch_buffer(Mod_id, 0, frameP, subframeP); // Calculate the number of RBs required by each UE on the basis of logical channel's buffer - assign_rbs_required(Mod_id, 0, frameP, subframeP, nb_rbs_required, - min_rb_unit); + assign_rbs_required_fairRR(Mod_id, frameP, subframeP, nb_rbs_required); #else memcpy(nb_rbs_required, pre_nb_rbs_required[dlsch_ue_select_tbl_in_use], sizeof(uint16_t)*MAX_NUM_CCs*MAX_MOBILES_PER_ENB); #endif @@ -678,7 +999,7 @@ void dlsch_scheduler_pre_processor_fairRR (module_id_t Mod_id, } rnti = dlsch_ue_select[CC_id].list[i].rnti; - ue_sched_ctl = &UE_list->UE_sched_ctrl[UE_id]; + ue_sched_ctl = &UE_info->UE_sched_ctrl[UE_id]; harq_pid = frame_subframe2_dl_harq_pid(cc->tdd_Config,frameP,subframeP); Round = ue_sched_ctl->round[CC_id][harq_pid]; @@ -689,23 +1010,15 @@ void dlsch_scheduler_pre_processor_fairRR (module_id_t Mod_id, nb_rbs_required_remaining[CC_id][UE_id] = cmin(average_rbs_per_user[CC_id], dlsch_ue_select[CC_id].list[i].nb_rb); } - /* slicing support has been introduced into the scheduler. Provide dummy - * data so that the preprocessor "simply works" */ - for (c = 0; c < MAX_NUM_CCs; ++c) - for (j = 0; j < N_RBG_MAX; ++j) - slice_allocation[c][j] = 1; - LOG_T(MAC,"calling dlsch_scheduler_pre_processor_allocate .. \n "); - dlsch_scheduler_pre_processor_allocate (Mod_id, - UE_id, - CC_id, - N_RBG[CC_id], - min_rb_unit[CC_id], - (uint16_t (*)[MAX_MOBILES_PER_ENB])nb_rbs_required, - (uint16_t (*)[MAX_MOBILES_PER_ENB])nb_rbs_required_remaining, - rballoc_sub, - slice_allocation, - MIMO_mode_indicator); + dlsch_scheduler_pre_processor_allocate_fairRR( + Mod_id, + UE_id, + CC_id, + N_RBG[CC_id], + (uint16_t(*)[NUMBER_OF_UE_MAX])nb_rbs_required, + (uint16_t(*)[NUMBER_OF_UE_MAX])nb_rbs_required_remaining, + rballoc_sub); temp_total_rbs_count -= ue_sched_ctl->pre_nb_available_rbs[CC_id]; temp_total_ue_count--; @@ -782,7 +1095,7 @@ void dlsch_scheduler_pre_processor_fairRR (module_id_t Mod_id, } UE_id = dlsch_ue_select[CC_id].list[i].UE_id; - ue_sched_ctl = &RC.mac[Mod_id]->UE_list.UE_sched_ctrl[UE_id]; + ue_sched_ctl = &RC.mac[Mod_id]->UE_info.UE_sched_ctrl[UE_id]; //PHY_vars_eNB_g[Mod_id]->mu_mimo_mode[UE_id].dl_pow_off = dl_pow_off[UE_id]; if (ue_sched_ctl->pre_nb_available_rbs[CC_id] > 0) { @@ -835,7 +1148,7 @@ schedule_ue_spec_fairRR(module_id_t module_idP, uint16_t sdu_length_total = 0; eNB_MAC_INST *eNB = RC.mac[module_idP]; COMMON_channels_t *cc = eNB->common_channels; - UE_list_t *UE_list = &eNB->UE_list; + UE_info_t *UE_info = &eNB->UE_info; // int continue_flag = 0; int32_t snr, target_snr; int32_t tpc = 1; @@ -933,7 +1246,7 @@ schedule_ue_spec_fairRR(module_id_t module_idP, N_RBG[CC_id] = to_rbg(cc[CC_id].mib->message.dl_Bandwidth); // store the global enb stats: - eNB->eNB_stats[CC_id].num_dlactive_UEs = UE_list->num_UEs; + eNB->eNB_stats[CC_id].num_dlactive_UEs = UE_info->num_UEs; eNB->eNB_stats[CC_id].available_prbs = total_nb_available_rb[CC_id]; eNB->eNB_stats[CC_id].total_available_prbs += @@ -973,12 +1286,12 @@ schedule_ue_spec_fairRR(module_id_t module_idP, rnti = UE_RNTI(module_idP,UE_id); if (rnti==NOT_A_RNTI) { - LOG_E(MAC,"Cannot find rnti for UE_id %d (num_UEs %d)\n",UE_id,UE_list->num_UEs); + LOG_E(MAC,"Cannot find rnti for UE_id %d (num_UEs %d)\n",UE_id,UE_info->num_UEs); continue; } - eNB_UE_stats = &UE_list->eNB_UE_stats[CC_id][UE_id]; - ue_sched_ctl = &UE_list->UE_sched_ctrl[UE_id]; + eNB_UE_stats = &UE_info->eNB_UE_stats[CC_id][UE_id]; + ue_sched_ctl = &UE_info->UE_sched_ctrl[UE_id]; /* switch(get_tmode(module_idP,CC_id,UE_id)){ @@ -1005,7 +1318,7 @@ schedule_ue_spec_fairRR(module_id_t module_idP, UE_id, CC_id, cc[CC_id].tdd_Config->subframeAssignment, - UE_list); + UE_info); // update UL DAI after DLSCH scheduling set_ul_DAI(module_idP,UE_id,CC_id,frameP,subframeP); } @@ -1013,18 +1326,16 @@ schedule_ue_spec_fairRR(module_id_t module_idP, nb_available_rb = ue_sched_ctl->pre_nb_available_rbs[CC_id]; harq_pid = frame_subframe2_dl_harq_pid(cc->tdd_Config,frameP,subframeP); round = ue_sched_ctl->round[CC_id][harq_pid]; - UE_list->eNB_UE_stats[CC_id][UE_id].crnti = rnti; - UE_list->eNB_UE_stats[CC_id][UE_id].rrc_status = - mac_eNB_get_rrc_status(module_idP, rnti); - UE_list->eNB_UE_stats[CC_id][UE_id].harq_pid = harq_pid; - UE_list->eNB_UE_stats[CC_id][UE_id].harq_round = round; + UE_info->eNB_UE_stats[CC_id][UE_id].crnti = rnti; + UE_info->eNB_UE_stats[CC_id][UE_id].rrc_status = mac_eNB_get_rrc_status(module_idP, rnti); + UE_info->eNB_UE_stats[CC_id][UE_id].harq_pid = harq_pid; + UE_info->eNB_UE_stats[CC_id][UE_id].harq_round = round; - if (UE_list->eNB_UE_stats[CC_id][UE_id].rrc_status < RRC_RECONFIGURED) { - UE_list->UE_sched_ctrl[UE_id].uplane_inactivity_timer = 0; + if (UE_info->eNB_UE_stats[CC_id][UE_id].rrc_status < RRC_RECONFIGURED) { + UE_info->UE_sched_ctrl[UE_id].uplane_inactivity_timer = 0; } - if (UE_list->eNB_UE_stats[CC_id][UE_id].rrc_status < - RRC_CONNECTED) + if (UE_info->eNB_UE_stats[CC_id][UE_id].rrc_status < RRC_CONNECTED) continue; sdu_length_total = 0; @@ -1043,13 +1354,11 @@ schedule_ue_spec_fairRR(module_id_t module_idP, //eNB_UE_stats->dlsch_mcs1 = cmin(eNB_UE_stats->dlsch_mcs1, openair_daq_vars.target_ue_dl_mcs); // store stats - //UE_list->eNB_UE_stats[CC_id][UE_id].dl_cqi= eNB_UE_stats->dl_cqi; + //UE_info->eNB_UE_stats[CC_id][UE_id].dl_cqi= eNB_UE_stats->dl_cqi; // initializing the rb allocation indicator for each UE for (j = 0; j < N_RBG[CC_id]; j++) { - UE_list-> - UE_template[CC_id][UE_id].rballoc_subband[harq_pid][j] - = 0; + UE_info->UE_template[CC_id][UE_id].rballoc_subband[harq_pid][j] = 0; } LOG_D(MAC, @@ -1057,33 +1366,31 @@ schedule_ue_spec_fairRR(module_id_t module_idP, module_idP, frameP, UE_id, CC_id, rnti, harq_pid, round, nb_available_rb, ue_sched_ctl->dl_cqi[CC_id], eNB_UE_stats->dlsch_mcs1, - UE_list->eNB_UE_stats[CC_id][UE_id].rrc_status); + UE_info->eNB_UE_stats[CC_id][UE_id].rrc_status); /* process retransmission */ if (round != 8) { // get freq_allocation - nb_rb = UE_list->UE_template[CC_id][UE_id].nb_rb[harq_pid]; + nb_rb = UE_info->UE_template[CC_id][UE_id].nb_rb[harq_pid]; TBS = - get_TBS_DL(UE_list-> - UE_template[CC_id][UE_id].oldmcs1[harq_pid], + get_TBS_DL(UE_info->UE_template[CC_id][UE_id].oldmcs1[harq_pid], nb_rb); if (nb_rb <= nb_available_rb) { if (cc[CC_id].tdd_Config != NULL) { - UE_list->UE_template[CC_id][UE_id].DAI++; + UE_info->UE_template[CC_id][UE_id].DAI++; update_ul_dci(module_idP, CC_id, rnti, - UE_list->UE_template[CC_id][UE_id]. - DAI,subframeP); + UE_info->UE_template[CC_id][UE_id].DAI,subframeP); LOG_D(MAC, "DAI update: CC_id %d subframeP %d: UE %d, DAI %d\n", CC_id, subframeP, UE_id, - UE_list->UE_template[CC_id][UE_id].DAI); + UE_info->UE_template[CC_id][UE_id].DAI); } if (nb_rb == ue_sched_ctl->pre_nb_available_rbs[CC_id]) { for (j = 0; j < N_RBG[CC_id]; j++) { // for indicating the rballoc for each sub-band - UE_list->UE_template[CC_id][UE_id]. + UE_info->UE_template[CC_id][UE_id]. rballoc_subband[harq_pid][j] = ue_sched_ctl->rballoc_sub_UE[CC_id][j]; } @@ -1094,16 +1401,10 @@ schedule_ue_spec_fairRR(module_id_t module_idP, while ((nb_rb_temp > 0) && (j < N_RBG[CC_id])) { if (ue_sched_ctl->rballoc_sub_UE[CC_id][j] == 1) { - if (UE_list-> - UE_template[CC_id] - [UE_id].rballoc_subband[harq_pid][j]) - printf - ("WARN: rballoc_subband not free for retrans?\n"); + if (UE_info->UE_template[CC_id][UE_id].rballoc_subband[harq_pid][j]) + LOG_W(MAC, "WARN: rballoc_subband not free for retrans?\n"); - UE_list-> - UE_template[CC_id] - [UE_id].rballoc_subband[harq_pid][j] = - ue_sched_ctl->rballoc_sub_UE[CC_id][j]; + UE_info->UE_template[CC_id][UE_id].rballoc_subband[harq_pid][j] = ue_sched_ctl->rballoc_sub_UE[CC_id][j]; if ((j == N_RBG[CC_id] - 1) && ((N_RB_DL[CC_id] == 25) || @@ -1127,7 +1428,7 @@ schedule_ue_spec_fairRR(module_id_t module_idP, eNB->mu_mimo_mode[UE_id].dl_pow_off = ue_sched_ctl->dl_pow_off[CC_id]; for(j=0; j<N_RBG[CC_id]; j++) { - eNB->mu_mimo_mode[UE_id].rballoc_sub[j] = UE_list->UE_template[CC_id][UE_id].rballoc_subband[harq_pid][j]; + eNB->mu_mimo_mode[UE_id].rballoc_sub[j] = UE_info->UE_template[CC_id][UE_id].rballoc_subband[harq_pid][j]; } */ @@ -1164,36 +1465,23 @@ schedule_ue_spec_fairRR(module_id_t module_idP, harq_process = harq_pid; dl_config_pdu->dci_dl_pdu.dci_dl_pdu_rel8.tpc = 1; // dont adjust power when retransmitting dl_config_pdu->dci_dl_pdu. - dci_dl_pdu_rel8.new_data_indicator_1 = - UE_list->UE_template[CC_id][UE_id]. - oldNDI[harq_pid]; - dl_config_pdu->dci_dl_pdu.dci_dl_pdu_rel8.mcs_1 = - UE_list->UE_template[CC_id][UE_id]. - oldmcs1[harq_pid]; - dl_config_pdu->dci_dl_pdu. - dci_dl_pdu_rel8.redundancy_version_1 = - round & 3; + dci_dl_pdu_rel8.new_data_indicator_1 = UE_info->UE_template[CC_id][UE_id].oldNDI[harq_pid]; + dl_config_pdu->dci_dl_pdu.dci_dl_pdu_rel8.mcs_1 = UE_info->UE_template[CC_id][UE_id].oldmcs1[harq_pid]; + dl_config_pdu->dci_dl_pdu.dci_dl_pdu_rel8.redundancy_version_1 = round & 3; if (cc[CC_id].tdd_Config != NULL) { //TDD dl_config_pdu->dci_dl_pdu. - dci_dl_pdu_rel8.downlink_assignment_index = - (UE_list->UE_template[CC_id][UE_id].DAI - - 1) & 3; + dci_dl_pdu_rel8.downlink_assignment_index = (UE_info->UE_template[CC_id][UE_id].DAI - 1) & 3; LOG_D(MAC, "[eNB %d] Retransmission CC_id %d : harq_pid %d, round %d, dai %d, mcs %d\n", module_idP, CC_id, harq_pid, round, - (UE_list->UE_template[CC_id][UE_id].DAI - - 1), - UE_list-> - UE_template[CC_id][UE_id].oldmcs1 - [harq_pid]); + UE_info->UE_template[CC_id][UE_id].DAI - 1, + UE_info-> UE_template[CC_id][UE_id].oldmcs1[harq_pid]); } else { LOG_D(MAC, "[eNB %d] Retransmission CC_id %d : harq_pid %d, round %d, mcs %d\n", module_idP, CC_id, harq_pid, round, - UE_list-> - UE_template[CC_id][UE_id].oldmcs1 - [harq_pid]); + UE_info->UE_template[CC_id][UE_id].oldmcs1[harq_pid]); } if (!CCE_allocation_infeasible @@ -1205,12 +1493,14 @@ schedule_ue_spec_fairRR(module_id_t module_idP, dl_req->tl.tag = NFAPI_DL_CONFIG_REQUEST_BODY_TAG; eNB->DL_req[CC_id].sfn_sf = frameP<<4 | subframeP; eNB->DL_req[CC_id].header.message_id = NFAPI_DL_CONFIG_REQUEST; - fill_nfapi_dlsch_config(eNB, dl_req, TBS, -1 + fill_nfapi_dlsch_config(&dl_req->dl_config_pdu_list[dl_req->number_pdu], + TBS, + -1 /* retransmission, no pdu_index */ , rnti, 0, // type 0 allocation from 7.1.6 in 36.213 0, // virtual_resource_block_assignment_flag, unused here 0, // resource_block_coding, to be filled in later - getQm(UE_list->UE_template[CC_id][UE_id].oldmcs1[harq_pid]), round & 3, // redundancy version + getQm(UE_info->UE_template[CC_id][UE_id].oldmcs1[harq_pid]), round & 3, // redundancy version 1, // transport blocks 0, // transport block to codeword swap flag cc[CC_id].p_eNB == 1 ? 0 : 1, // transmission_scheme @@ -1218,13 +1508,14 @@ schedule_ue_spec_fairRR(module_id_t module_idP, 1, // number of subbands // uint8_t codebook_index, 4, // UE category capacity - UE_list->UE_template[CC_id][UE_id].physicalConfigDedicated->pdsch_ConfigDedicated->p_a, 0, // delta_power_offset for TM5 + UE_info->UE_template[CC_id][UE_id].physicalConfigDedicated->pdsch_ConfigDedicated->p_a, 0, // delta_power_offset for TM5 0, // ngap 0, // nprb cc[CC_id].p_eNB == 1 ? 1 : 2, // transmission mode 0, //number of PRBs treated as one subband, not used here 0 // number of beamforming vectors, not used here ); + dl_req->number_pdu++; LOG_D(MAC, "Filled NFAPI configuration for DCI/DLSCH %d, retransmission round %d\n", eNB->pdu_index[CC_id], round); @@ -1248,16 +1539,11 @@ schedule_ue_spec_fairRR(module_id_t module_idP, S_DL_SCHEDULED, rnti); //eNB_UE_stats->dlsch_trials[round]++; - UE_list->eNB_UE_stats[CC_id][UE_id]. - num_retransmission += 1; - UE_list->eNB_UE_stats[CC_id][UE_id].rbs_used_retx = - nb_rb; - UE_list->eNB_UE_stats[CC_id][UE_id]. - total_rbs_used_retx += nb_rb; - UE_list->eNB_UE_stats[CC_id][UE_id].dlsch_mcs1 = - eNB_UE_stats->dlsch_mcs1; - UE_list->eNB_UE_stats[CC_id][UE_id].dlsch_mcs2 = - eNB_UE_stats->dlsch_mcs1; + UE_info->eNB_UE_stats[CC_id][UE_id].num_retransmission += 1; + UE_info->eNB_UE_stats[CC_id][UE_id].rbs_used_retx = nb_rb; + UE_info->eNB_UE_stats[CC_id][UE_id].total_rbs_used_retx += nb_rb; + UE_info->eNB_UE_stats[CC_id][UE_id].dlsch_mcs1 = eNB_UE_stats->dlsch_mcs1; + UE_info->eNB_UE_stats[CC_id][UE_id].dlsch_mcs2 = eNB_UE_stats->dlsch_mcs1; } else { LOG_D(MAC, "[eNB %d] Frame %d CC_id %d : don't schedule UE %d, its retransmission takes more resources than we have\n", @@ -1289,7 +1575,7 @@ schedule_ue_spec_fairRR(module_id_t module_idP, header_len_dcch = 2; // 2 bytes DCCH SDU subheader if (TBS - ta_len - header_len_dcch > 0) { - rlc_status = mac_rlc_status_ind(module_idP, rnti, module_idP, frameP, subframeP, ENB_FLAG_YES, MBMS_FLAG_NO, DCCH, (TBS - ta_len - header_len_dcch),0, 0); // transport block set size + rlc_status = mac_rlc_status_ind(module_idP, rnti, module_idP, frameP, subframeP, ENB_FLAG_YES, MBMS_FLAG_NO, DCCH, 0, 0); // transport block set size sdu_lengths[0] = 0; if (rlc_status.bytes_in_buffer > 0) { // There is DCCH to transmit @@ -1297,7 +1583,8 @@ schedule_ue_spec_fairRR(module_id_t module_idP, "[eNB %d] SFN/SF %d.%d, DL-DCCH->DLSCH CC_id %d, Requesting %d bytes from RLC (RRC message)\n", module_idP, frameP, subframeP, CC_id, TBS - header_len_dcch); - sdu_lengths[0] = mac_rlc_data_req(module_idP, rnti, module_idP, frameP, ENB_FLAG_YES, MBMS_FLAG_NO, DCCH, TBS, //not used + sdu_lengths[0] = mac_rlc_data_req(module_idP, rnti, module_idP, frameP, ENB_FLAG_YES, MBMS_FLAG_NO, DCCH, + TBS - ta_len - header_len_dcch, (char *) &dlsch_buffer[0],0, 0 ); @@ -1369,11 +1656,8 @@ schedule_ue_spec_fairRR(module_id_t module_idP, module_idP, CC_id, frameP, subframeP, UE_id, rnti, sdu_lengths[0],rlc_status.bytes_in_buffer,rrc_release_info.num_UEs); sdu_length_total = sdu_lengths[0]; sdu_lcids[0] = DCCH; - UE_list->eNB_UE_stats[CC_id][UE_id]. - num_pdu_tx[DCCH] += 1; - UE_list-> - eNB_UE_stats[CC_id][UE_id].num_bytes_tx[DCCH] - += sdu_lengths[0]; + UE_info->eNB_UE_stats[CC_id][UE_id].num_pdu_tx[DCCH] += 1; + UE_info->eNB_UE_stats[CC_id][UE_id].num_bytes_tx[DCCH] += sdu_lengths[0]; num_sdus = 1; #ifdef DEBUG_eNB_SCHEDULER LOG_T(MAC, @@ -1394,7 +1678,7 @@ schedule_ue_spec_fairRR(module_id_t module_idP, // check for DCCH1 and update header information (assume 2 byte sub-header) if (TBS - ta_len - header_len_dcch - sdu_length_total > 0) { - rlc_status = mac_rlc_status_ind(module_idP, rnti, module_idP, frameP, subframeP, ENB_FLAG_YES, MBMS_FLAG_NO, DCCH + 1, (TBS - ta_len - header_len_dcch - sdu_length_total),0, 0 + rlc_status = mac_rlc_status_ind(module_idP, rnti, module_idP, frameP, subframeP, ENB_FLAG_YES, MBMS_FLAG_NO, DCCH + 1, 0, 0 ); // transport block set size less allocations for timing advance and // DCCH SDU sdu_lengths[num_sdus] = 0; @@ -1404,7 +1688,8 @@ schedule_ue_spec_fairRR(module_id_t module_idP, "[eNB %d], Frame %d, DCCH1->DLSCH, CC_id %d, Requesting %d bytes from RLC (RRC message)\n", module_idP, frameP, CC_id, TBS - header_len_dcch - sdu_length_total); - sdu_lengths[num_sdus] += mac_rlc_data_req(module_idP, rnti, module_idP, frameP, ENB_FLAG_YES, MBMS_FLAG_NO, DCCH + 1, TBS, //not used + sdu_lengths[num_sdus] += mac_rlc_data_req(module_idP, rnti, module_idP, frameP, ENB_FLAG_YES, MBMS_FLAG_NO, DCCH + 1, + TBS - ta_len - header_len_dcch - sdu_length_total, (char *) &dlsch_buffer[sdu_length_total],0, 0 ); T(T_ENB_MAC_UE_DL_SDU, T_INT(module_idP), @@ -1414,11 +1699,8 @@ schedule_ue_spec_fairRR(module_id_t module_idP, sdu_lcids[num_sdus] = DCCH1; sdu_length_total += sdu_lengths[num_sdus]; header_len_dcch += 2; - UE_list->eNB_UE_stats[CC_id][UE_id]. - num_pdu_tx[DCCH1] += 1; - UE_list-> - eNB_UE_stats[CC_id][UE_id].num_bytes_tx[DCCH1] - += sdu_lengths[num_sdus]; + UE_info->eNB_UE_stats[CC_id][UE_id].num_pdu_tx[DCCH1] += 1; + UE_info->eNB_UE_stats[CC_id][UE_id].num_bytes_tx[DCCH1] += sdu_lengths[num_sdus]; num_sdus++; #ifdef DEBUG_eNB_SCHEDULER LOG_T(MAC, @@ -1460,7 +1742,7 @@ schedule_ue_spec_fairRR(module_id_t module_idP, ENB_FLAG_YES, MBMS_FLAG_NO, lcid, - TBS - ta_len - header_len_dcch - sdu_length_total - header_len_dtch, 0, 0 + 0, 0 ); if (rlc_status.bytes_in_buffer > 0) { @@ -1477,7 +1759,7 @@ schedule_ue_spec_fairRR(module_id_t module_idP, ENB_FLAG_YES, MBMS_FLAG_NO, lcid, - TBS, //not used + TBS - ta_len - header_len_dcch - sdu_length_total - header_len_dtch, (char *)&dlsch_buffer[sdu_length_total], 0, 0 ); T(T_ENB_MAC_UE_DL_SDU, @@ -1495,8 +1777,8 @@ schedule_ue_spec_fairRR(module_id_t module_idP, lcid); sdu_lcids[num_sdus] = lcid; sdu_length_total += sdu_lengths[num_sdus]; - UE_list->eNB_UE_stats[CC_id][UE_id].num_pdu_tx[lcid] += 1; - UE_list->eNB_UE_stats[CC_id][UE_id].num_bytes_tx[lcid] += sdu_lengths[num_sdus]; + UE_info->eNB_UE_stats[CC_id][UE_id].num_pdu_tx[lcid] += 1; + UE_info->eNB_UE_stats[CC_id][UE_id].num_bytes_tx[lcid] += sdu_lengths[num_sdus]; if (sdu_lengths[num_sdus] < 128) { header_len_dtch--; @@ -1504,7 +1786,7 @@ schedule_ue_spec_fairRR(module_id_t module_idP, } num_sdus++; - UE_list->UE_sched_ctrl[UE_id].uplane_inactivity_timer = 0; + UE_info->UE_sched_ctrl[UE_id].uplane_inactivity_timer = 0; } else { // no data for this LCID header_len_dtch -= 3; } @@ -1557,9 +1839,7 @@ schedule_ue_spec_fairRR(module_id_t module_idP, if (nb_rb == ue_sched_ctl->pre_nb_available_rbs[CC_id]) { for (j = 0; j < N_RBG[CC_id]; j++) { // for indicating the rballoc for each sub-band - UE_list->UE_template[CC_id][UE_id]. - rballoc_subband[harq_pid][j] = - ue_sched_ctl->rballoc_sub_UE[CC_id][j]; + UE_info->UE_template[CC_id][UE_id].rballoc_subband[harq_pid][j] = ue_sched_ctl->rballoc_sub_UE[CC_id][j]; } } else { nb_rb_temp = nb_rb; @@ -1568,10 +1848,7 @@ schedule_ue_spec_fairRR(module_id_t module_idP, while ((nb_rb_temp > 0) && (j < N_RBG[CC_id])) { if (ue_sched_ctl->rballoc_sub_UE[CC_id][j] == 1) { - UE_list-> - UE_template[CC_id] - [UE_id].rballoc_subband[harq_pid][j] = - ue_sched_ctl->rballoc_sub_UE[CC_id][j]; + UE_info->UE_template[CC_id][UE_id].rballoc_subband[harq_pid][j] = ue_sched_ctl->rballoc_sub_UE[CC_id][j]; if ((j == N_RBG[CC_id] - 1) && ((N_RB_DL[CC_id] == 25) || @@ -1650,7 +1927,7 @@ schedule_ue_spec_fairRR(module_id_t module_idP, } #endif - offset = generate_dlsch_header((unsigned char *) UE_list->DLSCH_pdu[CC_id][0][UE_id].payload[0], num_sdus, //num_sdus + offset = generate_dlsch_header((unsigned char *) UE_info->DLSCH_pdu[CC_id][0][UE_id].payload[0], num_sdus, //num_sdus sdu_lengths, // sdu_lcids, 255, // no drx ta_update, // timing advance @@ -1679,20 +1956,20 @@ schedule_ue_spec_fairRR(module_id_t module_idP, LOG_T(MAC, "\n"); #endif // cycle through SDUs and place in dlsch_buffer - memcpy(&UE_list->DLSCH_pdu[CC_id][0][UE_id].payload[0][offset],dlsch_buffer,sdu_length_total); + memcpy(&UE_info->DLSCH_pdu[CC_id][0][UE_id].payload[0][offset],dlsch_buffer,sdu_length_total); // memcpy(RC.mac[0].DLSCH_pdu[0][0].payload[0][offset],dcch_buffer,sdu_lengths[0]); // fill remainder of DLSCH with random data for (j=0; j<(TBS-sdu_length_total-offset); j++) { - UE_list->DLSCH_pdu[CC_id][0][UE_id].payload[0][offset+sdu_length_total+j] = (char)(taus()&0xff); + UE_info->DLSCH_pdu[CC_id][0][UE_id].payload[0][offset+sdu_length_total+j] = (char)(taus()&0xff); } - trace_pdu(DIRECTION_DOWNLINK, (uint8_t *)UE_list->DLSCH_pdu[CC_id][0][UE_id].payload[0], + trace_pdu(DIRECTION_DOWNLINK, (uint8_t *)UE_info->DLSCH_pdu[CC_id][0][UE_id].payload[0], TBS, module_idP, WS_RA_RNTI, UE_RNTI(module_idP, UE_id), eNB->frame, eNB->subframe,0,0); T(T_ENB_MAC_UE_DL_PDU_WITH_DATA, T_INT(module_idP), T_INT(CC_id), T_INT(rnti), T_INT(frameP), T_INT(subframeP), - T_INT(harq_pid), T_BUFFER(UE_list->DLSCH_pdu[CC_id][0][UE_id].payload[0], TBS)); - UE_list->UE_template[CC_id][UE_id].nb_rb[harq_pid] = nb_rb; + T_INT(harq_pid), T_BUFFER(UE_info->DLSCH_pdu[CC_id][0][UE_id].payload[0], TBS)); + UE_info->UE_template[CC_id][UE_id].nb_rb[harq_pid] = nb_rb; add_ue_dlsch_info(module_idP, CC_id, UE_id, @@ -1702,37 +1979,37 @@ schedule_ue_spec_fairRR(module_id_t module_idP, // store stats eNB->eNB_stats[CC_id].dlsch_bytes_tx+=sdu_length_total; eNB->eNB_stats[CC_id].dlsch_pdus_tx+=1; - UE_list->eNB_UE_stats[CC_id][UE_id].rbs_used = nb_rb; - UE_list->eNB_UE_stats[CC_id][UE_id].total_rbs_used += nb_rb; - UE_list->eNB_UE_stats[CC_id][UE_id].dlsch_mcs1=eNB_UE_stats->dlsch_mcs1; - UE_list->eNB_UE_stats[CC_id][UE_id].dlsch_mcs2=mcs; - UE_list->eNB_UE_stats[CC_id][UE_id].TBS = TBS; - UE_list->eNB_UE_stats[CC_id][UE_id].overhead_bytes= TBS- sdu_length_total; - UE_list->eNB_UE_stats[CC_id][UE_id].total_sdu_bytes+= sdu_length_total; - UE_list->eNB_UE_stats[CC_id][UE_id].total_pdu_bytes+= TBS; - UE_list->eNB_UE_stats[CC_id][UE_id].total_num_pdus+=1; + UE_info->eNB_UE_stats[CC_id][UE_id].rbs_used = nb_rb; + UE_info->eNB_UE_stats[CC_id][UE_id].total_rbs_used += nb_rb; + UE_info->eNB_UE_stats[CC_id][UE_id].dlsch_mcs1=eNB_UE_stats->dlsch_mcs1; + UE_info->eNB_UE_stats[CC_id][UE_id].dlsch_mcs2=mcs; + UE_info->eNB_UE_stats[CC_id][UE_id].TBS = TBS; + UE_info->eNB_UE_stats[CC_id][UE_id].overhead_bytes= TBS- sdu_length_total; + UE_info->eNB_UE_stats[CC_id][UE_id].total_sdu_bytes+= sdu_length_total; + UE_info->eNB_UE_stats[CC_id][UE_id].total_pdu_bytes+= TBS; + UE_info->eNB_UE_stats[CC_id][UE_id].total_num_pdus+=1; if (cc[CC_id].tdd_Config != NULL) { // TDD - UE_list->UE_template[CC_id][UE_id].DAI++; - update_ul_dci(module_idP,CC_id,rnti,UE_list->UE_template[CC_id][UE_id].DAI,subframeP); + UE_info->UE_template[CC_id][UE_id].DAI++; + update_ul_dci(module_idP,CC_id,rnti,UE_info->UE_template[CC_id][UE_id].DAI,subframeP); } // do PUCCH power control // this is the snr - eNB_UE_stats = &UE_list->eNB_UE_stats[CC_id][UE_id]; + eNB_UE_stats = &UE_info->eNB_UE_stats[CC_id][UE_id]; /* Unit is not dBm, it's special from nfapi */ snr = (5 * ue_sched_ctl->pucch1_snr[CC_id] - 640) / 10; target_snr = eNB->puCch10xSnr / 10; // this assumes accumulated tpc // make sure that we are only sending a tpc update once a frame, otherwise the control loop will freak out - int32_t framex10psubframe = UE_list->UE_template[CC_id][UE_id].pucch_tpc_tx_frame*10+UE_list->UE_template[CC_id][UE_id].pucch_tpc_tx_subframe; + int32_t framex10psubframe = UE_info->UE_template[CC_id][UE_id].pucch_tpc_tx_frame*10+UE_info->UE_template[CC_id][UE_id].pucch_tpc_tx_subframe; if (((framex10psubframe+10)<=(frameP*10+subframeP)) || //normal case ((framex10psubframe>(frameP*10+subframeP)) && (((10240-framex10psubframe+frameP*10+subframeP)>=10)))) //frame wrap-around if (ue_sched_ctl->pucch1_cqi_update[CC_id] == 1) { ue_sched_ctl->pucch1_cqi_update[CC_id] = 0; - UE_list->UE_template[CC_id][UE_id].pucch_tpc_tx_frame=frameP; - UE_list->UE_template[CC_id][UE_id].pucch_tpc_tx_subframe=subframeP; + UE_info->UE_template[CC_id][UE_id].pucch_tpc_tx_frame=frameP; + UE_info->UE_template[CC_id][UE_id].pucch_tpc_tx_subframe=subframeP; if (snr > target_snr + 4) { tpc = 0; //-1 @@ -1767,7 +2044,7 @@ schedule_ue_spec_fairRR(module_id_t module_idP, dl_config_pdu->dci_dl_pdu.dci_dl_pdu_rel8.transmission_power = 6000; // equal to RS power dl_config_pdu->dci_dl_pdu.dci_dl_pdu_rel8.harq_process = harq_pid; dl_config_pdu->dci_dl_pdu.dci_dl_pdu_rel8.tpc = tpc; // dont adjust power when retransmitting - dl_config_pdu->dci_dl_pdu.dci_dl_pdu_rel8.new_data_indicator_1 = 1-UE_list->UE_template[CC_id][UE_id].oldNDI[harq_pid]; + dl_config_pdu->dci_dl_pdu.dci_dl_pdu_rel8.new_data_indicator_1 = 1-UE_info->UE_template[CC_id][UE_id].oldNDI[harq_pid]; dl_config_pdu->dci_dl_pdu.dci_dl_pdu_rel8.mcs_1 = mcs; dl_config_pdu->dci_dl_pdu.dci_dl_pdu_rel8.redundancy_version_1 = 0; //deactivate second codeword @@ -1775,10 +2052,10 @@ schedule_ue_spec_fairRR(module_id_t module_idP, dl_config_pdu->dci_dl_pdu.dci_dl_pdu_rel8.redundancy_version_2 = 1; if (cc[CC_id].tdd_Config != NULL) { //TDD - dl_config_pdu->dci_dl_pdu.dci_dl_pdu_rel8.downlink_assignment_index = (UE_list->UE_template[CC_id][UE_id].DAI-1)&3; + dl_config_pdu->dci_dl_pdu.dci_dl_pdu_rel8.downlink_assignment_index = (UE_info->UE_template[CC_id][UE_id].DAI-1)&3; LOG_D(MAC,"[eNB %d] Initial transmission CC_id %d : harq_pid %d, dai %d, mcs %d\n", module_idP,CC_id,harq_pid, - (UE_list->UE_template[CC_id][UE_id].DAI-1), + (UE_info->UE_template[CC_id][UE_id].DAI-1), mcs); } else { LOG_D(MAC,"[eNB %d] Initial transmission CC_id %d : harq_pid %d, mcs %d\n", @@ -1797,13 +2074,13 @@ schedule_ue_spec_fairRR(module_id_t module_idP, // Toggle NDI for next time LOG_D(MAC,"CC_id %d Frame %d, subframeP %d: Toggling Format1 NDI for UE %d (rnti %x/%d) oldNDI %d\n", CC_id, frameP,subframeP,UE_id, - rnti,harq_pid,UE_list->UE_template[CC_id][UE_id].oldNDI[harq_pid]); - UE_list->UE_template[CC_id][UE_id].oldNDI[harq_pid]=1-UE_list->UE_template[CC_id][UE_id].oldNDI[harq_pid]; - UE_list->UE_template[CC_id][UE_id].oldmcs1[harq_pid] = mcs; - UE_list->UE_template[CC_id][UE_id].oldmcs2[harq_pid] = 0; - AssertFatal(UE_list->UE_template[CC_id][UE_id].physicalConfigDedicated!=NULL,"physicalConfigDedicated is NULL\n"); - AssertFatal(UE_list->UE_template[CC_id][UE_id].physicalConfigDedicated->pdsch_ConfigDedicated!=NULL,"physicalConfigDedicated->pdsch_ConfigDedicated is NULL\n"); - fill_nfapi_dlsch_config(eNB,dl_req, + rnti,harq_pid,UE_info->UE_template[CC_id][UE_id].oldNDI[harq_pid]); + UE_info->UE_template[CC_id][UE_id].oldNDI[harq_pid]=1-UE_info->UE_template[CC_id][UE_id].oldNDI[harq_pid]; + UE_info->UE_template[CC_id][UE_id].oldmcs1[harq_pid] = mcs; + UE_info->UE_template[CC_id][UE_id].oldmcs2[harq_pid] = 0; + AssertFatal(UE_info->UE_template[CC_id][UE_id].physicalConfigDedicated!=NULL,"physicalConfigDedicated is NULL\n"); + AssertFatal(UE_info->UE_template[CC_id][UE_id].physicalConfigDedicated->pdsch_ConfigDedicated!=NULL,"physicalConfigDedicated->pdsch_ConfigDedicated is NULL\n"); + fill_nfapi_dlsch_config(&dl_req->dl_config_pdu_list[dl_req->number_pdu], TBS, eNB->pdu_index[CC_id], rnti, @@ -1819,7 +2096,7 @@ schedule_ue_spec_fairRR(module_id_t module_idP, 1, // number of subbands // uint8_t codebook_index, 4, // UE category capacity - UE_list->UE_template[CC_id][UE_id].physicalConfigDedicated->pdsch_ConfigDedicated->p_a, + UE_info->UE_template[CC_id][UE_id].physicalConfigDedicated->pdsch_ConfigDedicated->p_a, 0, // delta_power_offset for TM5 0, // ngap 0, // nprb @@ -1827,11 +2104,12 @@ schedule_ue_spec_fairRR(module_id_t module_idP, 0, //number of PRBs treated as one subband, not used here 0 // number of beamforming vectors, not used here ); + dl_req->number_pdu++; eNB->TX_req[CC_id].sfn_sf = fill_nfapi_tx_req(&eNB->TX_req[CC_id].tx_request_body, (frameP*10)+subframeP, TBS, eNB->pdu_index[CC_id], - eNB->UE_list.DLSCH_pdu[CC_id][0][(unsigned char)UE_id].payload[0]); + eNB->UE_info.DLSCH_pdu[CC_id][0][(unsigned char)UE_id].payload[0]); LOG_D(MAC,"Filled NFAPI configuration for DCI/DLSCH/TXREQ %d, new SDU\n",eNB->pdu_index[CC_id]); eNB->pdu_index[CC_id]++; program_dlsch_acknak(module_idP,CC_id,UE_id,frameP,subframeP,dl_config_pdu->dci_dl_pdu.dci_dl_pdu_rel8.cce_idx); @@ -1876,7 +2154,7 @@ fill_DLSCH_dci_fairRR( int i; int CC_id; eNB_MAC_INST *eNB =RC.mac[module_idP]; - UE_list_t *UE_list = &eNB->UE_list; + UE_info_t *UE_info = &eNB->UE_info; int N_RBG; int N_RB_DL; COMMON_channels_t *cc; @@ -1912,11 +2190,11 @@ fill_DLSCH_dci_fairRR( eNB_dlsch_info[module_idP][CC_id][UE_id].status = S_DL_WAITING; rnti = UE_RNTI(module_idP,UE_id); harq_pid = frame_subframe2_dl_harq_pid(cc->tdd_Config,frameP,subframeP); - nb_rb = UE_list->UE_template[CC_id][UE_id].nb_rb[harq_pid]; + nb_rb = UE_info->UE_template[CC_id][UE_id].nb_rb[harq_pid]; /// Synchronizing rballoc with rballoc_sub for(i=0; i<N_RBG; i++) { - rballoc_sub[i] = UE_list->UE_template[CC_id][UE_id].rballoc_subband[harq_pid][i]; + rballoc_sub[i] = UE_info->UE_template[CC_id][UE_id].rballoc_subband[harq_pid][i]; } nfapi_dl_config_request_t *DL_req = &RC.mac[module_idP]->DL_req[0]; @@ -1970,7 +2248,7 @@ void ulsch_scheduler_pre_ue_select_fairRR( UE_sched_ctrl_t *UE_sched_ctl = NULL; uint8_t cc_id_flag[MAX_NUM_CCs]; uint8_t harq_pid = 0,round = 0; - UE_list_t *UE_list= &eNB->UE_list; + UE_info_t *UE_info= &eNB->UE_info; uint8_t aggregation; int format_flag; nfapi_hi_dci0_request_body_t *HI_DCI0_req; @@ -1989,7 +2267,7 @@ void ulsch_scheduler_pre_ue_select_fairRR( // UE round >0 for ( UE_id = 0; UE_id < NUMBER_OF_UE_MAX; UE_id++ ) { - if (UE_list->active[UE_id] == FALSE) + if (UE_info->active[UE_id] == FALSE) continue; rnti = UE_RNTI(module_idP,UE_id); @@ -1999,10 +2277,10 @@ void ulsch_scheduler_pre_ue_select_fairRR( CC_id = UE_PCCID(module_idP,UE_id); - if (UE_list->UE_template[CC_id][UE_id].configured == FALSE) + if (UE_info->UE_template[CC_id][UE_id].configured == FALSE) continue; - if (UE_list->UE_sched_ctrl[UE_id].ul_out_of_sync == 1) + if (UE_info->UE_sched_ctrl[UE_id].ul_out_of_sync == 1) continue; // UL DCI @@ -2026,12 +2304,12 @@ void ulsch_scheduler_pre_ue_select_fairRR( //harq_pid harq_pid = subframe2harqpid(cc,(frameP+(sched_subframeP<subframeP ? 1 : 0)),sched_subframeP); //round - round = UE_list->UE_sched_ctrl[UE_id].round_UL[CC_id][harq_pid]; + round = UE_info->UE_sched_ctrl[UE_id].round_UL[CC_id][harq_pid]; if ( round > 0 ) { hi_dci0_pdu = &HI_DCI0_req->hi_dci0_pdu_list[HI_DCI0_req->number_of_dci+HI_DCI0_req->number_of_hi]; format_flag = 2; - aggregation=get_aggregation(get_bw_index(module_idP,CC_id),UE_list->UE_sched_ctrl[UE_id].dl_cqi[CC_id],format0); + aggregation=get_aggregation(get_bw_index(module_idP,CC_id),UE_info->UE_sched_ctrl[UE_id].dl_cqi[CC_id],format0); if (CCE_allocation_infeasible(module_idP,CC_id,format_flag,subframeP,aggregation,rnti) == 1) { cc_id_flag[CC_id] = 1; @@ -2042,8 +2320,8 @@ void ulsch_scheduler_pre_ue_select_fairRR( hi_dci0_pdu->dci_pdu.dci_pdu_rel8.aggregation_level = aggregation; HI_DCI0_req->number_of_dci++; ulsch_ue_select[CC_id].list[ulsch_ue_select[CC_id].ue_num].ue_priority = SCH_UL_RETRANS; - ulsch_ue_select[CC_id].list[ulsch_ue_select[CC_id].ue_num].start_rb = eNB->UE_list.UE_template[CC_id][UE_id].first_rb_ul[harq_pid]; - ulsch_ue_select[CC_id].list[ulsch_ue_select[CC_id].ue_num].nb_rb = eNB->UE_list.UE_template[CC_id][UE_id].nb_rb_ul[harq_pid]; + ulsch_ue_select[CC_id].list[ulsch_ue_select[CC_id].ue_num].start_rb = eNB->UE_info.UE_template[CC_id][UE_id].first_rb_ul[harq_pid]; + ulsch_ue_select[CC_id].list[ulsch_ue_select[CC_id].ue_num].nb_rb = eNB->UE_info.UE_template[CC_id][UE_id].nb_rb_ul[harq_pid]; ulsch_ue_select[CC_id].list[ulsch_ue_select[CC_id].ue_num].UE_id = UE_id; ulsch_ue_select[CC_id].ue_num++; continue; @@ -2051,7 +2329,7 @@ void ulsch_scheduler_pre_ue_select_fairRR( } // - int bytes_to_schedule = UE_list->UE_template[CC_id][UE_id].estimated_ul_buffer - UE_list->UE_template[CC_id][UE_id].scheduled_ul_bytes; + int bytes_to_schedule = UE_info->UE_template[CC_id][UE_id].estimated_ul_buffer - UE_info->UE_template[CC_id][UE_id].scheduled_ul_bytes; if (bytes_to_schedule < 0) bytes_to_schedule = 0; @@ -2063,14 +2341,14 @@ void ulsch_scheduler_pre_ue_select_fairRR( continue; } - if ( UE_list->UE_template[CC_id][UE_id].ul_SR > 0 ) { + if ( UE_info->UE_template[CC_id][UE_id].ul_SR > 0 ) { first_ue_id[CC_id][ue_first_num[CC_id]]= UE_id; first_ue_total[CC_id] [ue_first_num[CC_id]] = 0; ue_first_num[CC_id]++; continue; } - UE_sched_ctl = &UE_list->UE_sched_ctrl[UE_id]; + UE_sched_ctl = &UE_info->UE_sched_ctrl[UE_id]; rrc_status = mac_eNB_get_rrc_status(module_idP, rnti); if ( ((UE_sched_ctl->ul_inactivity_timer>20)&&(UE_sched_ctl->ul_scheduled==0)) || @@ -2083,7 +2361,7 @@ void ulsch_scheduler_pre_ue_select_fairRR( } /*if ( (ulsch_ue_select[CC_id].ue_num+ul_inactivity_num[CC_id] ) < ulsch_ue_max_num[CC_id] ) { - UE_sched_ctl = &UE_list->UE_sched_ctrl[UE_id]; + UE_sched_ctl = &UE_info->UE_sched_ctrl[UE_id]; uint8_t ul_period = 0; if (cc->tdd_Config) { ul_period = 50; @@ -2113,7 +2391,7 @@ void ulsch_scheduler_pre_ue_select_fairRR( hi_dci0_pdu = &HI_DCI0_req->hi_dci0_pdu_list[HI_DCI0_req->number_of_dci+HI_DCI0_req->number_of_hi]; format_flag = 2; rnti = UE_RNTI(module_idP,first_ue_id[CC_id][temp]); - aggregation=get_aggregation(get_bw_index(module_idP,CC_id),UE_list->UE_sched_ctrl[first_ue_id[CC_id][temp]].dl_cqi[CC_id],format0); + aggregation=get_aggregation(get_bw_index(module_idP,CC_id),UE_info->UE_sched_ctrl[first_ue_id[CC_id][temp]].dl_cqi[CC_id],format0); if (CCE_allocation_infeasible(module_idP,CC_id,format_flag,subframeP,aggregation,rnti) == 1) { cc_id_flag[CC_id] = 1; @@ -2132,7 +2410,7 @@ void ulsch_scheduler_pre_ue_select_fairRR( } for ( UE_id = 0; UE_id < NUMBER_OF_UE_MAX; UE_id++ ) { - if (UE_list->active[UE_id] == FALSE) + if (UE_info->active[UE_id] == FALSE) continue; rnti = UE_RNTI(module_idP,UE_id); @@ -2145,10 +2423,10 @@ void ulsch_scheduler_pre_ue_select_fairRR( if (UE_id > last_ulsch_ue_id[CC_id]) continue; - if (UE_list->UE_template[CC_id][UE_id].configured == FALSE) + if (UE_info->UE_template[CC_id][UE_id].configured == FALSE) continue; - if (UE_list->UE_sched_ctrl[UE_id].ul_out_of_sync == 1) + if (UE_info->UE_sched_ctrl[UE_id].ul_out_of_sync == 1) continue; if ( (ulsch_ue_select[CC_id].ue_num >= ulsch_ue_max_num[CC_id]) || (cc_id_flag[CC_id] == 1) ) { @@ -2176,19 +2454,19 @@ void ulsch_scheduler_pre_ue_select_fairRR( HI_DCI0_req = &eNB->HI_DCI0_req[CC_id][subframeP].hi_dci0_request_body; //SR BSR - UE_sched_ctl = &UE_list->UE_sched_ctrl[UE_id]; - int bytes_to_schedule = UE_list->UE_template[CC_id][UE_id].estimated_ul_buffer - UE_list->UE_template[CC_id][UE_id].scheduled_ul_bytes; + UE_sched_ctl = &UE_info->UE_sched_ctrl[UE_id]; + int bytes_to_schedule = UE_info->UE_template[CC_id][UE_id].estimated_ul_buffer - UE_info->UE_template[CC_id][UE_id].scheduled_ul_bytes; if (bytes_to_schedule < 0) bytes_to_schedule = 0; rrc_status = mac_eNB_get_rrc_status(module_idP, rnti); - if ( (bytes_to_schedule > 0) || (UE_list->UE_template[CC_id][UE_id].ul_SR > 0) || + if ( (bytes_to_schedule > 0) || (UE_info->UE_template[CC_id][UE_id].ul_SR > 0) || ((UE_sched_ctl->ul_inactivity_timer>20)&&(UE_sched_ctl->ul_scheduled==0)) || ((UE_sched_ctl->ul_inactivity_timer>10)&&(UE_sched_ctl->ul_scheduled==0)&&(rrc_status < RRC_CONNECTED)) || ((UE_sched_ctl->cqi_req_timer>300)&&((rrc_status >= RRC_CONNECTED))) ) { hi_dci0_pdu = &HI_DCI0_req->hi_dci0_pdu_list[HI_DCI0_req->number_of_dci+HI_DCI0_req->number_of_hi]; format_flag = 2; - aggregation=get_aggregation(get_bw_index(module_idP,CC_id),UE_list->UE_sched_ctrl[UE_id].dl_cqi[CC_id],format0); + aggregation=get_aggregation(get_bw_index(module_idP,CC_id),UE_info->UE_sched_ctrl[UE_id].dl_cqi[CC_id],format0); if (CCE_allocation_infeasible(module_idP,CC_id,format_flag,subframeP,aggregation,rnti) == 1) { cc_id_flag[CC_id] = 1; @@ -2202,7 +2480,7 @@ void ulsch_scheduler_pre_ue_select_fairRR( if(bytes_to_schedule > 0) ulsch_ue_select[CC_id].list[ulsch_ue_select[CC_id].ue_num].ul_total_buffer = bytes_to_schedule; - else if(UE_list->UE_template[CC_id][UE_id].ul_SR > 0) + else if(UE_info->UE_template[CC_id][UE_id].ul_SR > 0) ulsch_ue_select[CC_id].list[ulsch_ue_select[CC_id].ue_num].ul_total_buffer = 0; ulsch_ue_select[CC_id].list[ulsch_ue_select[CC_id].ue_num].UE_id = UE_id; @@ -2213,7 +2491,7 @@ void ulsch_scheduler_pre_ue_select_fairRR( //inactivity UE /* if ( (ulsch_ue_select[CC_id].ue_num+ul_inactivity_num[CC_id]) < ulsch_ue_max_num[CC_id] ) { - UE_sched_ctl = &UE_list->UE_sched_ctrl[UE_id]; + UE_sched_ctl = &UE_info->UE_sched_ctrl[UE_id]; uint8_t ul_period = 0; if (cc->tdd_Config) { ul_period = 50; @@ -2242,7 +2520,7 @@ void ulsch_scheduler_pre_ue_select_fairRR( hi_dci0_pdu = &HI_DCI0_req->hi_dci0_pdu_list[HI_DCI0_req->number_of_dci+HI_DCI0_req->number_of_hi]; format_flag = 2; rnti = UE_RNTI(module_idP,ul_inactivity_id[CC_id][temp]); - aggregation=get_aggregation(get_bw_index(module_idP,CC_id),UE_list->UE_sched_ctrl[ul_inactivity_id[CC_id][temp]].dl_cqi[CC_id],format0); + aggregation=get_aggregation(get_bw_index(module_idP,CC_id),UE_info->UE_sched_ctrl[ul_inactivity_id[CC_id][temp]].dl_cqi[CC_id],format0); if (CCE_allocation_infeasible(module_idP,CC_id,format_flag,subframeP,aggregation,rnti) == 1) { cc_id_flag[CC_id] = 1; @@ -2284,7 +2562,7 @@ void ulsch_scheduler_pre_processor_fairRR(module_id_t module_idP, ULSCH_UE_SELECT ulsch_ue_select[MAX_NUM_CCs]) { int CC_id,ulsch_ue_num; eNB_MAC_INST *eNB = RC.mac[module_idP]; - UE_list_t *UE_list= &eNB->UE_list; + UE_info_t *UE_info= &eNB->UE_info; UE_TEMPLATE *UE_template = NULL; LTE_DL_FRAME_PARMS *frame_parms = NULL; uint8_t ue_num_temp; @@ -2383,9 +2661,9 @@ void ulsch_scheduler_pre_processor_fairRR(module_id_t module_idP, } } } else { - UE_template = &UE_list->UE_template[CC_id][UE_id]; + UE_template = &UE_info->UE_template[CC_id][UE_id]; - if ( UE_list->UE_sched_ctrl[UE_id].phr_received == 1 ) { + if ( UE_info->UE_sched_ctrl[UE_id].phr_received == 1 ) { mcs = 20; } else { mcs = 10; @@ -2421,9 +2699,9 @@ void ulsch_scheduler_pre_processor_fairRR(module_id_t module_idP, if ( rb_table[rb_table_index] <= average_rbs ) { // assigne RBS( nb_rb) first_rb[CC_id] = first_rb[CC_id] + rb_table[rb_table_index]; - UE_list->UE_template[CC_id][UE_id].pre_allocated_nb_rb_ul[0] = rb_table[rb_table_index]; - UE_list->UE_template[CC_id][UE_id].pre_allocated_rb_table_index_ul = rb_table_index; - UE_list->UE_template[CC_id][UE_id].pre_assigned_mcs_ul = mcs; + UE_info->UE_template[CC_id][UE_id].pre_allocated_nb_rb_ul = rb_table[rb_table_index]; + UE_info->UE_template[CC_id][UE_id].pre_allocated_rb_table_index_ul = rb_table_index; + UE_info->UE_template[CC_id][UE_id].pre_assigned_mcs_ul = mcs; } if ( rb_table[rb_table_index] > average_rbs ) { @@ -2437,31 +2715,31 @@ void ulsch_scheduler_pre_processor_fairRR(module_id_t module_idP, } first_rb[CC_id] = first_rb[CC_id] + rb_table[rb_table_index]; - UE_list->UE_template[CC_id][UE_id].pre_allocated_nb_rb_ul[0] = rb_table[rb_table_index]; - UE_list->UE_template[CC_id][UE_id].pre_allocated_rb_table_index_ul = rb_table_index; - UE_list->UE_template[CC_id][UE_id].pre_assigned_mcs_ul = mcs; + UE_info->UE_template[CC_id][UE_id].pre_allocated_nb_rb_ul = rb_table[rb_table_index]; + UE_info->UE_template[CC_id][UE_id].pre_allocated_rb_table_index_ul = rb_table_index; + UE_info->UE_template[CC_id][UE_id].pre_assigned_mcs_ul = mcs; } } else { if (mac_eNB_get_rrc_status(module_idP,UE_RNTI(module_idP, UE_id)) < RRC_CONNECTED) { // assigne RBS( 6 RBs) first_rb[CC_id] = first_rb[CC_id] + 6; - UE_list->UE_template[CC_id][UE_id].pre_allocated_nb_rb_ul[0] = 6; - UE_list->UE_template[CC_id][UE_id].pre_allocated_rb_table_index_ul = 5; - UE_list->UE_template[CC_id][UE_id].pre_assigned_mcs_ul = 10; + UE_info->UE_template[CC_id][UE_id].pre_allocated_nb_rb_ul = 6; + UE_info->UE_template[CC_id][UE_id].pre_allocated_rb_table_index_ul = 5; + UE_info->UE_template[CC_id][UE_id].pre_assigned_mcs_ul = 10; } else { // assigne RBS( 3 RBs) first_rb[CC_id] = first_rb[CC_id] + 3; - UE_list->UE_template[CC_id][UE_id].pre_allocated_nb_rb_ul[0] = 3; - UE_list->UE_template[CC_id][UE_id].pre_allocated_rb_table_index_ul = 2; - UE_list->UE_template[CC_id][UE_id].pre_assigned_mcs_ul = 10; + UE_info->UE_template[CC_id][UE_id].pre_allocated_nb_rb_ul = 3; + UE_info->UE_template[CC_id][UE_id].pre_allocated_rb_table_index_ul = 2; + UE_info->UE_template[CC_id][UE_id].pre_assigned_mcs_ul = 10; } } } else if ( ulsch_ue_select[CC_id].list[ulsch_ue_num].ue_priority == SCH_UL_INACTIVE ) { // assigne RBS( 3 RBs) first_rb[CC_id] = first_rb[CC_id] + 3; - UE_list->UE_template[CC_id][UE_id].pre_allocated_nb_rb_ul[0] = 3; - UE_list->UE_template[CC_id][UE_id].pre_allocated_rb_table_index_ul = 2; - UE_list->UE_template[CC_id][UE_id].pre_assigned_mcs_ul = 10; + UE_info->UE_template[CC_id][UE_id].pre_allocated_nb_rb_ul = 3; + UE_info->UE_template[CC_id][UE_id].pre_allocated_rb_table_index_ul = 2; + UE_info->UE_template[CC_id][UE_id].pre_assigned_mcs_ul = 10; } } @@ -2641,7 +2919,7 @@ void schedule_ulsch_rnti_fairRR(module_id_t module_idP, int N_RB_UL; eNB_MAC_INST *eNB = RC.mac[module_idP]; COMMON_channels_t *cc; - UE_list_t *UE_list=&eNB->UE_list; + UE_info_t *UE_info=&eNB->UE_info; UE_TEMPLATE *UE_template; UE_sched_ctrl_t *UE_sched_ctrl; int sched_frame=frameP; @@ -2750,8 +3028,8 @@ void schedule_ulsch_rnti_fairRR(module_id_t module_idP, continue; } - UE_template = &UE_list->UE_template[CC_id][UE_id]; - UE_sched_ctrl = &UE_list->UE_sched_ctrl[UE_id]; + UE_template = &UE_info->UE_template[CC_id][UE_id]; + UE_sched_ctrl = &UE_info->UE_sched_ctrl[UE_id]; harq_pid = subframe2harqpid(cc,sched_frame,sched_subframeP); rnti = UE_RNTI(CC_id,UE_id); aggregation=get_aggregation(get_bw_index(module_idP,CC_id),UE_sched_ctrl[UE_id].dl_cqi[CC_id],format0); @@ -2844,9 +3122,9 @@ void schedule_ulsch_rnti_fairRR(module_id_t module_idP, UE_sched_ctrl->cqi_req_timer); ndi = 1-UE_template->oldNDI_UL[harq_pid]; UE_template->oldNDI_UL[harq_pid]=ndi; - UE_list->eNB_UE_stats[CC_id][UE_id].snr = snr; - UE_list->eNB_UE_stats[CC_id][UE_id].target_snr = target_snr; - UE_list->eNB_UE_stats[CC_id][UE_id].ulsch_mcs1=UE_template->pre_assigned_mcs_ul; + UE_info->eNB_UE_stats[CC_id][UE_id].snr = snr; + UE_info->eNB_UE_stats[CC_id][UE_id].target_snr = target_snr; + UE_info->eNB_UE_stats[CC_id][UE_id].ulsch_mcs1=UE_template->pre_assigned_mcs_ul; UE_template->mcs_UL[harq_pid] = UE_template->pre_assigned_mcs_ul;//cmin (UE_template->pre_assigned_mcs_ul, openair_daq_vars.target_ue_ul_mcs); // adjust, based on user-defined MCS if (UE_template->pre_allocated_rb_table_index_ul >=0) { @@ -2856,10 +3134,10 @@ void schedule_ulsch_rnti_fairRR(module_id_t module_idP, rb_table_index=5; // for PHR } - UE_list->eNB_UE_stats[CC_id][UE_id].ulsch_mcs2=UE_template->mcs_UL[harq_pid]; + UE_info->eNB_UE_stats[CC_id][UE_id].ulsch_mcs2=UE_template->mcs_UL[harq_pid]; UE_template->TBS_UL[harq_pid] = get_TBS_UL(UE_template->mcs_UL[harq_pid],rb_table[rb_table_index]); - UE_list->eNB_UE_stats[CC_id][UE_id].total_rbs_used_rx+=rb_table[rb_table_index]; - UE_list->eNB_UE_stats[CC_id][UE_id].ulsch_TBS=UE_template->TBS_UL[harq_pid]; + UE_info->eNB_UE_stats[CC_id][UE_id].total_rbs_used_rx+=rb_table[rb_table_index]; + UE_info->eNB_UE_stats[CC_id][UE_id].ulsch_TBS=UE_template->TBS_UL[harq_pid]; T(T_ENB_MAC_UE_UL_SCHEDULE, T_INT(module_idP), T_INT(CC_id), T_INT(rnti), T_INT(frameP), T_INT(subframeP), T_INT(harq_pid), T_INT(UE_template->mcs_UL[harq_pid]), T_INT(first_rb[CC_id]), T_INT(rb_table[rb_table_index]), T_INT(UE_template->TBS_UL[harq_pid]), T_INT(ndi)); @@ -2877,7 +3155,7 @@ void schedule_ulsch_rnti_fairRR(module_id_t module_idP, UE_template->cqi_req[harq_pid] = cqi_req; UE_sched_ctrl->ul_scheduled |= (1<<harq_pid); - if (UE_id == UE_list->head) + if (UE_id == UE_info->list.head) VCD_SIGNAL_DUMPER_DUMP_VARIABLE_BY_NAME(VCD_SIGNAL_DUMPER_VARIABLES_UE0_SCHEDULED,UE_sched_ctrl->ul_scheduled); // adjust total UL buffer status by TBS, wait for UL sdus to do final update @@ -3019,8 +3297,8 @@ void schedule_ulsch_rnti_fairRR(module_id_t module_idP, T(T_ENB_MAC_UE_UL_SCHEDULE_RETRANSMISSION, T_INT(module_idP), T_INT(CC_id), T_INT(rnti), T_INT(frameP), T_INT(subframeP), T_INT(harq_pid), T_INT(UE_template->mcs_UL[harq_pid]), T_INT(ulsch_ue_select[CC_id].list[ulsch_ue_num].start_rb), T_INT(ulsch_ue_select[CC_id].list[ulsch_ue_num].nb_rb), T_INT(round)); - UE_list->eNB_UE_stats[CC_id][UE_id].snr = snr; - UE_list->eNB_UE_stats[CC_id][UE_id].target_snr = target_snr; + UE_info->eNB_UE_stats[CC_id][UE_id].snr = snr; + UE_info->eNB_UE_stats[CC_id][UE_id].target_snr = target_snr; uint8_t mcs_rv = 0; if(rvidx_tab[round&3]==1) { @@ -3032,7 +3310,7 @@ void schedule_ulsch_rnti_fairRR(module_id_t module_idP, } UE_template->TBS_UL[harq_pid] = get_TBS_UL(UE_template->mcs_UL[harq_pid],ulsch_ue_select[CC_id].list[ulsch_ue_num].nb_rb); - UE_list->eNB_UE_stats[CC_id][UE_id].ulsch_TBS=UE_template->TBS_UL[harq_pid]; + UE_info->eNB_UE_stats[CC_id][UE_id].ulsch_TBS=UE_template->TBS_UL[harq_pid]; if (mac_eNB_get_rrc_status(module_idP,rnti) < RRC_CONNECTED) LOG_D(MAC,"[eNB %d][PUSCH %d/%x] CC_id %d Frame %d subframeP %d Scheduled UE %d (mcs %d, first rb %d, nb_rb %d, TBS %d, harq_pid %d)\n", diff --git a/openair2/LAYER2/MAC/eNB_scheduler_fairRR.h b/openair2/LAYER2/MAC/eNB_scheduler_fairRR.h index 5355a614a6c8c14b8dc7e2e3a1cd95ff270957c3..880e60ec199d747fea8bf0203105efd31eaab63e 100644 --- a/openair2/LAYER2/MAC/eNB_scheduler_fairRR.h +++ b/openair2/LAYER2/MAC/eNB_scheduler_fairRR.h @@ -85,6 +85,30 @@ void dlsch_scheduler_pre_ue_select_fairRR( uint16_t nb_rbs_required[MAX_NUM_CCs][MAX_MOBILES_PER_ENB], DLSCH_UE_SELECT dlsch_ue_select[MAX_NUM_CCs]); +void dlsch_scheduler_pre_processor_reset_fairRR( + module_id_t module_idP, + frame_t frameP, + sub_frame_t subframeP, + int min_rb_unit[NFAPI_CC_MAX], + uint16_t nb_rbs_required[NFAPI_CC_MAX][MAX_MOBILES_PER_ENB], + uint8_t rballoc_sub[NFAPI_CC_MAX][N_RBG_MAX], + uint8_t MIMO_mode_indicator[NFAPI_CC_MAX][N_RBG_MAX]); + +void assign_rbs_required_fairRR( + module_id_t Mod_id, + frame_t frameP, + sub_frame_t subframe, + uint16_t nb_rbs_required[NFAPI_CC_MAX][MAX_MOBILES_PER_ENB]); + +void dlsch_scheduler_pre_processor_allocate_fairRR( + module_id_t Mod_id, + int UE_id, + uint8_t CC_id, + int N_RBG, + uint16_t nb_rbs_required[NFAPI_CC_MAX][MAX_MOBILES_PER_ENB], + uint16_t nb_rbs_remaining[NFAPI_CC_MAX][MAX_MOBILES_PER_ENB], + uint8_t rballoc_sub[NFAPI_CC_MAX][N_RBG_MAX]); + void dlsch_scheduler_pre_processor_fairRR (module_id_t Mod_id, frame_t frameP, sub_frame_t subframeP, diff --git a/openair2/LAYER2/MAC/eNB_scheduler_mch.c b/openair2/LAYER2/MAC/eNB_scheduler_mch.c index 2953c8e70b4065b9af032b4efebe6e10909eef1a..12cdb29f4cec48b9d374ef406c46215db1225901 100644 --- a/openair2/LAYER2/MAC/eNB_scheduler_mch.c +++ b/openair2/LAYER2/MAC/eNB_scheduler_mch.c @@ -718,9 +718,7 @@ schedule_MBMS_NFAPI(module_id_t module_idP, uint8_t CC_id, frame_t frameP, module_idP, ENB_FLAG_YES, MBMS_FLAG_YES, cc->mbms_SessionList[0]->list.array[0]->logicalChannelIdentity_r9, //MTCH, - TBS - header_len_mcch - header_len_msi - - sdu_length_total - header_len_mtch - ,0, 0 + 0, 0 ); bytes_in_buffer = rlc_status.bytes_in_buffer; @@ -773,7 +771,8 @@ schedule_MBMS_NFAPI(module_id_t module_idP, uint8_t CC_id, frame_t frameP, TBS - header_len_mcch - header_len_msi - sdu_length_total - header_len_mtch, header_len_mtch, rlc_status.bytes_in_buffer); - sdu_lengths[num_sdus] = mac_rlc_data_req(module_idP, 0/*0xfffd*/, module_idP, frameP, ENB_FLAG_YES, MBMS_FLAG_YES,cc->mbms_SessionList[0]->list.array[0]->logicalChannelIdentity_r9, 0, //not used + sdu_lengths[num_sdus] = mac_rlc_data_req(module_idP, 0, module_idP, frameP, ENB_FLAG_YES, MBMS_FLAG_YES,cc->mbms_SessionList[0]->list.array[0]->logicalChannelIdentity_r9, + TBS - header_len_mcch - header_len_msi - sdu_length_total - header_len_mtch, (char *) &mch_buffer[sdu_length_total] ,0, @@ -1558,9 +1557,7 @@ schedule_MBMS(module_id_t module_idP, uint8_t CC_id, frame_t frameP, module_idP, ENB_FLAG_YES, MBMS_FLAG_YES, cc->mbms_SessionList[0]->list.array[0]->logicalChannelIdentity_r9, //MTCH, - TBS - header_len_mcch - header_len_msi - - sdu_length_total - header_len_mtch - ,0, 0 + 0, 0 ); bytes_in_buffer = rlc_status.bytes_in_buffer; @@ -1579,7 +1576,8 @@ schedule_MBMS(module_id_t module_idP, uint8_t CC_id, frame_t frameP, TBS - header_len_mcch - header_len_msi - sdu_length_total - header_len_mtch, header_len_mtch, rlc_status.bytes_in_buffer); - sdu_lengths[num_sdus] = mac_rlc_data_req(module_idP, 0/*0xfffd*/, module_idP, frameP, ENB_FLAG_YES, MBMS_FLAG_YES,cc->mbms_SessionList[0]->list.array[0]->logicalChannelIdentity_r9, 0, //not used + sdu_lengths[num_sdus] = mac_rlc_data_req(module_idP, 0, module_idP, frameP, ENB_FLAG_YES, MBMS_FLAG_YES,cc->mbms_SessionList[0]->list.array[0]->logicalChannelIdentity_r9, + TBS - header_len_mcch - header_len_msi - sdu_length_total - header_len_mtch, (char *) &mch_buffer[sdu_length_total] ,0, diff --git a/openair2/LAYER2/MAC/eNB_scheduler_phytest.c b/openair2/LAYER2/MAC/eNB_scheduler_phytest.c index 647db3f6249ea7a2c74f0e6ebe7857eb0daff226..689db8e208da38a3c6e10cbae74e4a2c49240f32 100644 --- a/openair2/LAYER2/MAC/eNB_scheduler_phytest.c +++ b/openair2/LAYER2/MAC/eNB_scheduler_phytest.c @@ -133,16 +133,15 @@ schedule_ue_spec_phy_test( /* LOG_D(MAC,"CC_id %d Frame %d, subframeP %d: Toggling Format1 NDI for UE %d (rnti %x/%d) oldNDI %d\n", CC_id, frameP,subframeP,UE_id, - rnti,harq_pid,UE_list->UE_template[CC_id][UE_id].oldNDI[harq_pid]); + rnti,harq_pid,UE_info->UE_template[CC_id][UE_id].oldNDI[harq_pid]); - UE_list->UE_template[CC_id][UE_id].oldNDI[harq_pid]=1-UE_list->UE_template[CC_id][UE_id].oldNDI[harq_pid]; - UE_list->UE_template[CC_id][UE_id].oldmcs1[harq_pid] = mcs; - UE_list->UE_template[CC_id][UE_id].oldmcs2[harq_pid] = 0; - AssertFatal(UE_list->UE_template[CC_id][UE_id].physicalConfigDedicated!=NULL,"physicalConfigDedicated is NULL\n"); - AssertFatal(UE_list->UE_template[CC_id][UE_id].physicalConfigDedicated->pdsch_ConfigDedicated!=NULL,"physicalConfigDedicated->pdsch_ConfigDedicated is NULL\n"); + UE_info->UE_template[CC_id][UE_id].oldNDI[harq_pid]=1-UE_info->UE_template[CC_id][UE_id].oldNDI[harq_pid]; + UE_info->UE_template[CC_id][UE_id].oldmcs1[harq_pid] = mcs; + UE_info->UE_template[CC_id][UE_id].oldmcs2[harq_pid] = 0; + AssertFatal(UE_info->UE_template[CC_id][UE_id].physicalConfigDedicated!=NULL,"physicalConfigDedicated is NULL\n"); + AssertFatal(UE_info->UE_template[CC_id][UE_id].physicalConfigDedicated->pdsch_ConfigDedicated!=NULL,"physicalConfigDedicated->pdsch_ConfigDedicated is NULL\n"); */ - fill_nfapi_dlsch_config(eNB, - dl_req, + fill_nfapi_dlsch_config(&dl_req->dl_config_pdu_list[dl_req->number_pdu], TBS, eNB->pdu_index[CC_id], rnti, @@ -166,11 +165,12 @@ schedule_ue_spec_phy_test( 0, //number of PRBs treated as one subband, not used here 0 // number of beamforming vectors, not used here ); + dl_req->number_pdu++; eNB->TX_req[CC_id].sfn_sf = fill_nfapi_tx_req(&eNB->TX_req[CC_id].tx_request_body, (frameP*10)+subframeP, TBS, eNB->pdu_index[CC_id], - eNB->UE_list.DLSCH_pdu[CC_id][0][(unsigned char)UE_id].payload[0]); + eNB->UE_info.DLSCH_pdu[CC_id][0][(unsigned char)UE_id].payload[0]); } else { LOG_W(MAC,"[eNB_scheduler_phytest] DCI allocation infeasible!\n"); } @@ -192,7 +192,7 @@ void schedule_ulsch_phy_test(module_id_t module_idP,frame_t frameP,sub_frame_t s int N_RB_UL; eNB_MAC_INST *mac = RC.mac[module_idP]; COMMON_channels_t *cc = &mac->common_channels[0]; - UE_list_t *UE_list=&mac->UE_list; + UE_info_t *UE_info=&mac->UE_info; UE_TEMPLATE *UE_template; UE_sched_ctrl_t *UE_sched_ctrl; int sched_frame=frameP; @@ -231,8 +231,8 @@ void schedule_ulsch_phy_test(module_id_t module_idP,frame_t frameP,sub_frame_t s first_rb[CC_id] = 1; // loop over all active UEs // if (eNB_UE_stats->mode == PUSCH) { // ue has a ulsch channel - UE_template = &UE_list->UE_template[CC_id][UE_id]; - UE_sched_ctrl = &UE_list->UE_sched_ctrl[UE_id]; + UE_template = &UE_info->UE_template[CC_id][UE_id]; + UE_sched_ctrl = &UE_info->UE_sched_ctrl[UE_id]; harq_pid = subframe2harqpid(&cc[CC_id],sched_frame,sched_subframe); RC.eNB[module_idP][CC_id]->pusch_stats_BO[UE_id][(frameP*10)+subframeP] = UE_template->TBS_UL[harq_pid]; //power control @@ -242,15 +242,15 @@ void schedule_ulsch_phy_test(module_id_t module_idP,frame_t frameP,sub_frame_t s // new transmission ndi = 1-UE_template->oldNDI_UL[harq_pid]; UE_template->oldNDI_UL[harq_pid]=ndi; - UE_list->eNB_UE_stats[CC_id][UE_id].snr = snr; - UE_list->eNB_UE_stats[CC_id][UE_id].target_snr = target_snr; - UE_list->eNB_UE_stats[CC_id][UE_id].ulsch_mcs1 = mcs; + UE_info->eNB_UE_stats[CC_id][UE_id].snr = snr; + UE_info->eNB_UE_stats[CC_id][UE_id].target_snr = target_snr; + UE_info->eNB_UE_stats[CC_id][UE_id].ulsch_mcs1 = mcs; UE_template->mcs_UL[harq_pid] = mcs;//cmin (UE_template->pre_assigned_mcs_ul, openair_daq_vars.target_ue_ul_mcs); // adjust, based on user-defined MCS - UE_list->eNB_UE_stats[CC_id][UE_id].ulsch_mcs2 = mcs; + UE_info->eNB_UE_stats[CC_id][UE_id].ulsch_mcs2 = mcs; // buffer_occupancy = UE_template->ul_total_buffer; UE_template->TBS_UL[harq_pid] = get_TBS_UL(mcs,nb_rb); - UE_list->eNB_UE_stats[CC_id][UE_id].total_rbs_used_rx += nb_rb; - UE_list->eNB_UE_stats[CC_id][UE_id].ulsch_TBS = get_TBS_UL(mcs,nb_rb); + UE_info->eNB_UE_stats[CC_id][UE_id].total_rbs_used_rx += nb_rb; + UE_info->eNB_UE_stats[CC_id][UE_id].ulsch_TBS = get_TBS_UL(mcs,nb_rb); // buffer_occupancy -= TBS; // bad indices : 20 (40 PRB), 21 (45 PRB), 22 (48 PRB) //store for possible retransmission diff --git a/openair2/LAYER2/MAC/eNB_scheduler_primitives.c b/openair2/LAYER2/MAC/eNB_scheduler_primitives.c index e76e6b24ba70a96d5f0140797a86c3b59ccbb2a9..78d6f6a3d76574d1b8ab70d96184b5e5297095c0 100644 --- a/openair2/LAYER2/MAC/eNB_scheduler_primitives.c +++ b/openair2/LAYER2/MAC/eNB_scheduler_primitives.c @@ -1169,14 +1169,14 @@ program_dlsch_acknak(module_id_t module_idP, { eNB_MAC_INST *eNB = RC.mac[module_idP]; COMMON_channels_t *cc = eNB->common_channels; - UE_list_t *UE_list = &eNB->UE_list; + UE_info_t *UE_info = &eNB->UE_info; rnti_t rnti = UE_RNTI(module_idP, UE_idP); nfapi_ul_config_request_body_t *ul_req; nfapi_ul_config_request_pdu_t *ul_config_pdu; int use_simultaneous_pucch_pusch = 0; nfapi_ul_config_ulsch_harq_information *ulsch_harq_information = NULL; nfapi_ul_config_harq_information *harq_information = NULL; - struct LTE_PhysicalConfigDedicated__ext2 *ext2 = UE_list->UE_template[CC_idP][UE_idP].physicalConfigDedicated->ext2; + struct LTE_PhysicalConfigDedicated__ext2 *ext2 = UE_info->UE_template[CC_idP][UE_idP].physicalConfigDedicated->ext2; if (ext2 && ext2->pucch_ConfigDedicated_v1020 && @@ -1363,12 +1363,12 @@ fill_nfapi_ulsch_harq_information(module_id_t module_ { eNB_MAC_INST *eNB = RC.mac[module_idP]; COMMON_channels_t *cc = &eNB->common_channels[CC_idP]; - UE_list_t *UE_list = &eNB->UE_list; + UE_info_t *UE_info = &eNB->UE_info; int UE_id = find_UE_id(module_idP, rntiP); nfapi_ul_config_ulsch_harq_information_rel10_t *harq_information_rel10 = &harq_information->harq_information_rel10; AssertFatal(UE_id >= 0, "UE_id cannot be found, impossible\n"); - AssertFatal(UE_list != NULL, "UE_list is null\n"); - LTE_PhysicalConfigDedicated_t *physicalConfigDedicated = UE_list->UE_template[CC_idP][UE_id].physicalConfigDedicated; + AssertFatal(UE_info != NULL, "UE_info is null\n"); + LTE_PhysicalConfigDedicated_t *physicalConfigDedicated = UE_info->UE_template[CC_idP][UE_id].physicalConfigDedicated; AssertFatal(physicalConfigDedicated != NULL, "physicalConfigDedicated for rnti %x is null\n", rntiP); struct LTE_PUSCH_ConfigDedicated *puschConfigDedicated = physicalConfigDedicated->pusch_ConfigDedicated; @@ -1468,14 +1468,14 @@ fill_nfapi_harq_information(module_id_t module_idP, { eNB_MAC_INST *eNB = RC.mac[module_idP]; COMMON_channels_t *cc = &eNB->common_channels[CC_idP]; - UE_list_t *UE_list = &eNB->UE_list; + UE_info_t *UE_info = &eNB->UE_info; int UE_id = find_UE_id(module_idP, rntiP); AssertFatal(UE_id >= 0, "UE_id cannot be found, impossible\n"); - AssertFatal(UE_list != NULL, "UE_list is null\n"); + AssertFatal(UE_info != NULL, "UE_info is null\n"); harq_information->harq_information_rel11.tl.tag = NFAPI_UL_CONFIG_REQUEST_HARQ_INFORMATION_REL11_TAG; harq_information->harq_information_rel11.num_ant_ports = 1; - LTE_PhysicalConfigDedicated_t *physicalConfigDedicated = UE_list->UE_template[CC_idP][UE_id].physicalConfigDedicated; + LTE_PhysicalConfigDedicated_t *physicalConfigDedicated = UE_info->UE_template[CC_idP][UE_id].physicalConfigDedicated; struct LTE_PUCCH_ConfigDedicated *pucch_ConfigDedicated = NULL; if (physicalConfigDedicated != NULL) pucch_ConfigDedicated = physicalConfigDedicated->pucch_ConfigDedicated; @@ -1489,7 +1489,7 @@ fill_nfapi_harq_information(module_id_t module_idP, case 6: case 7: if (cc->tdd_Config != NULL) { - // AssertFatal(UE_list->UE_template[CC_idP][UE_id].physicalConfigDedicated->pucch_ConfigDedicated != NULL, + // AssertFatal(UE_info->UE_template[CC_idP][UE_id].physicalConfigDedicated->pucch_ConfigDedicated != NULL, // "pucch_ConfigDedicated is null for TDD!\n"); if (physicalConfigDedicated != NULL && pucch_ConfigDedicated != NULL && pucch_ConfigDedicated->tdd_AckNackFeedbackMode != NULL && @@ -1619,15 +1619,14 @@ fill_nfapi_mch_config(nfapi_dl_config_request_body_t *dl_req, //------------------------------------------------------------------------------ void -fill_nfapi_dlsch_config(eNB_MAC_INST *eNB, - nfapi_dl_config_request_body_t *dl_req, +fill_nfapi_dlsch_config(nfapi_dl_config_request_pdu_t *dl_config_pdu, uint16_t length, int16_t pdu_index, uint16_t rnti, uint8_t resource_allocation_type, uint8_t virtual_resource_block_assignment_flag, - uint16_t resource_block_coding, + uint32_t resource_block_coding, uint8_t modulation, uint8_t redundancy_version, uint8_t transport_blocks, @@ -1646,7 +1645,6 @@ fill_nfapi_dlsch_config(eNB_MAC_INST *eNB, uint8_t num_bf_vector) //------------------------------------------------------------------------------ { - nfapi_dl_config_request_pdu_t *dl_config_pdu = &dl_req->dl_config_pdu_list[dl_req->number_pdu]; memset((void *) dl_config_pdu, 0, sizeof(nfapi_dl_config_request_pdu_t)); dl_config_pdu->pdu_type = NFAPI_DL_CONFIG_DLSCH_PDU_TYPE; dl_config_pdu->pdu_size = (uint8_t) (2 + sizeof(nfapi_dl_config_dlsch_pdu)); @@ -1673,7 +1671,6 @@ fill_nfapi_dlsch_config(eNB_MAC_INST *eNB, dl_config_pdu->dlsch_pdu.dlsch_pdu_rel8.transmission_mode = transmission_mode; dl_config_pdu->dlsch_pdu.dlsch_pdu_rel8.num_bf_prb_per_subband = num_bf_prb_per_subband; dl_config_pdu->dlsch_pdu.dlsch_pdu_rel8.num_bf_vector = num_bf_vector; - dl_req->number_pdu++; return; } @@ -1879,8 +1876,7 @@ mpdcch_sf_condition(eNB_MAC_INST *eNB, break; case TYPEUESPEC: - epdcch_setconfig_r11 = - eNB->UE_list.UE_template[CC_id][UE_id].physicalConfigDedicated->ext4->epdcch_Config_r11->config_r11.choice.setup.setConfigToAddModList_r11->list.array[0]; + epdcch_setconfig_r11 = eNB->UE_info.UE_template[CC_id][UE_id].physicalConfigDedicated->ext4->epdcch_Config_r11->config_r11.choice.setup.setConfigToAddModList_r11->list.array[0]; AssertFatal(epdcch_setconfig_r11 != NULL, " epdcch_setconfig_r11 is null for UE specific \n"); AssertFatal(epdcch_setconfig_r11->ext2 != NULL, " ext2 doesn't exist in epdcch config ' \n"); @@ -1988,11 +1984,11 @@ find_UE_id(module_id_t mod_idP, //------------------------------------------------------------------------------ { int UE_id; - UE_list_t *UE_list = &RC.mac[mod_idP]->UE_list; + UE_info_t *UE_info = &RC.mac[mod_idP]->UE_info; for (UE_id = 0; UE_id < MAX_MOBILES_PER_ENB; UE_id++) { - if (UE_list->active[UE_id] == TRUE) { - if (UE_list->UE_template[UE_PCCID(mod_idP, UE_id)][UE_id].rnti == rntiP) { + if (UE_info->active[UE_id] == TRUE) { + if (UE_info->UE_template[UE_PCCID(mod_idP, UE_id)][UE_id].rnti == rntiP) { return UE_id; } } @@ -2027,7 +2023,7 @@ find_RA_id(module_id_t mod_idP, //------------------------------------------------------------------------------ int -UE_num_active_CC(UE_list_t *listP, +UE_num_active_CC(UE_info_t *listP, int ue_idP) //------------------------------------------------------------------------------ { @@ -2040,7 +2036,7 @@ UE_PCCID(module_id_t mod_idP, int ue_idP) //------------------------------------------------------------------------------ { - return (RC.mac[mod_idP]->UE_list.pCC_id[ue_idP]); + return (RC.mac[mod_idP]->UE_info.pCC_id[ue_idP]); } //------------------------------------------------------------------------------ @@ -2051,7 +2047,7 @@ UE_RNTI(module_id_t mod_idP, { if (!RC.mac || !RC.mac[mod_idP]) return 0; - rnti_t rnti = RC.mac[mod_idP]->UE_list.UE_template[UE_PCCID(mod_idP, + rnti_t rnti = RC.mac[mod_idP]->UE_info.UE_template[UE_PCCID(mod_idP, ue_idP)][ue_idP].rnti; if (rnti > 0) { @@ -2069,7 +2065,7 @@ is_UE_active(module_id_t mod_idP, int ue_idP) //------------------------------------------------------------------------------ { - return (RC.mac[mod_idP]->UE_list.active[ue_idP]); + return (RC.mac[mod_idP]->UE_info.active[ue_idP]); } //------------------------------------------------------------------------------ @@ -2122,28 +2118,46 @@ get_aggregation(uint8_t bw_index, //------------------------------------------------------------------------------ /* - * Dump the UL or DL UE_list into LOG_T(MAC) + * Dump the UE_list into LOG_T(MAC) */ void -dump_ue_list(UE_list_t *listP, - int ul_flag) +dump_ue_list(UE_list_t *listP) { + for (int j = listP->head; j >= 0; j = listP->next[j]) + LOG_T(MAC, "DL list node %d => %d\n", j, listP->next[j]); +} + //------------------------------------------------------------------------------ -{ - if (ul_flag == 0) { - for (int j = listP->head; j >= 0; j = listP->next[j]) { - LOG_T(MAC, "DL list node %d => %d\n", - j, - listP->next[j]); - } +/* + * Add a UE to UE_list listP + */ +inline void add_ue_list(UE_list_t *listP, int UE_id) { + if (listP->head == -1) { + listP->head = UE_id; + listP->next[UE_id] = -1; } else { - for (int j = listP->head_ul; j >= 0; j = listP->next_ul[j]) { - LOG_T(MAC, "UL list node %d => %d\n", - j, - listP->next_ul[j]); - } + int i = listP->head; + while (listP->next[i] >= 0) + i = listP->next[i]; + listP->next[i] = UE_id; + listP->next[UE_id] = -1; + } +} + +//------------------------------------------------------------------------------ +/* + * Remove a UE from the UE_list listP, return the previous element + */ +inline int remove_ue_list(UE_list_t *listP, int UE_id) { + listP->next[UE_id] = -1; + if (listP->head == UE_id) { + listP->head = listP->next[UE_id]; + return -1; } - return; + int previous = prev(listP, UE_id); + if (previous != -1) + listP->next[previous] = listP->next[UE_id]; + return previous; } //------------------------------------------------------------------------------ @@ -2158,50 +2172,47 @@ add_new_ue(module_id_t mod_idP, { int UE_id; int i, j; - UE_list_t *UE_list = &RC.mac[mod_idP]->UE_list; - LOG_D(MAC, "[eNB %d, CC_id %d] Adding UE with rnti %x (next avail %d, num_UEs %d)\n", + UE_info_t *UE_info = &RC.mac[mod_idP]->UE_info; + LOG_D(MAC, "[eNB %d, CC_id %d] Adding UE with rnti %x (prev. num_UEs %d)\n", mod_idP, cc_idP, rntiP, - UE_list->avail, - UE_list->num_UEs); - dump_ue_list(UE_list, 0); + UE_info->num_UEs); for (i = 0; i < MAX_MOBILES_PER_ENB; i++) { - if (UE_list->active[i] == TRUE) + if (UE_info->active[i] == TRUE) continue; UE_id = i; - memset(&UE_list->UE_template[cc_idP][UE_id], 0, sizeof(UE_TEMPLATE)); - UE_list->UE_template[cc_idP][UE_id].rnti = rntiP; - UE_list->UE_template[cc_idP][UE_id].configured = FALSE; - UE_list->numactiveCCs[UE_id] = 1; - UE_list->numactiveULCCs[UE_id] = 1; - UE_list->pCC_id[UE_id] = cc_idP; - UE_list->ordered_CCids[0][UE_id] = cc_idP; - UE_list->ordered_ULCCids[0][UE_id] = cc_idP; - UE_list->num_UEs++; - UE_list->active[UE_id] = TRUE; + memset(&UE_info->UE_template[cc_idP][UE_id], 0, sizeof(UE_TEMPLATE)); + UE_info->UE_template[cc_idP][UE_id].rnti = rntiP; + UE_info->UE_template[cc_idP][UE_id].configured = FALSE; + UE_info->numactiveCCs[UE_id] = 1; + UE_info->numactiveULCCs[UE_id] = 1; + UE_info->pCC_id[UE_id] = cc_idP; + UE_info->ordered_CCids[0][UE_id] = cc_idP; + UE_info->ordered_ULCCids[0][UE_id] = cc_idP; + UE_info->num_UEs++; + UE_info->active[UE_id] = TRUE; + add_ue_list(&UE_info->list, UE_id); + dump_ue_list(&UE_info->list); if (IS_SOFTMODEM_IQPLAYER)// not specific to record/playback ? - UE_list->UE_template[cc_idP][UE_id].pre_assigned_mcs_ul = 0; - UE_list->UE_template[cc_idP][UE_id].rach_resource_type = rach_resource_type; - memset((void *) &UE_list->UE_sched_ctrl[UE_id], + UE_info->UE_template[cc_idP][UE_id].pre_assigned_mcs_ul = 0; + UE_info->UE_template[cc_idP][UE_id].rach_resource_type = rach_resource_type; + memset((void *) &UE_info->UE_sched_ctrl[UE_id], 0, sizeof(UE_sched_ctrl_t)); - memset((void *) &UE_list->eNB_UE_stats[cc_idP][UE_id], + memset((void *) &UE_info->eNB_UE_stats[cc_idP][UE_id], 0, sizeof(eNB_UE_STATS)); - UE_list->UE_sched_ctrl[UE_id].ue_reestablishment_reject_timer = 0; - /* default slice in case there was something different */ - UE_list->assoc_dl_slice_idx[UE_id] = 0; - UE_list->assoc_ul_slice_idx[UE_id] = 0; - UE_list->UE_sched_ctrl[UE_id].ta_update = 31; + UE_info->UE_sched_ctrl[UE_id].ue_reestablishment_reject_timer = 0; + UE_info->UE_sched_ctrl[UE_id].ta_update = 31; for (j = 0; j < 8; j++) { - UE_list->UE_template[cc_idP][UE_id].oldNDI[j] = 0; - UE_list->UE_template[cc_idP][UE_id].oldNDI_UL[j] = 0; - UE_list->UE_sched_ctrl[UE_id].round[cc_idP][j] = 8; - UE_list->UE_sched_ctrl[UE_id].round_UL[cc_idP][j] = 0; + UE_info->UE_template[cc_idP][UE_id].oldNDI[j] = 0; + UE_info->UE_template[cc_idP][UE_id].oldNDI_UL[j] = 0; + UE_info->UE_sched_ctrl[UE_id].round[cc_idP][j] = 8; + UE_info->UE_sched_ctrl[UE_id].round_UL[cc_idP][j] = 0; } eNB_ulsch_info[mod_idP][cc_idP][UE_id].status = S_UL_WAITING; @@ -2211,15 +2222,11 @@ add_new_ue(module_id_t mod_idP, UE_id, cc_idP, rntiP); - dump_ue_list(UE_list, - 0); return (UE_id); } - // printf("MAC: cannot add new UE for rnti %x\n", rntiP); LOG_E(MAC, "error in add_new_ue(), could not find space in UE_list, Dumping UE list\n"); - dump_ue_list(UE_list, - 0); + dump_ue_list(&UE_info->list); return -1; } @@ -2232,7 +2239,7 @@ rrc_mac_remove_ue(module_id_t mod_idP, rnti_t rntiP) //------------------------------------------------------------------------------ { - UE_list_t *UE_list = &RC.mac[mod_idP]->UE_list; + UE_info_t *UE_info = &RC.mac[mod_idP]->UE_info; int UE_id = find_UE_id(mod_idP, rntiP); eNB_UE_STATS *ue_stats = NULL; int pCC_id = -1; @@ -2248,37 +2255,14 @@ rrc_mac_remove_ue(module_id_t mod_idP, UE_id, pCC_id, rntiP); - dump_ue_list(UE_list, 0); // DL list displayed in LOG_T(MAC) - UE_list->active[UE_id] = FALSE; - UE_list->num_UEs--; - - /* If present, remove UE from DL list */ - if (UE_list->head == UE_id) { - UE_list->head = UE_list->next[UE_id]; - } else { - int previous = prev(UE_list, UE_id, 0); + UE_info->active[UE_id] = FALSE; + UE_info->num_UEs--; - if (previous != -1) { - UE_list->next[previous] = UE_list->next[UE_id]; - } - } - - /* If present, remove UE from UL list */ - if (UE_list->head_ul == UE_id) { - UE_list->head_ul = UE_list->next_ul[UE_id]; - } else { - int previous = prev(UE_list, UE_id, 1); - - if (previous != -1) { - UE_list->next_ul[previous] = UE_list->next_ul[UE_id]; - } - } + remove_ue_list(&UE_info->list, UE_id); /* Clear all remaining pending transmissions */ - memset(&UE_list->UE_template[pCC_id][UE_id], - 0, - sizeof(UE_TEMPLATE)); - ue_stats = &UE_list->eNB_UE_stats[pCC_id][UE_id]; + memset(&UE_info->UE_template[pCC_id][UE_id], 0, sizeof(UE_TEMPLATE)); + ue_stats = &UE_info->eNB_UE_stats[pCC_id][UE_id]; ue_stats->total_rbs_used = 0; ue_stats->total_rbs_used_retx = 0; @@ -2355,166 +2339,19 @@ rrc_mac_remove_ue(module_id_t mod_idP, /* * Returns the previous UE_id in the scheduling list in UL or DL */ -int -prev(UE_list_t *listP, - int nodeP, - int ul_flag) -//------------------------------------------------------------------------------ -{ - if (ul_flag == 0) { - if (nodeP == listP->head) { - return nodeP; - } +inline int prev(UE_list_t *listP, int nodeP) { + if (nodeP == listP->head) + return -1; /* there is no previous of the head */ - for (int j = listP->head; j >= 0; j = listP->next[j]) { - if (listP->next[j] == nodeP) { - return j; - } - } - } else { - if (nodeP == listP->head_ul) { - return nodeP; - } + for (int j = listP->head; j >= 0; j = listP->next[j]) + if (listP->next[j] == nodeP) + return j; - for (int j = listP->head_ul; j >= 0; j = listP->next_ul[j]) { - if (listP->next_ul[j] == nodeP) { - return j; - } - } - } - - LOG_E(MAC, "error in prev(), could not find previous to %d in UE_list %s, should never happen, Dumping UE list\n", - nodeP, - (ul_flag == 0) ? "DL" : "UL"); - dump_ue_list(listP, - ul_flag); + LOG_E(MAC, "%s(): could not find previous to %d in UE_list\n", __func__, nodeP); + dump_ue_list(listP); return -1; } -//------------------------------------------------------------------------------ -void -swap_UEs(UE_list_t *listP, - int nodeiP, - int nodejP, - int ul_flag) -//------------------------------------------------------------------------------ -{ - int prev_i, prev_j, next_i, next_j; - LOG_T(MAC, "Swapping UE %d,%d\n", - nodeiP, - nodejP); - dump_ue_list(listP, - ul_flag); - prev_i = prev(listP, - nodeiP, - ul_flag); - prev_j = prev(listP, - nodejP, - ul_flag); - AssertFatal((prev_i >= 0) && (prev_j >= 0), "swap_UEs: problem"); - - if (ul_flag == 0) { - next_i = listP->next[nodeiP]; - next_j = listP->next[nodejP]; - } else { - next_i = listP->next_ul[nodeiP]; - next_j = listP->next_ul[nodejP]; - } - - LOG_T(MAC, "[%s] next_i %d, next_i, next_j %d, head %d \n", - (ul_flag == 0) ? "DL" : "UL", - next_i, - next_j, - listP->head); - - if (ul_flag == 0) { - if (next_i == nodejP) { // case ... p(i) i j n(j) ... => ... p(j) j i n(i) ... - LOG_T(MAC, "Case ... p(i) i j n(j) ... => ... p(j) j i n(i) ...\n"); - listP->next[nodeiP] = next_j; - listP->next[nodejP] = nodeiP; - - if (nodeiP == listP->head) { // case i j n(j) - listP->head = nodejP; - } else { - listP->next[prev_i] = nodejP; - } - } else if (next_j == nodeiP) { // case ... p(j) j i n(i) ... => ... p(i) i j n(j) ... - LOG_T(MAC, "Case ... p(j) j i n(i) ... => ... p(i) i j n(j) ...\n"); - listP->next[nodejP] = next_i; - listP->next[nodeiP] = nodejP; - - if (nodejP == listP->head) { // case j i n(i) - listP->head = nodeiP; - } else { - listP->next[prev_j] = nodeiP; - } - } else { // case ... p(i) i n(i) ... p(j) j n(j) ... - listP->next[nodejP] = next_i; - listP->next[nodeiP] = next_j; - - if (nodeiP == listP->head) { - LOG_T(MAC, "changing head to %d\n", - nodejP); - listP->head = nodejP; - listP->next[prev_j] = nodeiP; - } else if (nodejP == listP->head) { - LOG_D(MAC, "changing head to %d\n", - nodeiP); - listP->head = nodeiP; - listP->next[prev_i] = nodejP; - } else { - listP->next[prev_i] = nodejP; - listP->next[prev_j] = nodeiP; - } - } - } else { // ul_flag - if (next_i == nodejP) { // case ... p(i) i j n(j) ... => ... p(j) j i n(i) ... - LOG_T(MAC, "[UL] Case ... p(i) i j n(j) ... => ... p(j) j i n(i) ...\n"); - listP->next_ul[nodeiP] = next_j; - listP->next_ul[nodejP] = nodeiP; - - if (nodeiP == listP->head_ul) { // case i j n(j) - listP->head_ul = nodejP; - } else { - listP->next_ul[prev_i] = nodejP; - } - } else if (next_j == nodeiP) { // case ... p(j) j i n(i) ... => ... p(i) i j n(j) ... - LOG_T(MAC, "[UL]Case ... p(j) j i n(i) ... => ... p(i) i j n(j) ...\n"); - listP->next_ul[nodejP] = next_i; - listP->next_ul[nodeiP] = nodejP; - - if (nodejP == listP->head_ul) { // case j i n(i) - listP->head_ul = nodeiP; - } else { - listP->next_ul[prev_j] = nodeiP; - } - } else { // case ... p(i) i n(i) ... p(j) j n(j) ... - listP->next_ul[nodejP] = next_i; - listP->next_ul[nodeiP] = next_j; - - if (nodeiP == listP->head_ul) { - LOG_T(MAC, "[UL]changing head to %d\n", - nodejP); - listP->head_ul = nodejP; - listP->next_ul[prev_j] = nodeiP; - } else if (nodejP == listP->head_ul) { - LOG_T(MAC, "[UL]changing head to %d\n", - nodeiP); - listP->head_ul = nodeiP; - listP->next_ul[prev_i] = nodejP; - } else { - listP->next_ul[prev_i] = nodejP; - listP->next_ul[prev_j] = nodeiP; - } - } - } - - LOG_T(MAC, "After swap\n"); - dump_ue_list(listP, - ul_flag); - return; -} - // This has to be updated to include BSR information //------------------------------------------------------------------------------ uint8_t @@ -2523,8 +2360,8 @@ UE_is_to_be_scheduled(module_id_t module_idP, uint8_t UE_id) //------------------------------------------------------------------------------ { - UE_TEMPLATE *UE_template = &RC.mac[module_idP]->UE_list.UE_template[CC_id][UE_id]; - UE_sched_ctrl_t *UE_sched_ctl = &RC.mac[module_idP]->UE_list.UE_sched_ctrl[UE_id]; + UE_TEMPLATE *UE_template = &RC.mac[module_idP]->UE_info.UE_template[CC_id][UE_id]; + UE_sched_ctrl_t *UE_sched_ctl = &RC.mac[module_idP]->UE_info.UE_sched_ctrl[UE_id]; int rrc_status; // do not schedule UE if UL is not working @@ -2566,7 +2403,7 @@ get_tmode(module_id_t module_idP, { eNB_MAC_INST *eNB = RC.mac[module_idP]; COMMON_channels_t *cc = &eNB->common_channels[CC_idP]; - struct LTE_PhysicalConfigDedicated *physicalConfigDedicated = eNB->UE_list.UE_template[CC_idP][UE_idP].physicalConfigDedicated; + struct LTE_PhysicalConfigDedicated *physicalConfigDedicated = eNB->UE_info.UE_template[CC_idP][UE_idP].physicalConfigDedicated; if (physicalConfigDedicated == NULL) { // RRCConnectionSetup not received by UE yet AssertFatal(cc->p_eNB <= 2, "p_eNB is %d, should be <2\n", @@ -2776,19 +2613,21 @@ get_min_rb_unit(module_id_t module_id, int N_RB_DL = to_prb(RC.mac[module_id]->common_channels[CC_id].mib->message.dl_Bandwidth); switch (N_RB_DL) { - case 6: // 1.4 MHz + case 6: // 1.4MHz min_rb_unit = 1; break; - case 25: // 5HMz + case 15: // 3MHz + case 25: // 5MHz min_rb_unit = 2; break; - case 50: // 10HMz + case 50: // 10MHz min_rb_unit = 3; break; - case 100: // 20HMz + case 75: // 15MHz + case 100: // 20MHz min_rb_unit = 4; break; @@ -2809,7 +2648,7 @@ uint32_t allocate_prbs_sub(int nb_rb, int N_RB_DL, int N_RBG, - uint8_t *rballoc) + const uint8_t *rballoc) //------------------------------------------------------------------------------ { int check = 0; //check1=0,check2=0; @@ -3482,7 +3321,7 @@ try_again: if (fCCE == -1) { if (DL_req->number_pdcch_ofdm_symbols == max_symbol) { - LOG_I(MAC, "subframe %d: Dropping Allocation for RNTI %x\n", + LOG_D(MAC, "subframe %d: Dropping Allocation for RNTI %x\n", subframeP, dl_config_pduLoop->dci_dl_pdu.dci_dl_pdu_rel8.rnti); @@ -3671,6 +3510,121 @@ CCE_allocation_infeasible(int module_idP, return res; } +int CCE_try_allocate_dlsch(int module_id, + int CC_id, + int subframe, + int UE_id, + uint8_t dl_cqi) { + const rnti_t rnti = RC.mac[module_id]->UE_info.UE_template[CC_id][UE_id].rnti; + nfapi_dl_config_request_body_t *DL_req = &RC.mac[module_id]->DL_req[CC_id].dl_config_request_body; + + if (DL_req->number_pdu >= MAX_NUM_DL_PDU) { + LOG_W(MAC, "Subframe %d: FAPI DL structure is full, skip scheduling UE %d\n", subframe, rnti); + return -1; + } + + int aggregation = 2; + const uint8_t tm = get_tmode(module_id, CC_id, UE_id); + switch (tm) { + case 1: + case 2: + case 7: + aggregation = get_aggregation(get_bw_index(module_id, CC_id), + dl_cqi, + format1); + break; + + case 3: + aggregation = get_aggregation(get_bw_index(module_id, CC_id), + dl_cqi, + format2A); + break; + + default: + AssertFatal(0, "Unsupported transmission mode %d\n", tm); + break; + } + + nfapi_dl_config_request_pdu_t *dl_config_pdu = &DL_req->dl_config_pdu_list[DL_req->number_pdu]; + memset(dl_config_pdu, 0, sizeof(nfapi_dl_config_request_pdu_t)); + dl_config_pdu->dci_dl_pdu.dci_dl_pdu_rel8.tl.tag = NFAPI_DL_CONFIG_REQUEST_DCI_DL_PDU_REL8_TAG; + dl_config_pdu->pdu_type = NFAPI_DL_CONFIG_DCI_DL_PDU_TYPE; + dl_config_pdu->dci_dl_pdu.dci_dl_pdu_rel8.rnti = rnti; + dl_config_pdu->dci_dl_pdu.dci_dl_pdu_rel8.rnti_type = 1; + dl_config_pdu->dci_dl_pdu.dci_dl_pdu_rel8.aggregation_level = aggregation; + DL_req->number_pdu++; + LOG_D(MAC, "Subframe %d: Checking CCE feasibility format 1: (%x,%d) \n", + subframe, rnti, aggregation); + + if (allocate_CCEs(module_id, CC_id, 0, subframe, 0) < 0) { + DL_req->number_pdu--; + return -1; + } + + DL_req->number_dci++; + nfapi_dl_config_request_pdu_t *dl_dlsch_pdu = &DL_req->dl_config_pdu_list[DL_req->number_pdu]; + dl_dlsch_pdu->pdu_type = NFAPI_DL_CONFIG_DLSCH_PDU_TYPE; + dl_dlsch_pdu->dlsch_pdu.dlsch_pdu_rel8.tl.tag = NFAPI_DL_CONFIG_REQUEST_DLSCH_PDU_REL8_TAG; + dl_dlsch_pdu->dlsch_pdu.dlsch_pdu_rel8.rnti = rnti; + DL_req->number_pdu++; + + return DL_req->number_pdu - 2; +} + +int CCE_try_allocate_ulsch(int module_id, + int CC_id, + int subframe, + int UE_id, + uint8_t dl_cqi) { + const rnti_t rnti = RC.mac[module_id]->UE_info.UE_template[CC_id][UE_id].rnti; + nfapi_hi_dci0_request_body_t *HI_DCI0_req = &RC.mac[module_id]->HI_DCI0_req[CC_id][subframe].hi_dci0_request_body; + + if (HI_DCI0_req->number_of_dci + HI_DCI0_req->number_of_hi >= MAX_NUM_HI_DCI0_PDU) { + LOG_W(MAC, "Subframe %d: FAPI UL structure is full, skip scheduling UE %d\n", subframe, rnti); + return -1; + } + + int aggregation = 2; + const uint8_t tm = get_tmode(module_id, CC_id, UE_id); + switch (tm) { + case 1: + case 2: + case 7: + aggregation = get_aggregation(get_bw_index(module_id, CC_id), + dl_cqi, + format1); + break; + + case 3: + aggregation = get_aggregation(get_bw_index(module_id, CC_id), + dl_cqi, + format2A); + break; + + default: + AssertFatal(0, "Unsupported transmission mode %d\n", tm); + break; + } + + const int idx = HI_DCI0_req->number_of_dci + HI_DCI0_req->number_of_hi; + nfapi_hi_dci0_request_pdu_t *hi_dci0_pdu = &HI_DCI0_req->hi_dci0_pdu_list[idx]; + memset(hi_dci0_pdu, 0, sizeof(nfapi_hi_dci0_request_pdu_t)); + hi_dci0_pdu->pdu_type = NFAPI_HI_DCI0_DCI_PDU_TYPE; + hi_dci0_pdu->dci_pdu.dci_pdu_rel8.tl.tag = NFAPI_HI_DCI0_REQUEST_DCI_PDU_REL8_TAG; + hi_dci0_pdu->dci_pdu.dci_pdu_rel8.rnti = rnti; + hi_dci0_pdu->dci_pdu.dci_pdu_rel8.aggregation_level = aggregation; + HI_DCI0_req->number_of_dci++; + LOG_D(MAC, "%s() sf %d: Checking CCE feasibility format 2: RNTI %04x, agg %d\n", + __func__, subframe, rnti, aggregation); + + if (allocate_CCEs(module_id, CC_id, 0, subframe, 0) < 0) { + HI_DCI0_req->number_of_dci--; + return -1; + } + + return idx; +} + //------------------------------------------------------------------------------ void get_retransmission_timing(LTE_TDD_Config_t *tdd_Config, @@ -3931,15 +3885,15 @@ extract_harq(module_id_t mod_idP, //------------------------------------------------------------------------------ { eNB_MAC_INST *eNB = RC.mac[mod_idP]; - UE_list_t *UE_list = &eNB->UE_list; - UE_sched_ctrl_t *sched_ctl = &UE_list->UE_sched_ctrl[UE_id]; + UE_info_t *UE_info = &eNB->UE_info; + UE_sched_ctrl_t *sched_ctl = &UE_info->UE_sched_ctrl[UE_id]; rnti_t rnti = UE_RNTI(mod_idP, UE_id); COMMON_channels_t *cc = &eNB->common_channels[CC_idP]; nfapi_harq_indication_fdd_rel13_t *harq_indication_fdd; nfapi_harq_indication_tdd_rel13_t *harq_indication_tdd; uint16_t num_ack_nak; - int numCC = UE_list->numactiveCCs[UE_id]; - int pCCid = UE_list->pCC_id[UE_id]; + int numCC = UE_info->numactiveCCs[UE_id]; + int pCCid = UE_info->pCC_id[UE_id]; int spatial_bundling = 0; int tmode[5]; int i, j, m; @@ -3947,7 +3901,7 @@ extract_harq(module_id_t mod_idP, sub_frame_t subframe_tx; int frame_tx; uint8_t harq_pid; - LTE_PhysicalConfigDedicated_t *physicalConfigDedicated = UE_list->UE_template[pCCid][UE_id].physicalConfigDedicated; + LTE_PhysicalConfigDedicated_t *physicalConfigDedicated = UE_info->UE_template[pCCid][UE_id].physicalConfigDedicated; if (physicalConfigDedicated != NULL && physicalConfigDedicated->pucch_ConfigDedicated != NULL && physicalConfigDedicated->ext7 != NULL && physicalConfigDedicated->ext7->pucch_ConfigDedicated_r13 != NULL && @@ -4081,7 +4035,7 @@ extract_harq(module_id_t mod_idP, sched_ctl->round[CC_idP][harq_pid]); // use 1 HARQ proces of BL/CE UE for now - if (UE_list->UE_template[pCCid][UE_id].rach_resource_type > 0) harq_pid = 0; + if (UE_info->UE_template[pCCid][UE_id].rach_resource_type > 0) harq_pid = 0; switch (harq_indication_fdd->mode) { case 0: // Format 1a/b (10.1.2.1) @@ -4567,18 +4521,18 @@ extract_pucch_csi(module_id_t mod_idP, uint8_t length) //------------------------------------------------------------------------------ { - UE_list_t *UE_list = &RC.mac[mod_idP]->UE_list; - UE_sched_ctrl_t *sched_ctl = &UE_list->UE_sched_ctrl[UE_id]; + UE_info_t *UE_info = &RC.mac[mod_idP]->UE_info; + UE_sched_ctrl_t *sched_ctl = &UE_info->UE_sched_ctrl[UE_id]; COMMON_channels_t *cc = &RC.mac[mod_idP]->common_channels[CC_idP]; int no_pmi; uint8_t Ltab[6] = { 0, 2, 4, 4, 4, 4 }; uint8_t Jtab[6] = { 0, 2, 2, 3, 4, 4 }; int feedback_cnt; - AssertFatal(UE_list->UE_template[CC_idP][UE_id].physicalConfigDedicated != NULL, "physicalConfigDedicated is null for UE %d\n", + AssertFatal(UE_info->UE_template[CC_idP][UE_id].physicalConfigDedicated != NULL, "physicalConfigDedicated is null for UE %d\n", UE_id); - AssertFatal(UE_list->UE_template[CC_idP][UE_id].physicalConfigDedicated->cqi_ReportConfig != NULL, "cqi_ReportConfig is null for UE %d\n", + AssertFatal(UE_info->UE_template[CC_idP][UE_id].physicalConfigDedicated->cqi_ReportConfig != NULL, "cqi_ReportConfig is null for UE %d\n", UE_id); - struct LTE_CQI_ReportPeriodic *cqi_ReportPeriodic = UE_list->UE_template[CC_idP][UE_id].physicalConfigDedicated->cqi_ReportConfig->cqi_ReportPeriodic; + struct LTE_CQI_ReportPeriodic *cqi_ReportPeriodic = UE_info->UE_template[CC_idP][UE_id].physicalConfigDedicated->cqi_ReportConfig->cqi_ReportPeriodic; AssertFatal(cqi_ReportPeriodic != NULL, "cqi_ReportPeriodic is null for UE %d\n", UE_id); // determine feedback mode @@ -4678,9 +4632,9 @@ extract_pusch_csi(module_id_t mod_idP, uint8_t length) //------------------------------------------------------------------------------ { - UE_list_t *UE_list = &RC.mac[mod_idP]->UE_list; + UE_info_t *UE_info = &RC.mac[mod_idP]->UE_info; COMMON_channels_t *cc = &RC.mac[mod_idP]->common_channels[CC_idP]; - UE_sched_ctrl_t *sched_ctl = &UE_list->UE_sched_ctrl[UE_id]; + UE_sched_ctrl_t *sched_ctl = &UE_info->UE_sched_ctrl[UE_id]; int Ntab[6] = { 0, 4, 7, 9, 10, 13 }; int Ntab_uesel[6] = { 0, 8, 13, 17, 19, 25 }; int Ltab_uesel[6] = { 0, 6, 9, 13, 15, 18 }; @@ -4689,12 +4643,12 @@ extract_pusch_csi(module_id_t mod_idP, int i; uint64_t p = *(uint64_t *) pdu; int curbyte, curbit; - AssertFatal(UE_list->UE_template[CC_idP][UE_id].physicalConfigDedicated != NULL, "physicalConfigDedicated is null for UE %d\n", + AssertFatal(UE_info->UE_template[CC_idP][UE_id].physicalConfigDedicated != NULL, "physicalConfigDedicated is null for UE %d\n", UE_id); - AssertFatal(UE_list->UE_template[CC_idP][UE_id].physicalConfigDedicated->cqi_ReportConfig != NULL, "cqi_ReportConfig is null for UE %d\n", + AssertFatal(UE_info->UE_template[CC_idP][UE_id].physicalConfigDedicated->cqi_ReportConfig != NULL, "cqi_ReportConfig is null for UE %d\n", UE_id); LTE_CQI_ReportModeAperiodic_t *cqi_ReportModeAperiodic - = UE_list->UE_template[CC_idP][UE_id].physicalConfigDedicated->cqi_ReportConfig->cqi_ReportModeAperiodic; + = UE_info->UE_template[CC_idP][UE_id].physicalConfigDedicated->cqi_ReportConfig->cqi_ReportModeAperiodic; AssertFatal(cqi_ReportModeAperiodic != NULL, "cqi_ReportModeAperiodic is null for UE %d\n", UE_id); int N = Ntab[cc->mib->message.dl_Bandwidth]; @@ -4964,14 +4918,14 @@ cqi_indication(module_id_t mod_idP, //------------------------------------------------------------------------------ { int UE_id = find_UE_id(mod_idP, rntiP); - UE_list_t *UE_list = &RC.mac[mod_idP]->UE_list; + UE_info_t *UE_info = &RC.mac[mod_idP]->UE_info; if (UE_id == -1) { LOG_W(MAC, "cqi_indication: UE %x not found\n", rntiP); return; } - UE_sched_ctrl_t *sched_ctl = &UE_list->UE_sched_ctrl[UE_id]; + UE_sched_ctrl_t *sched_ctl = &UE_info->UE_sched_ctrl[UE_id]; if (UE_id >= 0) { LOG_D(MAC,"%s() UE_id:%d channel:%d cqi:%d\n", @@ -5037,11 +4991,11 @@ SR_indication(module_id_t mod_idP, T_INT(subframeP), T_INT(rntiP)); int UE_id = find_UE_id(mod_idP, rntiP); - UE_list_t *UE_list = &RC.mac[mod_idP]->UE_list; + UE_info_t *UE_info = &RC.mac[mod_idP]->UE_info; UE_sched_ctrl_t *UE_scheduling_ctrl = NULL; if (UE_id != -1) { - UE_scheduling_ctrl = &(UE_list->UE_sched_ctrl[UE_id]); + UE_scheduling_ctrl = &(UE_info->UE_sched_ctrl[UE_id]); if ((UE_scheduling_ctrl->cdrx_configured == TRUE) && (UE_scheduling_ctrl->dci0_ongoing_timer > 0) && @@ -5065,8 +5019,8 @@ SR_indication(module_id_t mod_idP, cc_idP); } - UE_list->UE_template[cc_idP][UE_id].ul_SR = 1; - UE_list->UE_template[cc_idP][UE_id].ul_active = TRUE; + UE_info->UE_template[cc_idP][UE_id].ul_SR = 1; + UE_info->UE_template[cc_idP][UE_id].ul_active = TRUE; VCD_SIGNAL_DUMPER_DUMP_FUNCTION_BY_NAME(VCD_SIGNAL_DUMPER_FUNCTIONS_SR_INDICATION, 1); VCD_SIGNAL_DUMPER_DUMP_FUNCTION_BY_NAME(VCD_SIGNAL_DUMPER_FUNCTIONS_SR_INDICATION, 0); } @@ -5093,7 +5047,7 @@ UL_failure_indication(module_id_t mod_idP, //------------------------------------------------------------------------------ { int UE_id = find_UE_id(mod_idP, rntiP); - UE_list_t *UE_list = &RC.mac[mod_idP]->UE_list; + UE_info_t *UE_info = &RC.mac[mod_idP]->UE_info; if (UE_id != -1) { LOG_D(MAC, "[eNB %d][UE %d/%x] Frame %d subframeP %d Signaling UL Failure for UE %d on CC_id %d (timer %d)\n", @@ -5104,9 +5058,9 @@ UL_failure_indication(module_id_t mod_idP, subframeP, UE_id, cc_idP, - UE_list->UE_sched_ctrl[UE_id].ul_failure_timer); + UE_info->UE_sched_ctrl[UE_id].ul_failure_timer); - if (UE_list->UE_sched_ctrl[UE_id].ul_failure_timer == 0) UE_list->UE_sched_ctrl[UE_id].ul_failure_timer = 1; + if (UE_info->UE_sched_ctrl[UE_id].ul_failure_timer == 0) UE_info->UE_sched_ctrl[UE_id].ul_failure_timer = 1; } else { // AssertFatal(0, "find_UE_id(%u,rnti %d) not found", enb_mod_idP, rntiP); // AssertError(0, 0, "Frame %d: find_UE_id(%u,rnti %d) not found\n", frameP, enb_mod_idP, rntiP); @@ -5169,8 +5123,8 @@ harq_indication(module_id_t mod_idP, return; } - UE_list_t *UE_list = &RC.mac[mod_idP]->UE_list; - UE_sched_ctrl_t *sched_ctl = &UE_list->UE_sched_ctrl[UE_id]; + UE_info_t *UE_info = &RC.mac[mod_idP]->UE_info; + UE_sched_ctrl_t *sched_ctl = &UE_info->UE_sched_ctrl[UE_id]; COMMON_channels_t *cc = &RC.mac[mod_idP]->common_channels[CC_idP]; // extract HARQ Information @@ -5201,51 +5155,3 @@ harq_indication(module_id_t mod_idP, return; } - -// Flexran Slicing functions -//------------------------------------------------------------------------------ -uint16_t -nb_rbs_allowed_slice(float rb_percentage, - int total_rbs) -//------------------------------------------------------------------------------ -{ - return (uint16_t) floor(rb_percentage * total_rbs); -} - -//------------------------------------------------------------------------------ -int -ue_dl_slice_membership(module_id_t mod_id, - int UE_id, - int slice_idx) -//------------------------------------------------------------------------------ -{ - eNB_MAC_INST *eNB = RC.mac[mod_id]; - - if (slice_idx < 0 || slice_idx >= eNB->slice_info.n_dl) { - LOG_W(MAC, "out of range slice index %d (slice ID %d)\n", - slice_idx, - eNB->slice_info.dl[slice_idx].id); - return 0; - } - - return eNB->UE_list.active[UE_id] == TRUE && eNB->UE_list.assoc_dl_slice_idx[UE_id] == slice_idx; -} - -//------------------------------------------------------------------------------ -int -ue_ul_slice_membership(module_id_t mod_id, - int UE_id, - int slice_idx) -//------------------------------------------------------------------------------ -{ - eNB_MAC_INST *eNB = RC.mac[mod_id]; - - if (slice_idx < 0 || slice_idx >= eNB->slice_info.n_ul) { - LOG_W(MAC, "out of range slice index %d (slice ID %d)\n", - slice_idx, - eNB->slice_info.dl[slice_idx].id); - return 0; - } - - return eNB->UE_list.active[UE_id] == TRUE && eNB->UE_list.assoc_ul_slice_idx[UE_id] == slice_idx; -} diff --git a/openair2/LAYER2/MAC/eNB_scheduler_ulsch.c b/openair2/LAYER2/MAC/eNB_scheduler_ulsch.c index fdaa7de586ac62c7dae2354fad235e4ea687b541..3062e5c9647826af5fe547d5fa7a06c7f6707004 100644 --- a/openair2/LAYER2/MAC/eNB_scheduler_ulsch.c +++ b/openair2/LAYER2/MAC/eNB_scheduler_ulsch.c @@ -123,17 +123,15 @@ rx_sdu(const module_id_t enb_mod_idP, unsigned short rx_lengths[NB_RB_MAX]; uint8_t lcgid = 0; int lcgid_updated[4] = {0, 0, 0, 0}; - eNB_MAC_INST *mac = NULL; - UE_list_t *UE_list = NULL; + eNB_MAC_INST *mac = RC.mac[enb_mod_idP]; + UE_info_t *UE_info = &mac->UE_info; rrc_eNB_ue_context_t *ue_contextP = NULL; UE_sched_ctrl_t *UE_scheduling_control = NULL; UE_TEMPLATE *UE_template_ptr = NULL; /* Init */ current_rnti = rntiP; UE_id = find_UE_id(enb_mod_idP, current_rnti); - mac = RC.mac[enb_mod_idP]; harq_pid = subframe2harqpid(&mac->common_channels[CC_idP], frameP, subframeP); - UE_list = &mac->UE_list; memset(rx_ces, 0, MAX_NUM_CE * sizeof(unsigned char)); memset(rx_lcids, 0, NB_RB_MAX * sizeof(unsigned char)); memset(rx_lengths, 0, NB_RB_MAX * sizeof(unsigned short)); @@ -142,8 +140,8 @@ rx_sdu(const module_id_t enb_mod_idP, trace_pdu(DIRECTION_UPLINK, sduP, sdu_lenP, 0, WS_C_RNTI, current_rnti, frameP, subframeP, 0, 0); if (UE_id != -1) { - UE_scheduling_control = &(UE_list->UE_sched_ctrl[UE_id]); - UE_template_ptr = &(UE_list->UE_template[CC_idP][UE_id]); + UE_scheduling_control = &UE_info->UE_sched_ctrl[UE_id]; + UE_template_ptr = &UE_info->UE_template[CC_idP][UE_id]; LOG_D(MAC, "[eNB %d][PUSCH %d] CC_id %d %d.%d Received ULSCH sdu round %d from PHY (rnti %x, UE_id %d) ul_cqi %d\n", enb_mod_idP, harq_pid, @@ -414,8 +412,8 @@ rx_sdu(const module_id_t enb_mod_idP, UE_id = old_UE_id; current_rnti = old_rnti; /* Clear timer */ - UE_scheduling_control = &(UE_list->UE_sched_ctrl[UE_id]); - UE_template_ptr = &(UE_list->UE_template[CC_idP][UE_id]); + UE_scheduling_control = &UE_info->UE_sched_ctrl[UE_id]; + UE_template_ptr = &UE_info->UE_template[CC_idP][UE_id]; UE_scheduling_control->uplane_inactivity_timer = 0; UE_scheduling_control->ul_inactivity_timer = 0; UE_scheduling_control->ul_failure_timer = 0; @@ -431,7 +429,7 @@ rx_sdu(const module_id_t enb_mod_idP, UE_template_ptr->ul_SR = 1; UE_scheduling_control->crnti_reconfigurationcomplete_flag = 1; - UE_list->UE_template[UE_PCCID(enb_mod_idP, UE_id)][UE_id].configured = 1; + UE_info->UE_template[UE_PCCID(enb_mod_idP, UE_id)][UE_id].configured = 1; cancel_ra_proc(enb_mod_idP, CC_idP, frameP, @@ -481,8 +479,8 @@ rx_sdu(const module_id_t enb_mod_idP, ra->crnti_rrc_mui = rrc_eNB_mui-1; ra->crnti_harq_pid = -1; /* Clear timer */ - UE_scheduling_control = &(UE_list->UE_sched_ctrl[UE_id]); - UE_template_ptr = &(UE_list->UE_template[CC_idP][UE_id]); + UE_scheduling_control = &UE_info->UE_sched_ctrl[UE_id]; + UE_template_ptr = &UE_info->UE_template[CC_idP][UE_id]; UE_scheduling_control->uplane_inactivity_timer = 0; UE_scheduling_control->ul_inactivity_timer = 0; UE_scheduling_control->ul_failure_timer = 0; @@ -533,7 +531,7 @@ rx_sdu(const module_id_t enb_mod_idP, UE_template_ptr->ul_buffer_info[LCGID3]; RC.eNB[enb_mod_idP][CC_idP]->pusch_stats_bsr[UE_id][(frameP * 10) + subframeP] = (payload_ptr[0] & 0x3f); - if (UE_id == UE_list->head) { + if (UE_id == UE_info->list.head) { VCD_SIGNAL_DUMPER_DUMP_VARIABLE_BY_NAME(VCD_SIGNAL_DUMPER_VARIABLES_UE0_BSR, (payload_ptr[0] & 0x3f)); } @@ -690,8 +688,8 @@ rx_sdu(const module_id_t enb_mod_idP, frameP, ra->rnti, UE_id); - UE_scheduling_control = &(UE_list->UE_sched_ctrl[UE_id]); - UE_template_ptr = &(UE_list->UE_template[CC_idP][UE_id]); + UE_scheduling_control = &UE_info->UE_sched_ctrl[UE_id]; + UE_template_ptr = &UE_info->UE_template[CC_idP][UE_id]; } } else { LOG_D(MAC, "[eNB %d][RAPROC] CC_id %d Frame %d CCCH: Received Msg3 from already registered UE %d: length %d, offset %ld\n", @@ -780,11 +778,11 @@ rx_sdu(const module_id_t enb_mod_idP, enb_mod_idP, CC_idP, frameP, rx_lengths[i], UE_id, rx_lcids[i]); mac_rlc_data_ind(enb_mod_idP, current_rnti, enb_mod_idP, frameP, ENB_FLAG_YES, MBMS_FLAG_NO, rx_lcids[i], (char *) payload_ptr, rx_lengths[i], 1, NULL); //(unsigned int*)crc_status); - UE_list->eNB_UE_stats[CC_idP][UE_id].num_pdu_rx[rx_lcids[i]] += 1; - UE_list->eNB_UE_stats[CC_idP][UE_id].num_bytes_rx[rx_lcids[i]] += rx_lengths[i]; + UE_info->eNB_UE_stats[CC_idP][UE_id].num_pdu_rx[rx_lcids[i]] += 1; + UE_info->eNB_UE_stats[CC_idP][UE_id].num_bytes_rx[rx_lcids[i]] += rx_lengths[i]; if (mac_eNB_get_rrc_status(enb_mod_idP, current_rnti) < RRC_RECONFIGURED) { - UE_list->UE_sched_ctrl[UE_id].uplane_inactivity_timer = 0; + UE_info->UE_sched_ctrl[UE_id].uplane_inactivity_timer = 0; } } @@ -841,8 +839,8 @@ rx_sdu(const module_id_t enb_mod_idP, if ((rx_lengths[i] < SCH_PAYLOAD_SIZE_MAX) && (rx_lengths[i] > 0)) { // MAX SIZE OF transport block mac_rlc_data_ind(enb_mod_idP, current_rnti, enb_mod_idP, frameP, ENB_FLAG_YES, MBMS_FLAG_NO, rx_lcids[i], (char *) payload_ptr, rx_lengths[i], 1, NULL); - UE_list->eNB_UE_stats[CC_idP][UE_id].num_pdu_rx[rx_lcids[i]] += 1; - UE_list->eNB_UE_stats[CC_idP][UE_id].num_bytes_rx[rx_lcids[i]] += rx_lengths[i]; + UE_info->eNB_UE_stats[CC_idP][UE_id].num_pdu_rx[rx_lcids[i]] += 1; + UE_info->eNB_UE_stats[CC_idP][UE_id].num_bytes_rx[rx_lcids[i]] += rx_lengths[i]; /* Clear uplane_inactivity_timer */ UE_scheduling_control->uplane_inactivity_timer = 0; /* Reset RRC inactivity timer after uplane activity */ @@ -857,7 +855,7 @@ rx_sdu(const module_id_t enb_mod_idP, current_rnti); } } else { /* rx_length[i] Max size */ - UE_list->eNB_UE_stats[CC_idP][UE_id].num_errors_rx += 1; + UE_info->eNB_UE_stats[CC_idP][UE_id].num_errors_rx += 1; LOG_E(MAC, "[eNB %d] CC_id %d Frame %d : Max size of transport block reached LCID %d from UE %d ", enb_mod_idP, CC_idP, @@ -922,12 +920,12 @@ rx_sdu(const module_id_t enb_mod_idP, /* NN--> FK: we could either check the payload, or use a phy helper to detect a false msg3 */ if ((num_sdu == 0) && (num_ce == 0)) { if (UE_id != -1) - UE_list->eNB_UE_stats[CC_idP][UE_id].total_num_errors_rx += 1; + UE_info->eNB_UE_stats[CC_idP][UE_id].total_num_errors_rx += 1; } else { if (UE_id != -1) { - UE_list->eNB_UE_stats[CC_idP][UE_id].pdu_bytes_rx = sdu_lenP; - UE_list->eNB_UE_stats[CC_idP][UE_id].total_pdu_bytes_rx += sdu_lenP; - UE_list->eNB_UE_stats[CC_idP][UE_id].total_num_pdus_rx += 1; + UE_info->eNB_UE_stats[CC_idP][UE_id].pdu_bytes_rx = sdu_lenP; + UE_info->eNB_UE_stats[CC_idP][UE_id].total_pdu_bytes_rx += sdu_lenP; + UE_info->eNB_UE_stats[CC_idP][UE_id].total_num_pdus_rx += 1; } } @@ -1102,16 +1100,12 @@ schedule_ulsch(module_id_t module_idP, sub_frame_t subframeP) //----------------------------------------------------------------------------- { - uint16_t first_rb[NFAPI_CC_MAX]; eNB_MAC_INST *mac = NULL; - slice_info_t *sli = NULL; COMMON_channels_t *cc = NULL; int sched_subframe; int sched_frame; /* Init */ mac = RC.mac[module_idP]; - sli = &(mac->slice_info); - memset(first_rb, 0, NFAPI_CC_MAX * sizeof(uint16_t)); start_meas(&(mac->schedule_ulsch)); sched_subframe = (subframeP + 4) % 10; sched_frame = frameP; @@ -1218,60 +1212,53 @@ schedule_ulsch(module_id_t module_idP, /* Note: RC.nb_mac_CC[module_idP] should be lower than or equal to NFAPI_CC_MAX */ for (int CC_id = 0; CC_id < RC.nb_mac_CC[module_idP]; CC_id++, cc++) { - first_rb[CC_id] = (emtc_active[CC_id] == 1) ? 7 : 1; - RA_t *ra_ptr = cc->ra; - - /* From Louis-Adrien to François: - * The comment bloc below is to configure with a command line. - * I took it from the equivalent part in the fairRR scheduler (around line 2578 in eNB_scheduler_fairRR.c). - * As said in the meeting, it seems to work only for small TBS. - * The cause of false RA still present with this fix is to investigate. - * - * Note: in the get_prach_prb_offset() function below, the last argument is frameP in eNB_scheduler_fairRR.c - * I think it should be sched_frame instead. This parameter has only impacts in case TDD and preamble format 4. - * To confirm. - */ - /* - int start_rb = 0; - int nb_rb = 6; - LTE_DL_FRAME_PARMS *frame_parms = &(RC.eNB[module_idP][CC_id]->frame_parms); - - if (is_prach_subframe(frame_parms, sched_frame, sched_subframe) == 1) { - start_rb = get_prach_prb_offset(frame_parms, - frame_parms->prach_config_common.prach_ConfigInfo.prach_ConfigIndex, - frame_parms->prach_config_common.prach_ConfigInfo.prach_FreqOffset, - 0, // tdd_mapindex - sched_frame); // Nf - - first_rb[CC_id] = start_rb + nb_rb; + LTE_DL_FRAME_PARMS *frame_parms = &RC.eNB[module_idP][CC_id]->frame_parms; + if (is_prach_subframe(frame_parms, sched_frame, sched_subframe)) { + int start_rb = get_prach_prb_offset( + frame_parms, + frame_parms->prach_config_common.prach_ConfigInfo.prach_ConfigIndex, + frame_parms->prach_config_common.prach_ConfigInfo.prach_FreqOffset, + 0, // tdd_mapindex + sched_frame); // Nf + for (int i = 0; i < 6; i++) + cc[CC_id].vrb_map_UL[start_rb + i] = 1; } - */ - /* - * Check if RA (Msg3) is active in this subframeP, if so skip the PRB used for Msg3 - * Msg3 is using 1 PRB so we need to increase first_rb accordingly - * Not sure about the break (can there be more than 1 active RA procedure per CC_id and per subframe?) + /* HACK: let's remove the PUCCH from available RBs + * we suppose PUCCH size is: + * - for 25 RBs: 1 RB (top and bottom of ressource grid) + * - for 50: 2 RBs + * - for 100: 3 RBs + * This is totally arbitrary and might even be wrong. */ - for (int ra_index = 0; ra_index < NB_RA_PROC_MAX; ra_index++, ra_ptr++) { - if ((ra_ptr->state == WAITMSG3) && (ra_ptr->Msg3_subframe == sched_subframe)) { - if (first_rb[CC_id] < ra_ptr->msg3_first_rb + ra_ptr->msg3_nb_rb) { - first_rb[CC_id] = ra_ptr->msg3_first_rb + ra_ptr->msg3_nb_rb; - } + switch (to_prb(cc[CC_id].ul_Bandwidth)) { + case 25: + cc[CC_id].vrb_map_UL[0] = 1; + cc[CC_id].vrb_map_UL[24] = 1; + break; - /* Louis-Adrien: I couldn't find an interdiction of multiple Msg3 scheduling - * on the same time resources. Also the performance improvement of breaking is low, - * since we will loop until the end, most of the time. - * I'm letting the break as a reminder, in case of misunderstanding the spec. - */ - // break; - } + case 50: + cc[CC_id].vrb_map_UL[0] = 1; + cc[CC_id].vrb_map_UL[1] = 1; + cc[CC_id].vrb_map_UL[48] = 1; + cc[CC_id].vrb_map_UL[49] = 1; + break; + + case 100: + cc[CC_id].vrb_map_UL[0] = 1; + cc[CC_id].vrb_map_UL[1] = 1; + cc[CC_id].vrb_map_UL[2] = 1; + cc[CC_id].vrb_map_UL[97] = 1; + cc[CC_id].vrb_map_UL[98] = 1; + cc[CC_id].vrb_map_UL[99] = 1; + break; + + default: + LOG_E(MAC, "RBs setting not handled. Todo.\n"); + exit(1); } - } - /* Run each enabled slice-specific schedulers one by one */ - for (int i = 0; i < sli->n_ul; i++) { - /* By default the scheduler is schedule_ulsch_rnti (see below) */ - sli->ul[i].sched_cb(module_idP, i, frameP, subframeP, sched_subframe, first_rb); + schedule_ulsch_rnti(module_idP, CC_id, frameP, subframeP, sched_subframe); } stop_meas(&mac->schedule_ulsch); @@ -1283,48 +1270,20 @@ schedule_ulsch(module_id_t module_idP, */ void schedule_ulsch_rnti(module_id_t module_idP, - int slice_idx, + int CC_id, frame_t frameP, sub_frame_t subframeP, - unsigned char sched_subframeP, - uint16_t *first_rb) -//----------------------------------------------------------------------------- -{ - rnti_t rnti = -1; - uint8_t aggregation = 2; - uint8_t round_index = 0; - uint8_t harq_pid = 0; - uint8_t status = 0; - uint8_t rb_table_index = -1; - uint8_t dlsch_flag = 0; - uint16_t ul_req_index = 0; - uint32_t cqi_req = 0; - uint32_t cshift = 0; - uint32_t ndi = 0; - uint32_t tpc = 0; - int32_t snr = 0; - int32_t target_snr = 0; - int32_t framex10psubframe = 0; + unsigned char sched_subframeP) { + /* TODO: does this need to be static? */ static int32_t tpc_accumulated = 0; - int sched_frame = 0; - int CC_id = 0; - eNB_MAC_INST *mac = NULL; - COMMON_channels_t *cc = NULL; - UE_list_t *UE_list = NULL; - slice_info_t *sli = NULL; - UE_TEMPLATE *UE_template_ptr = NULL; - UE_sched_ctrl_t *UE_sched_ctrl_ptr = NULL; - int rvidx_tab[4] = {0, 2, 3, 1}; - int first_rb_slice[NFAPI_CC_MAX]; - int n_rb_ul_tab[NFAPI_CC_MAX]; - /* Init */ - mac = RC.mac[module_idP]; - cc = mac->common_channels; - UE_list = &(mac->UE_list); - sli = &(mac->slice_info); - memset(first_rb_slice, 0, NFAPI_CC_MAX * sizeof(int)); - memset(n_rb_ul_tab, 0, NFAPI_CC_MAX * sizeof(int)); - sched_frame = frameP; + /* values from 0 to 7 can be used for mapping the cyclic shift + * (36.211 , Table 5.5.2.1.1-1) */ + const uint32_t cshift = 0; + eNB_MAC_INST *mac = RC.mac[module_idP]; + COMMON_channels_t *cc = mac->common_channels; + UE_info_t *UE_info = &mac->UE_info; + + int sched_frame = frameP; if (sched_subframeP < subframeP) { sched_frame++; @@ -1340,63 +1299,23 @@ schedule_ulsch_rnti(module_id_t module_idP, nfapi_ul_config_ulsch_harq_information *ulsch_harq_information; hi_dci0_req->sfn_sf = (frameP << 4) + subframeP; - /* Note: RC.nb_mac_CC[module_idP] should be lower than or equal to NFAPI_CC_MAX */ - for (CC_id = 0; CC_id < RC.nb_mac_CC[module_idP]; CC_id++) { - n_rb_ul_tab[CC_id] = to_prb(cc[CC_id].ul_Bandwidth); // return total number of PRB - - /* HACK: let's remove the PUCCH from available RBs - * we suppose PUCCH size is: - * - for 25 RBs: 1 RB (top and bottom of ressource grid) - * - for 50: 2 RBs - * - for 100: 3 RBs - * This is totally arbitrary and might even be wrong. - * We suppose 'first_rb[]' has been correctly populated by the caller, - * so we only remove the top part of the resource grid. - */ - switch (n_rb_ul_tab[CC_id]) { - case 25: - n_rb_ul_tab[CC_id] -= 1; - break; - - case 50: - n_rb_ul_tab[CC_id] -= 2; - break; - - case 100: - n_rb_ul_tab[CC_id] -= 3; - break; - - default: - LOG_E(MAC, "RBs setting not handled. Todo.\n"); - exit(1); - } - - UE_list->first_rb_offset[CC_id][slice_idx] = cmin(n_rb_ul_tab[CC_id], sli->ul[slice_idx].first_rb); - } - /* * ULSCH preprocessor: set UE_template-> * pre_allocated_nb_rb_ul[slice_idx] * pre_assigned_mcs_ul * pre_allocated_rb_table_index_ul */ - ulsch_scheduler_pre_processor(module_idP, slice_idx, frameP, subframeP, sched_frame, sched_subframeP, first_rb); - - for (CC_id = 0; CC_id < RC.nb_mac_CC[module_idP]; CC_id++) { - first_rb_slice[CC_id] = first_rb[CC_id] + UE_list->first_rb_offset[CC_id][slice_idx]; - } + ulsch_scheduler_pre_processor(module_idP, CC_id, frameP, subframeP, sched_frame, sched_subframeP); - // loop over all active UEs until end of function - for (int UE_id = UE_list->head_ul; UE_id >= 0; UE_id = UE_list->next_ul[UE_id]) { - if (!ue_ul_slice_membership(module_idP, UE_id, slice_idx)) { + for (int UE_id = UE_info->list.head; UE_id >= 0; UE_id = UE_info->list.next[UE_id]) { + if (UE_info->UE_template[CC_id][UE_id].rach_resource_type > 0) continue; - } - - if (UE_list->UE_template[UE_PCCID(module_idP, UE_id)][UE_id].rach_resource_type > 0) continue; // don't schedule if Msg5 is not received yet - if (UE_list->UE_template[UE_PCCID(module_idP, UE_id)][UE_id].configured == FALSE) { - LOG_D(MAC, "[eNB %d] frame %d, subframe %d, UE %d: not configured, skipping UE scheduling \n", + if (UE_info->UE_template[CC_id][UE_id].configured == FALSE) { + LOG_D(MAC, + "[eNB %d] frame %d, subframe %d, UE %d: not configured, skipping " + "UE scheduling \n", module_idP, frameP, subframeP, @@ -1404,10 +1323,11 @@ schedule_ulsch_rnti(module_id_t module_idP, continue; } - rnti = UE_RNTI(module_idP, UE_id); + const rnti_t rnti = UE_RNTI(module_idP, UE_id); if (rnti == NOT_A_RNTI) { - LOG_W(MAC, "[eNB %d] frame %d, subframe %d, UE %d: no RNTI \n", + LOG_W(MAC, + "[eNB %d] frame %d, subframe %d, UE %d: no RNTI \n", module_idP, frameP, subframeP, @@ -1415,485 +1335,509 @@ schedule_ulsch_rnti(module_id_t module_idP, continue; } - // loop over all active UL CC_ids for this UE until end of function - for (int n = 0; n < UE_list->numactiveULCCs[UE_id]; n++) { - /* This is the actual CC_id in the list */ - CC_id = UE_list->ordered_ULCCids[n][UE_id]; - UE_template_ptr = &(UE_list->UE_template[CC_id][UE_id]); - UE_sched_ctrl_ptr = &(UE_list->UE_sched_ctrl[UE_id]); - harq_pid = subframe2harqpid(&cc[CC_id], sched_frame, sched_subframeP); - round_index = UE_sched_ctrl_ptr->round_UL[CC_id][harq_pid]; - AssertFatal(round_index < 8, "round %d > 7 for UE %d/%x\n", - round_index, - UE_id, - rnti); - LOG_D(MAC, "[eNB %d] frame %d subframe %d (sched_frame %d, sched_subframe %d), Checking PUSCH %d for UE %d/%x CC %d : aggregation level %d, N_RB_UL %d\n", - module_idP, - frameP, - subframeP, - sched_frame, - sched_subframeP, - harq_pid, - UE_id, - rnti, - CC_id, - aggregation, - n_rb_ul_tab[CC_id]); - /* Seems unused, only for debug */ - RC.eNB[module_idP][CC_id]->pusch_stats_BO[UE_id][(frameP * 10) + subframeP] = UE_template_ptr->estimated_ul_buffer; - VCD_SIGNAL_DUMPER_DUMP_VARIABLE_BY_NAME(VCD_SIGNAL_DUMPER_VARIABLES_UE0_BO, UE_template_ptr->estimated_ul_buffer); + UE_TEMPLATE *UE_template_ptr = &UE_info->UE_template[CC_id][UE_id]; + UE_sched_ctrl_t *UE_sched_ctrl_ptr = &UE_info->UE_sched_ctrl[UE_id]; + const uint8_t harq_pid = subframe2harqpid(&cc[CC_id], sched_frame, sched_subframeP); + uint8_t round_index = UE_sched_ctrl_ptr->round_UL[CC_id][harq_pid]; + AssertFatal(round_index < 8, + "round %d > 7 for UE %d/%x\n", + round_index, + UE_id, + rnti); - /* - * If there is information on BSR of DCCH, DTCH or if there is UL_SR, - * or if there is a packet to retransmit, or we want to schedule a periodic feedback - */ - if (UE_is_to_be_scheduled(module_idP, CC_id, UE_id) > 0 || round_index > 0) { - LOG_D(MAC, "[eNB %d][PUSCH %d] Frame %d subframe %d Scheduling UE %d/%x in round %d(SR %d,UL_inactivity timer %d,UL_failure timer %d,cqi_req_timer %d)\n", - module_idP, - harq_pid, - frameP, - subframeP, - UE_id, - rnti, - round_index, - UE_template_ptr->ul_SR, - UE_sched_ctrl_ptr->ul_inactivity_timer, - UE_sched_ctrl_ptr->ul_failure_timer, - UE_sched_ctrl_ptr->cqi_req_timer); - /* Reset the scheduling request */ - UE_template_ptr->ul_SR = 0; - status = mac_eNB_get_rrc_status(module_idP, rnti); - - /* New transmission */ - if (round_index == 0) { - /* Be sure that there are some free RBs */ - if (first_rb_slice[CC_id] >= n_rb_ul_tab[CC_id]) { - LOG_W(MAC, "[eNB %d] frame %d, subframe %d, UE %d/%x CC %d: dropping, not enough RBs\n", - module_idP, - frameP, - subframeP, - UE_id, - rnti, - CC_id); - continue; - } + /* Seems unused, only for debug */ + RC.eNB[module_idP][CC_id]->pusch_stats_BO[UE_id][(frameP * 10) + subframeP] = + UE_template_ptr->estimated_ul_buffer; + VCD_SIGNAL_DUMPER_DUMP_VARIABLE_BY_NAME(VCD_SIGNAL_DUMPER_VARIABLES_UE0_BO, + UE_template_ptr->estimated_ul_buffer); - /* Should format_flag be 2 in CCE_allocation_infeasible??? */ - /* This test seems to be way too long, can we provide an optimization? */ - if (CCE_allocation_infeasible(module_idP, CC_id, 1, subframeP, aggregation, rnti)) { - LOG_W(MAC, "[eNB %d] frame %d, subframe %d, UE %d/%x CC %d: not enough CCE\n", - module_idP, - frameP, - subframeP, - UE_id, - rnti, - CC_id); - continue; - } + if (UE_template_ptr->pre_allocated_nb_rb_ul < 1) + continue; - /* Handle the aperiodic CQI report */ - cqi_req = 0; - LOG_D(MAC,"RRC Conenction status %d, cqi_timer %d\n",status,UE_sched_ctrl_ptr->cqi_req_timer); - - if (status >= RRC_CONNECTED && UE_sched_ctrl_ptr->cqi_req_timer > 30) { - if (UE_sched_ctrl_ptr->cqi_received == 0) { - cqi_req = 1; - LOG_D(MAC, - "Setting CQI_REQ (timer %d)\n", - UE_sched_ctrl_ptr->cqi_req_timer); - - /* TDD: to be safe, do not ask CQI in special - * Subframes:36.213/7.2.3 CQI definition */ - if (cc[CC_id].tdd_Config) { - switch (cc[CC_id].tdd_Config->subframeAssignment) { - case 1: - if (subframeP == 1 || subframeP == 6) - cqi_req = 0; - break; - - case 3: - if (subframeP == 1) - cqi_req = 0; - break; - - default: - LOG_E(MAC, " TDD config not supported\n"); - break; - } - } + int dci_ul_pdu_idx = UE_template_ptr->pre_dci_ul_pdu_idx; + if (dci_ul_pdu_idx < 0) { + dci_ul_pdu_idx = CCE_try_allocate_ulsch( + module_idP, CC_id, subframeP, UE_id, UE_sched_ctrl_ptr->dl_cqi[CC_id]); + if (dci_ul_pdu_idx < 0) { + LOG_W(MAC ,"%4d.%d: Dropping UL Allocation for RNTI 0x%04x/UE %d\n", + frameP, subframeP, rnti, UE_id); + continue; + } + } - if (cqi_req == 1) { - UE_sched_ctrl_ptr->cqi_req_flag |= 1 << sched_subframeP; - } - } else { - LOG_D(MAC,"Clearing CQI request timer\n"); - UE_sched_ctrl_ptr->cqi_req_flag = 0; - UE_sched_ctrl_ptr->cqi_received = 0; - UE_sched_ctrl_ptr->cqi_req_timer = 0; - } - } + /* verify it is the right UE */ + hi_dci0_pdu = &hi_dci0_req_body->hi_dci0_pdu_list[dci_ul_pdu_idx]; + if (hi_dci0_pdu->pdu_type != NFAPI_HI_DCI0_DCI_PDU_TYPE + || hi_dci0_pdu->dci_pdu.dci_pdu_rel8.rnti != rnti) { + LOG_E(MAC, "illegal hi_dci0_pdu_list index %d for UE %d/RNTI %04x\n", + dci_ul_pdu_idx, + UE_id, + rnti); + continue; + } - /* Power control */ - /* - * Compute the expected ULSCH RX snr (for the stats) - * This is the normalized RX snr and this should be constant (regardless of mcs) - * Is not in dBm, unit from nfapi, converting to dBm - */ - snr = (5 * UE_sched_ctrl_ptr->pusch_snr[CC_id] - 640) / 10; - target_snr = mac->puSch10xSnr / 10; - /* - * This assumes accumulated tpc - * Make sure that we are only sending a tpc update once a frame, otherwise the control loop will freak out - */ - framex10psubframe = (UE_template_ptr->pusch_tpc_tx_frame * 10) + UE_template_ptr->pusch_tpc_tx_subframe; + LOG_D(MAC, + "[eNB %d][PUSCH %d] %d.%d Scheduling UE %d/%x in " + "round %d (SR %d, UL_inactivity timer %d, UL_failure timer " + "%d, cqi_req_timer %d)\n", + module_idP, + harq_pid, + frameP, + subframeP, + UE_id, + rnti, + round_index, + UE_template_ptr->ul_SR, + UE_sched_ctrl_ptr->ul_inactivity_timer, + UE_sched_ctrl_ptr->ul_failure_timer, + UE_sched_ctrl_ptr->cqi_req_timer); + + /* Reset the scheduling request */ + UE_template_ptr->ul_SR = 0; + const uint8_t status = mac_eNB_get_rrc_status(module_idP, rnti); + + /* Power control */ + /* + * Compute the expected ULSCH RX snr (for the stats) + * This is the normalized RX snr and this should be constant (regardless + * of mcs) Is not in dBm, unit from nfapi, converting to dBm + */ + const int32_t snr = (5 * UE_sched_ctrl_ptr->pusch_snr[CC_id] - 640) / 10; + const int32_t target_snr = mac->puSch10xSnr / 10; - if (((framex10psubframe + 10) <= (frameP * 10 + subframeP)) || // normal case - ((framex10psubframe > (frameP * 10 + subframeP)) && (((10240 - framex10psubframe + frameP * 10 + subframeP) >= 10)))) { //frame wrap-around - UE_template_ptr->pusch_tpc_tx_frame = frameP; - UE_template_ptr->pusch_tpc_tx_subframe = subframeP; + /* + * This assumes accumulated tpc + * Make sure that we are only sending a tpc update once a frame, otherwise + * the control loop will freak out + */ + const int32_t fx10psf = (UE_template_ptr->pusch_tpc_tx_frame * 10) + + UE_template_ptr->pusch_tpc_tx_subframe; + uint32_t tpc = 1; + if (((fx10psf + 10) <= (frameP * 10 + subframeP)) // normal case + || ((fx10psf > (frameP * 10 + subframeP)) + && (((10240 - fx10psf + frameP * 10 + subframeP) >= 10)))) { // frame wrap-around + UE_template_ptr->pusch_tpc_tx_frame = frameP; + UE_template_ptr->pusch_tpc_tx_subframe = subframeP; + + if (snr > target_snr + 4) { + tpc = 0; // -1 + tpc_accumulated--; + } else if (snr < target_snr - 4) { + tpc = 2; // +1 + tpc_accumulated++; + } + } + if (tpc != 1) { + LOG_D(MAC, + "[eNB %d] ULSCH scheduler: frame %d, subframe %d, harq_pid %d, " + "tpc %d, accumulated %d, snr/target snr %d/%d\n", + module_idP, + frameP, + subframeP, + harq_pid, + tpc, + tpc_accumulated, + snr, + target_snr); + } - if (snr > target_snr + 4) { - tpc = 0; // -1 - tpc_accumulated--; - } else if (snr < target_snr - 4) { - tpc = 2; // +1 - tpc_accumulated++; - } else { - tpc = 1; // 0 - } - } else { - tpc = 1; // 0 - } + /* New transmission */ + if (round_index == 0) { + /* Handle the aperiodic CQI report */ + uint32_t cqi_req = 0; + LOG_D(MAC, + "RRC Connection status %d, cqi_timer %d\n", + status, + UE_sched_ctrl_ptr->cqi_req_timer); + + if (status >= RRC_CONNECTED && UE_sched_ctrl_ptr->cqi_req_timer > 30) { + if (UE_sched_ctrl_ptr->cqi_received == 0) { + cqi_req = 1; + LOG_D(MAC, + "Setting CQI_REQ (timer %d)\n", + UE_sched_ctrl_ptr->cqi_req_timer); - if (tpc != 1) { - LOG_D(MAC, "[eNB %d] ULSCH scheduler: frame %d, subframe %d, harq_pid %d, tpc %d, accumulated %d, snr/target snr %d/%d\n", - module_idP, - frameP, - subframeP, - harq_pid, - tpc, - tpc_accumulated, - snr, - target_snr); - } + /* TDD: to be safe, do not ask CQI in special + * Subframes:36.213/7.2.3 CQI definition */ + if (cc[CC_id].tdd_Config) { + switch (cc[CC_id].tdd_Config->subframeAssignment) { + case 1: + if (subframeP == 1 || subframeP == 6) + cqi_req = 0; + break; - ndi = 1 - UE_template_ptr->oldNDI_UL[harq_pid]; // NDI: new data indicator - UE_template_ptr->oldNDI_UL[harq_pid] = ndi; - UE_list->eNB_UE_stats[CC_id][UE_id].snr = snr; - UE_list->eNB_UE_stats[CC_id][UE_id].target_snr = target_snr; - UE_template_ptr->mcs_UL[harq_pid] = cmin(UE_template_ptr->pre_assigned_mcs_ul, sli->ul[slice_idx].maxmcs); - UE_list->eNB_UE_stats[CC_id][UE_id].ulsch_mcs1= UE_template_ptr->mcs_UL[harq_pid]; - - /* CDRX */ - if (UE_sched_ctrl_ptr->cdrx_configured) { - UE_sched_ctrl_ptr->drx_inactivity_timer = 1; // reset drx inactivity timer when new transmission - VCD_SIGNAL_DUMPER_DUMP_VARIABLE_BY_NAME(VCD_SIGNAL_DUMPER_VARIABLES_DRX_INACTIVITY, (unsigned long) UE_sched_ctrl_ptr->drx_inactivity_timer); - UE_sched_ctrl_ptr->dci0_ongoing_timer = 1; // when set the UE_template_ptr->ul_SR cannot be set to 1, - // see definition for more information - } + case 3: + if (subframeP == 1) + cqi_req = 0; + break; - if (UE_template_ptr->pre_allocated_rb_table_index_ul >= 0) { - rb_table_index = UE_template_ptr->pre_allocated_rb_table_index_ul; - } else { - UE_template_ptr->mcs_UL[harq_pid] = 10; - rb_table_index = 5; // for PHR + default: + LOG_E(MAC, " TDD config not supported\n"); + break; + } } - UE_list->eNB_UE_stats[CC_id][UE_id].ulsch_mcs2 = UE_template_ptr->mcs_UL[harq_pid]; + if (cqi_req == 1) + UE_sched_ctrl_ptr->cqi_req_flag |= 1 << sched_subframeP; + } else { + LOG_D(MAC, "Clearing CQI request timer\n"); + UE_sched_ctrl_ptr->cqi_req_flag = 0; + UE_sched_ctrl_ptr->cqi_received = 0; + UE_sched_ctrl_ptr->cqi_req_timer = 0; + } + } - while (((rb_table[rb_table_index] > (n_rb_ul_tab[CC_id] - first_rb_slice[CC_id])) || - (rb_table[rb_table_index] > 45)) && (rb_table_index > 0)) { - rb_table_index--; - } + const uint8_t ndi = 1 - UE_template_ptr->oldNDI_UL[harq_pid]; // NDI: new data indicator + const uint8_t mcs = UE_template_ptr->pre_assigned_mcs_ul; + UE_template_ptr->oldNDI_UL[harq_pid] = ndi; + UE_info->eNB_UE_stats[CC_id][UE_id].snr = snr; + UE_info->eNB_UE_stats[CC_id][UE_id].target_snr = target_snr; + UE_template_ptr->mcs_UL[harq_pid] = mcs; + UE_info->eNB_UE_stats[CC_id][UE_id].ulsch_mcs1 = mcs; + + /* CDRX */ + if (UE_sched_ctrl_ptr->cdrx_configured) { + // reset drx inactivity timer when new transmission + UE_sched_ctrl_ptr->drx_inactivity_timer = 1; + VCD_SIGNAL_DUMPER_DUMP_VARIABLE_BY_NAME( + VCD_SIGNAL_DUMPER_VARIABLES_DRX_INACTIVITY, + (unsigned long)UE_sched_ctrl_ptr->drx_inactivity_timer); + // when set the UE_template_ptr->ul_SR cannot be set to 1, + // see definition for more information + UE_sched_ctrl_ptr->dci0_ongoing_timer = 1; + } - UE_template_ptr->TBS_UL[harq_pid] = get_TBS_UL(UE_template_ptr->mcs_UL[harq_pid], rb_table[rb_table_index]); - UE_list->eNB_UE_stats[CC_id][UE_id].total_rbs_used_rx += rb_table[rb_table_index]; - UE_list->eNB_UE_stats[CC_id][UE_id].ulsch_TBS = UE_template_ptr->TBS_UL[harq_pid]; - UE_list->eNB_UE_stats[CC_id][UE_id].total_ulsch_TBS += UE_template_ptr->TBS_UL[harq_pid]; - T(T_ENB_MAC_UE_UL_SCHEDULE, - T_INT(module_idP), - T_INT(CC_id), - T_INT(rnti), - T_INT(frameP), - T_INT(subframeP), - T_INT(harq_pid), - T_INT(UE_template_ptr->mcs_UL[harq_pid]), - T_INT(first_rb_slice[CC_id]), - T_INT(rb_table[rb_table_index]), - T_INT(UE_template_ptr->TBS_UL[harq_pid]), - T_INT(ndi)); - /* Store information for possible retransmission */ - UE_template_ptr->nb_rb_ul[harq_pid] = rb_table[rb_table_index]; - UE_template_ptr->first_rb_ul[harq_pid] = first_rb_slice[CC_id]; - UE_template_ptr->cqi_req[harq_pid] = cqi_req; - UE_sched_ctrl_ptr->ul_scheduled |= (1 << harq_pid); - - if (UE_id == UE_list->head) { - VCD_SIGNAL_DUMPER_DUMP_VARIABLE_BY_NAME(VCD_SIGNAL_DUMPER_VARIABLES_UE0_SCHEDULED, UE_sched_ctrl_ptr->ul_scheduled); - } + uint8_t rb_table_index = UE_template_ptr->pre_allocated_rb_table_index_ul; + + UE_info->eNB_UE_stats[CC_id][UE_id].ulsch_mcs2 = mcs; + + while (rb_table[rb_table_index] > 45 && rb_table_index > 0) + rb_table_index--; + + UE_template_ptr->TBS_UL[harq_pid] = get_TBS_UL(mcs, rb_table[rb_table_index]); + UE_info->eNB_UE_stats[CC_id][UE_id].total_rbs_used_rx += rb_table[rb_table_index]; + UE_info->eNB_UE_stats[CC_id][UE_id].ulsch_TBS = UE_template_ptr->TBS_UL[harq_pid]; + UE_info->eNB_UE_stats[CC_id][UE_id].total_ulsch_TBS += UE_template_ptr->TBS_UL[harq_pid]; + T(T_ENB_MAC_UE_UL_SCHEDULE, + T_INT(module_idP), + T_INT(CC_id), + T_INT(rnti), + T_INT(frameP), + T_INT(subframeP), + T_INT(harq_pid), + T_INT(mcs), + T_INT(rb_table[rb_table_index]), + T_INT(UE_template_ptr->TBS_UL[harq_pid]), + T_INT(ndi)); + /* Store information for possible retransmission */ + UE_template_ptr->nb_rb_ul[harq_pid] = rb_table[rb_table_index]; + UE_template_ptr->first_rb_ul[harq_pid] = UE_template_ptr->pre_first_nb_rb_ul; + UE_template_ptr->cqi_req[harq_pid] = cqi_req; + UE_sched_ctrl_ptr->ul_scheduled |= (1 << harq_pid); + + if (UE_id == UE_info->list.head) { + VCD_SIGNAL_DUMPER_DUMP_VARIABLE_BY_NAME( + VCD_SIGNAL_DUMPER_VARIABLES_UE0_SCHEDULED, + UE_sched_ctrl_ptr->ul_scheduled); + } - /* Adjust scheduled UL bytes by TBS, wait for UL sdus to do final update */ - LOG_D(MAC, "[eNB %d] CC_id %d UE %d/%x : adjusting scheduled_ul_bytes, old %d, TBS %d\n", - module_idP, - CC_id, - UE_id, - rnti, - UE_template_ptr->scheduled_ul_bytes, - UE_template_ptr->TBS_UL[harq_pid]); - UE_template_ptr->scheduled_ul_bytes += UE_template_ptr->TBS_UL[harq_pid]; - LOG_D(MAC, "scheduled_ul_bytes, new %d\n", - UE_template_ptr->scheduled_ul_bytes); - /* Cyclic shift for DM-RS */ - cshift = 0; // values from 0 to 7 can be used for mapping the cyclic shift (36.211 , Table 5.5.2.1.1-1) - /* Save it for a potential retransmission */ - UE_template_ptr->cshift[harq_pid] = cshift; - /* Setting DCI0 NFAPI struct */ - hi_dci0_pdu = &hi_dci0_req_body->hi_dci0_pdu_list[hi_dci0_req_body->number_of_dci + hi_dci0_req_body->number_of_hi]; - memset((void *) hi_dci0_pdu, 0,sizeof(nfapi_hi_dci0_request_pdu_t)); - hi_dci0_pdu->pdu_type = NFAPI_HI_DCI0_DCI_PDU_TYPE; - hi_dci0_pdu->pdu_size = 2 + sizeof(nfapi_hi_dci0_dci_pdu); - hi_dci0_pdu->dci_pdu.dci_pdu_rel8.tl.tag = NFAPI_HI_DCI0_REQUEST_DCI_PDU_REL8_TAG; - hi_dci0_pdu->dci_pdu.dci_pdu_rel8.dci_format = NFAPI_UL_DCI_FORMAT_0; - hi_dci0_pdu->dci_pdu.dci_pdu_rel8.aggregation_level = aggregation; - hi_dci0_pdu->dci_pdu.dci_pdu_rel8.rnti = rnti; - hi_dci0_pdu->dci_pdu.dci_pdu_rel8.transmission_power = 6000; - hi_dci0_pdu->dci_pdu.dci_pdu_rel8.resource_block_start = first_rb_slice[CC_id]; - hi_dci0_pdu->dci_pdu.dci_pdu_rel8.number_of_resource_block = rb_table[rb_table_index]; - hi_dci0_pdu->dci_pdu.dci_pdu_rel8.mcs_1 = UE_template_ptr->mcs_UL[harq_pid]; - hi_dci0_pdu->dci_pdu.dci_pdu_rel8.cyclic_shift_2_for_drms = cshift; - hi_dci0_pdu->dci_pdu.dci_pdu_rel8.frequency_hopping_enabled_flag = 0; - hi_dci0_pdu->dci_pdu.dci_pdu_rel8.new_data_indication_1 = ndi; - hi_dci0_pdu->dci_pdu.dci_pdu_rel8.tpc = tpc; - hi_dci0_pdu->dci_pdu.dci_pdu_rel8.cqi_csi_request = cqi_req; - hi_dci0_pdu->dci_pdu.dci_pdu_rel8.dl_assignment_index = UE_template_ptr->DAI_ul[sched_subframeP]; - hi_dci0_pdu->dci_pdu.dci_pdu_rel8.harq_pid = harq_pid; - hi_dci0_req_body->number_of_dci++; - hi_dci0_req_body->sfnsf = sfnsf_add_subframe(sched_frame, sched_subframeP, 0); - hi_dci0_req_body->tl.tag = NFAPI_HI_DCI0_REQUEST_BODY_TAG; - hi_dci0_req->sfn_sf = frameP << 4 | subframeP; - hi_dci0_req->header.message_id = NFAPI_HI_DCI0_REQUEST; - LOG_D(MAC, "[PUSCH %d] Frame %d, Subframe %d: Adding UL CONFIG.Request for UE %d/%x, ulsch_frame %d, ulsch_subframe %d\n", - harq_pid, + /* Adjust scheduled UL bytes by TBS, wait for UL sdus to do final update */ + LOG_D(MAC, + "[eNB %d] CC_id %d UE %d/%x : adjusting scheduled_ul_bytes, old " + "%d, TBS %d\n", + module_idP, + CC_id, + UE_id, + rnti, + UE_template_ptr->scheduled_ul_bytes, + UE_template_ptr->TBS_UL[harq_pid]); + UE_template_ptr->scheduled_ul_bytes += UE_template_ptr->TBS_UL[harq_pid]; + LOG_D(MAC, + "scheduled_ul_bytes, new %d\n", + UE_template_ptr->scheduled_ul_bytes); + /* Cyclic shift for DM-RS */ + /* Save it for a potential retransmission */ + UE_template_ptr->cshift[harq_pid] = cshift; + /* Setting DCI0 NFAPI struct */ + hi_dci0_pdu = &hi_dci0_req_body->hi_dci0_pdu_list[dci_ul_pdu_idx]; + hi_dci0_pdu->pdu_size = 2 + sizeof(nfapi_hi_dci0_dci_pdu); + hi_dci0_pdu->dci_pdu.dci_pdu_rel8.dci_format = NFAPI_UL_DCI_FORMAT_0; + hi_dci0_pdu->dci_pdu.dci_pdu_rel8.transmission_power = 6000; + hi_dci0_pdu->dci_pdu.dci_pdu_rel8.resource_block_start = UE_template_ptr->pre_first_nb_rb_ul; + hi_dci0_pdu->dci_pdu.dci_pdu_rel8.number_of_resource_block = + rb_table[rb_table_index]; + hi_dci0_pdu->dci_pdu.dci_pdu_rel8.mcs_1 = mcs; + hi_dci0_pdu->dci_pdu.dci_pdu_rel8.cyclic_shift_2_for_drms = cshift; + hi_dci0_pdu->dci_pdu.dci_pdu_rel8.frequency_hopping_enabled_flag = 0; + hi_dci0_pdu->dci_pdu.dci_pdu_rel8.new_data_indication_1 = ndi; + hi_dci0_pdu->dci_pdu.dci_pdu_rel8.tpc = tpc; + hi_dci0_pdu->dci_pdu.dci_pdu_rel8.cqi_csi_request = cqi_req; + hi_dci0_pdu->dci_pdu.dci_pdu_rel8.dl_assignment_index = + UE_template_ptr->DAI_ul[sched_subframeP]; + hi_dci0_pdu->dci_pdu.dci_pdu_rel8.harq_pid = harq_pid; + hi_dci0_req_body->sfnsf = + sfnsf_add_subframe(sched_frame, sched_subframeP, 0); + hi_dci0_req_body->tl.tag = NFAPI_HI_DCI0_REQUEST_BODY_TAG; + hi_dci0_req->sfn_sf = frameP << 4 | subframeP; + hi_dci0_req->header.message_id = NFAPI_HI_DCI0_REQUEST; + LOG_D(MAC, + "[PUSCH %d] Frame %d, Subframe %d: Adding UL CONFIG.Request for UE " + "%d/%x, ulsch_frame %d, ulsch_subframe %d\n", + harq_pid, + frameP, + subframeP, + UE_id, + rnti, + sched_frame, + sched_subframeP); + uint16_t ul_req_index = 0; + uint8_t dlsch_flag = 0; + + for (ul_req_index = 0; ul_req_index < ul_req_tmp_body->number_of_pdus; ul_req_index++) { + if (ul_req_tmp_body->ul_config_pdu_list[ul_req_index].pdu_type == NFAPI_UL_CONFIG_UCI_HARQ_PDU_TYPE && + ul_req_tmp_body->ul_config_pdu_list[ul_req_index].uci_harq_pdu.ue_information.ue_information_rel8.rnti == rnti) { + dlsch_flag = 1; + LOG_D(MAC, + "Frame %d, Subframe %d:rnti %x ul_req_index %d Switched UCI " + "HARQ to ULSCH HARQ(first)\n", frameP, subframeP, - UE_id, rnti, - sched_frame, - sched_subframeP); - ul_req_index = 0; - dlsch_flag = 0; - - for(ul_req_index = 0; ul_req_index < ul_req_tmp_body->number_of_pdus; ul_req_index++) { - if(ul_req_tmp_body->ul_config_pdu_list[ul_req_index].pdu_type == NFAPI_UL_CONFIG_UCI_HARQ_PDU_TYPE && - ul_req_tmp_body->ul_config_pdu_list[ul_req_index].uci_harq_pdu.ue_information.ue_information_rel8.rnti == rnti) { - dlsch_flag = 1; - LOG_D(MAC, "Frame %d, Subframe %d:rnti %x ul_req_index %d Switched UCI HARQ to ULSCH HARQ(first)\n", - frameP, - subframeP, - rnti, - ul_req_index); - break; - } - } + ul_req_index); + break; + } + } - /* Add UL_config PDUs */ - fill_nfapi_ulsch_config_request_rel8(&ul_req_tmp_body->ul_config_pdu_list[ul_req_index], - cqi_req, - cc, - UE_template_ptr->physicalConfigDedicated, - get_tmode(module_idP, CC_id, UE_id), - mac->ul_handle, - rnti, - first_rb_slice[CC_id], // resource_block_start - rb_table[rb_table_index], // number_of_resource_blocks - UE_template_ptr->mcs_UL[harq_pid], - cshift, // cyclic_shift_2_for_drms - 0, // frequency_hopping_enabled_flag - 0, // frequency_hopping_bits - ndi, // new_data_indication - 0, // redundancy_version - harq_pid, // harq_process_number - 0, // ul_tx_mode - 0, // current_tx_nb - 0, // n_srs - get_TBS_UL(UE_template_ptr->mcs_UL[harq_pid], rb_table[rb_table_index])); - - /* This is a BL/CE UE allocation */ - if (UE_template_ptr->rach_resource_type > 0) { - fill_nfapi_ulsch_config_request_emtc(&ul_req_tmp_body->ul_config_pdu_list[ul_req_index], - UE_template_ptr->rach_resource_type > 2 ? 2 : 1, - 1, // total_number_of_repetitions - 1, // repetition_number - (frameP * 10) + subframeP); - } + /* Add UL_config PDUs */ + fill_nfapi_ulsch_config_request_rel8( + &ul_req_tmp_body->ul_config_pdu_list[ul_req_index], + cqi_req, + cc, + UE_template_ptr->physicalConfigDedicated, + get_tmode(module_idP, CC_id, UE_id), + mac->ul_handle, + rnti, + UE_template_ptr->pre_first_nb_rb_ul, // resource_block_start + rb_table[rb_table_index], // number_of_resource_blocks + mcs, + cshift, // cyclic_shift_2_for_drms + 0, // frequency_hopping_enabled_flag + 0, // frequency_hopping_bits + ndi, // new_data_indication + 0, // redundancy_version + harq_pid, // harq_process_number + 0, // ul_tx_mode + 0, // current_tx_nb + 0, // n_srs + get_TBS_UL(mcs, rb_table[rb_table_index])); + + /* This is a BL/CE UE allocation */ + if (UE_template_ptr->rach_resource_type > 0) { + fill_nfapi_ulsch_config_request_emtc( + &ul_req_tmp_body->ul_config_pdu_list[ul_req_index], + UE_template_ptr->rach_resource_type > 2 ? 2 : 1, + 1, // total_number_of_repetitions + 1, // repetition_number + (frameP * 10) + subframeP); + } - if (dlsch_flag == 1) { - if (cqi_req == 1) { - ul_req_tmp_body->ul_config_pdu_list[ul_req_index].pdu_type = NFAPI_UL_CONFIG_ULSCH_CQI_HARQ_RI_PDU_TYPE; - ulsch_harq_information = &ul_req_tmp_body->ul_config_pdu_list[ul_req_index].ulsch_cqi_harq_ri_pdu.harq_information; - ul_req_tmp_body->ul_config_pdu_list[ul_req_index].ulsch_cqi_harq_ri_pdu.initial_transmission_parameters.initial_transmission_parameters_rel8.tl.tag = - NFAPI_UL_CONFIG_REQUEST_INITIAL_TRANSMISSION_PARAMETERS_REL8_TAG; - ul_req_tmp_body->ul_config_pdu_list[ul_req_index].ulsch_cqi_harq_ri_pdu.initial_transmission_parameters.initial_transmission_parameters_rel8.n_srs_initial = 0; // last symbol not punctured - ul_req_tmp_body->ul_config_pdu_list[ul_req_index].ulsch_cqi_harq_ri_pdu.initial_transmission_parameters.initial_transmission_parameters_rel8.initial_number_of_resource_blocks = - rb_table[rb_table_index]; - } else { - ul_req_tmp_body->ul_config_pdu_list[ul_req_index].pdu_type = NFAPI_UL_CONFIG_ULSCH_HARQ_PDU_TYPE; - ulsch_harq_information = &ul_req_tmp_body->ul_config_pdu_list[ul_req_index].ulsch_harq_pdu.harq_information; - ul_req_tmp_body->ul_config_pdu_list[ul_req_index].ulsch_harq_pdu.initial_transmission_parameters.initial_transmission_parameters_rel8.tl.tag = - NFAPI_UL_CONFIG_REQUEST_INITIAL_TRANSMISSION_PARAMETERS_REL8_TAG; - ul_req_tmp_body->ul_config_pdu_list[ul_req_index].ulsch_harq_pdu.initial_transmission_parameters.initial_transmission_parameters_rel8.n_srs_initial = 0; // last symbol not punctured - ul_req_tmp_body->ul_config_pdu_list[ul_req_index].ulsch_harq_pdu.initial_transmission_parameters.initial_transmission_parameters_rel8.initial_number_of_resource_blocks = rb_table[rb_table_index]; - } + if (dlsch_flag == 1) { + if (cqi_req == 1) { + ul_req_tmp_body->ul_config_pdu_list[ul_req_index].pdu_type = NFAPI_UL_CONFIG_ULSCH_CQI_HARQ_RI_PDU_TYPE; + ulsch_harq_information = &ul_req_tmp_body->ul_config_pdu_list[ul_req_index].ulsch_cqi_harq_ri_pdu.harq_information; + ul_req_tmp_body->ul_config_pdu_list[ul_req_index].ulsch_cqi_harq_ri_pdu.initial_transmission_parameters.initial_transmission_parameters_rel8.tl.tag = NFAPI_UL_CONFIG_REQUEST_INITIAL_TRANSMISSION_PARAMETERS_REL8_TAG; + ul_req_tmp_body->ul_config_pdu_list[ul_req_index].ulsch_cqi_harq_ri_pdu.initial_transmission_parameters.initial_transmission_parameters_rel8.n_srs_initial = 0; // last symbol not punctured + ul_req_tmp_body->ul_config_pdu_list[ul_req_index].ulsch_cqi_harq_ri_pdu.initial_transmission_parameters.initial_transmission_parameters_rel8.initial_number_of_resource_blocks = rb_table[rb_table_index]; + } else { + ul_req_tmp_body->ul_config_pdu_list[ul_req_index].pdu_type = NFAPI_UL_CONFIG_ULSCH_HARQ_PDU_TYPE; + ulsch_harq_information = &ul_req_tmp_body->ul_config_pdu_list[ul_req_index].ulsch_harq_pdu.harq_information; + ul_req_tmp_body->ul_config_pdu_list[ul_req_index].ulsch_harq_pdu.initial_transmission_parameters.initial_transmission_parameters_rel8.tl.tag = NFAPI_UL_CONFIG_REQUEST_INITIAL_TRANSMISSION_PARAMETERS_REL8_TAG; + ul_req_tmp_body->ul_config_pdu_list[ul_req_index].ulsch_harq_pdu.initial_transmission_parameters.initial_transmission_parameters_rel8.n_srs_initial = 0; // last symbol not punctured + ul_req_tmp_body->ul_config_pdu_list[ul_req_index].ulsch_harq_pdu.initial_transmission_parameters.initial_transmission_parameters_rel8.initial_number_of_resource_blocks = rb_table[rb_table_index]; + } - fill_nfapi_ulsch_harq_information(module_idP, CC_id,rnti, ulsch_harq_information,subframeP); - } else { - ul_req_tmp_body->number_of_pdus++; - } + fill_nfapi_ulsch_harq_information(module_idP, CC_id, rnti, ulsch_harq_information, subframeP); + } else { + ul_req_tmp_body->number_of_pdus++; + } - ul_req_tmp->header.message_id = NFAPI_UL_CONFIG_REQUEST; - ul_req_tmp_body->tl.tag = NFAPI_UL_CONFIG_REQUEST_BODY_TAG; - mac->ul_handle++; - ul_req_tmp->sfn_sf = sched_frame << 4 | sched_subframeP; - add_ue_ulsch_info(module_idP, CC_id, UE_id, subframeP, S_UL_SCHEDULED); - LOG_D(MAC, "[eNB %d] CC_id %d Frame %d, subframeP %d: Generated ULSCH DCI for next UE_id %d, format 0\n", - module_idP, - CC_id, - frameP, - subframeP, - UE_id); - LOG_D(MAC, "[PUSCH %d] SFN/SF:%04d%d UL_CFG:SFN/SF:%04d%d CQI:%d for UE %d/%x\n", - harq_pid, - frameP, - subframeP, - sched_frame, - sched_subframeP, - cqi_req, - UE_id, - rnti); - /* Increment first rb for next UE allocation */ - first_rb_slice[CC_id] += rb_table[rb_table_index]; - } else { // round_index > 0 => retransmission - T(T_ENB_MAC_UE_UL_SCHEDULE_RETRANSMISSION, - T_INT(module_idP), - T_INT(CC_id), - T_INT(rnti), - T_INT(frameP), - T_INT(subframeP), - T_INT(harq_pid), - T_INT(UE_template_ptr->mcs_UL[harq_pid]), - T_INT(UE_template_ptr->first_rb_ul[harq_pid]), - T_INT(UE_template_ptr->nb_rb_ul[harq_pid]), - T_INT(round_index)); - /* Add UL_config PDUs */ - LOG_D(MAC, "[PUSCH %d] Frame %d, Subframe %d: Adding UL CONFIG.Request for UE %d/%x, ulsch_frame %d, ulsch_subframe %d\n", - harq_pid, + ul_req_tmp->header.message_id = NFAPI_UL_CONFIG_REQUEST; + ul_req_tmp_body->tl.tag = NFAPI_UL_CONFIG_REQUEST_BODY_TAG; + mac->ul_handle++; + ul_req_tmp->sfn_sf = sched_frame << 4 | sched_subframeP; + add_ue_ulsch_info(module_idP, CC_id, UE_id, subframeP, S_UL_SCHEDULED); + LOG_D(MAC, + "[eNB %d] CC_id %d Frame %d, subframeP %d: Generated ULSCH DCI for " + "next UE_id %d, format 0\n", + module_idP, + CC_id, + frameP, + subframeP, + UE_id); + LOG_D( + MAC, + "[PUSCH %d] SFN/SF:%04d%d UL_CFG:SFN/SF:%04d%d CQI:%d for UE %d/%x\n", + harq_pid, + frameP, + subframeP, + sched_frame, + sched_subframeP, + cqi_req, + UE_id, + rnti); + } else { // round_index > 0 => retransmission + uint8_t mcs_rv = 0; + const int rvidx_tab[4] = {0, 2, 3, 1}; + uint8_t round_UL = UE_sched_ctrl_ptr->round_UL[CC_id][harq_pid]; + if (rvidx_tab[round_UL & 3] == 1) { + mcs_rv = 29; + } else if (rvidx_tab[round_UL & 3] == 2) { + mcs_rv = 30; + } else if (rvidx_tab[round_UL & 3] == 3) { + mcs_rv = 31; + } + + const uint16_t first_rb = UE_template_ptr->pre_first_nb_rb_ul; + const uint8_t nb_rb = UE_template_ptr->pre_allocated_nb_rb_ul; + if (first_rb != UE_template_ptr->first_rb_ul[harq_pid] + || nb_rb != UE_template_ptr->nb_rb_ul[harq_pid]) + LOG_D(MAC, + "%4d.%d UE %4x retx: change freq allocation to %d RBs start %d (from %d RBs start %d)\n", + frameP, + subframeP, + rnti, + nb_rb, + first_rb, + UE_template_ptr->nb_rb_ul[harq_pid], + UE_template_ptr->first_rb_ul[harq_pid]); + UE_template_ptr->first_rb_ul[harq_pid] = first_rb; + UE_template_ptr->nb_rb_ul[harq_pid] = nb_rb; + + T(T_ENB_MAC_UE_UL_SCHEDULE_RETRANSMISSION, + T_INT(module_idP), + T_INT(CC_id), + T_INT(rnti), + T_INT(frameP), + T_INT(subframeP), + T_INT(harq_pid), + T_INT(mcs_rv), + T_INT(first_rb), + T_INT(nb_rb), + T_INT(round_index)); + /* Add UL_config PDUs */ + LOG_D(MAC, + "[PUSCH %d] %4d.%d: Adding UL CONFIG.Request for UE " + "%d/%x, ulsch_frame %d, ulsch_subframe %d\n", + harq_pid, + frameP, + subframeP, + UE_id, + rnti, + sched_frame, + sched_subframeP); + + hi_dci0_pdu = &hi_dci0_req_body->hi_dci0_pdu_list[dci_ul_pdu_idx]; + hi_dci0_pdu->pdu_size = 2 + sizeof(nfapi_hi_dci0_dci_pdu); + hi_dci0_pdu->dci_pdu.dci_pdu_rel8.dci_format = NFAPI_UL_DCI_FORMAT_0; + hi_dci0_pdu->dci_pdu.dci_pdu_rel8.transmission_power = 6000; + hi_dci0_pdu->dci_pdu.dci_pdu_rel8.resource_block_start = first_rb; + hi_dci0_pdu->dci_pdu.dci_pdu_rel8.number_of_resource_block = nb_rb; + hi_dci0_pdu->dci_pdu.dci_pdu_rel8.mcs_1 = mcs_rv; + hi_dci0_pdu->dci_pdu.dci_pdu_rel8.cyclic_shift_2_for_drms = cshift; + hi_dci0_pdu->dci_pdu.dci_pdu_rel8.frequency_hopping_enabled_flag = 0; + hi_dci0_pdu->dci_pdu.dci_pdu_rel8.new_data_indication_1 = UE_template_ptr->oldNDI_UL[harq_pid]; + hi_dci0_pdu->dci_pdu.dci_pdu_rel8.tpc = tpc; + hi_dci0_pdu->dci_pdu.dci_pdu_rel8.cqi_csi_request = UE_template_ptr->cqi_req[harq_pid]; + hi_dci0_pdu->dci_pdu.dci_pdu_rel8.dl_assignment_index = UE_template_ptr->DAI_ul[sched_subframeP]; + hi_dci0_pdu->dci_pdu.dci_pdu_rel8.harq_pid = harq_pid; + + uint16_t ul_req_index = 0; + uint8_t dlsch_flag = 0; + uint32_t cqi_req = UE_template_ptr->cqi_req[harq_pid]; + for (ul_req_index = 0; ul_req_index < ul_req_tmp_body->number_of_pdus; ul_req_index++) { + if (ul_req_tmp_body->ul_config_pdu_list[ul_req_index].pdu_type == NFAPI_UL_CONFIG_UCI_HARQ_PDU_TYPE && + ul_req_tmp_body->ul_config_pdu_list[ul_req_index].uci_harq_pdu.ue_information.ue_information_rel8.rnti == rnti) { + dlsch_flag = 1; + LOG_D(MAC, + "Frame %d, Subframe %d:rnti %x ul_req_index %d Switched UCI " + "HARQ to ULSCH HARQ(first)\n", frameP, subframeP, - UE_id, rnti, - sched_frame, - sched_subframeP); - ul_req_index = 0; - dlsch_flag = 0; - cqi_req = UE_template_ptr->cqi_req[harq_pid]; - - for(ul_req_index = 0; ul_req_index < ul_req_tmp_body->number_of_pdus; ul_req_index++) { - if(ul_req_tmp_body->ul_config_pdu_list[ul_req_index].pdu_type == NFAPI_UL_CONFIG_UCI_HARQ_PDU_TYPE && - ul_req_tmp_body->ul_config_pdu_list[ul_req_index].uci_harq_pdu.ue_information.ue_information_rel8.rnti == rnti) { - dlsch_flag = 1; - LOG_D(MAC, "Frame %d, Subframe %d:rnti %x ul_req_index %d Switched UCI HARQ to ULSCH HARQ(first)\n", - frameP, - subframeP, - rnti, - ul_req_index); - break; - } - } + ul_req_index); + break; + } + } - fill_nfapi_ulsch_config_request_rel8(&ul_req_tmp_body->ul_config_pdu_list[ul_req_index], - cqi_req, - cc, - UE_template_ptr->physicalConfigDedicated, - get_tmode(module_idP, CC_id, UE_id), - mac->ul_handle, - rnti, - UE_template_ptr->first_rb_ul[harq_pid], // resource_block_start - UE_template_ptr->nb_rb_ul[harq_pid], // number_of_resource_blocks - UE_template_ptr->mcs_UL[harq_pid], - cshift, // cyclic_shift_2_for_drms - 0, // frequency_hopping_enabled_flag - 0, // frequency_hopping_bits - UE_template_ptr->oldNDI_UL[harq_pid], // new_data_indication - rvidx_tab[round_index & 3], // redundancy_version - harq_pid, // harq_process_number - 0, // ul_tx_mode - 0, // current_tx_nb - 0, // n_srs - UE_template_ptr->TBS_UL[harq_pid]); - - /* This is a BL/CE UE allocation */ - if (UE_template_ptr->rach_resource_type > 0) { - fill_nfapi_ulsch_config_request_emtc(&ul_req_tmp_body->ul_config_pdu_list[ul_req_index], - UE_template_ptr->rach_resource_type > 2 ? 2 : 1, - 1, // total_number_of_repetitions - 1, // repetition_number - (frameP * 10) + subframeP); - } + fill_nfapi_ulsch_config_request_rel8( + &ul_req_tmp_body->ul_config_pdu_list[ul_req_index], + cqi_req, + cc, + UE_template_ptr->physicalConfigDedicated, + get_tmode(module_idP, CC_id, UE_id), + mac->ul_handle, + rnti, + first_rb, // resource_block_start + nb_rb, // number_of_resource_blocks + mcs_rv, + cshift, // cyclic_shift_2_for_drms + 0, // frequency_hopping_enabled_flag + 0, // frequency_hopping_bits + UE_template_ptr->oldNDI_UL[harq_pid], // new_data_indication + rvidx_tab[round_index & 3], // redundancy_version + harq_pid, // harq_process_number + 0, // ul_tx_mode + 0, // current_tx_nb + 0, // n_srs + UE_template_ptr->TBS_UL[harq_pid]); + + /* This is a BL/CE UE allocation */ + if (UE_template_ptr->rach_resource_type > 0) { + fill_nfapi_ulsch_config_request_emtc( + &ul_req_tmp_body->ul_config_pdu_list[ul_req_index], + UE_template_ptr->rach_resource_type > 2 ? 2 : 1, + 1, // total_number_of_repetitions + 1, // repetition_number + (frameP * 10) + subframeP); + } - if(dlsch_flag == 1) { - if(cqi_req == 1) { - ul_req_tmp_body->ul_config_pdu_list[ul_req_index].pdu_type = NFAPI_UL_CONFIG_ULSCH_CQI_HARQ_RI_PDU_TYPE; - ulsch_harq_information = &ul_req_tmp_body->ul_config_pdu_list[ul_req_index].ulsch_cqi_harq_ri_pdu.harq_information; - ul_req_tmp_body->ul_config_pdu_list[ul_req_index].ulsch_cqi_harq_ri_pdu.initial_transmission_parameters.initial_transmission_parameters_rel8.tl.tag= - NFAPI_UL_CONFIG_REQUEST_INITIAL_TRANSMISSION_PARAMETERS_REL8_TAG; - ul_req_tmp_body->ul_config_pdu_list[ul_req_index].ulsch_cqi_harq_ri_pdu.initial_transmission_parameters.initial_transmission_parameters_rel8.n_srs_initial = 0; // last symbol not punctured - ul_req_tmp_body->ul_config_pdu_list[ul_req_index].ulsch_cqi_harq_ri_pdu.initial_transmission_parameters.initial_transmission_parameters_rel8.initial_number_of_resource_blocks = - UE_template_ptr->nb_rb_ul[harq_pid]; - } else { - ul_req_tmp_body->ul_config_pdu_list[ul_req_index].pdu_type = NFAPI_UL_CONFIG_ULSCH_HARQ_PDU_TYPE; - ulsch_harq_information = &ul_req_tmp_body->ul_config_pdu_list[ul_req_index].ulsch_harq_pdu.harq_information; - ul_req_tmp_body->ul_config_pdu_list[ul_req_index].ulsch_harq_pdu.initial_transmission_parameters.initial_transmission_parameters_rel8.tl.tag = - NFAPI_UL_CONFIG_REQUEST_INITIAL_TRANSMISSION_PARAMETERS_REL8_TAG; - ul_req_tmp_body->ul_config_pdu_list[ul_req_index].ulsch_harq_pdu.initial_transmission_parameters.initial_transmission_parameters_rel8.n_srs_initial = 0; // last symbol not punctured - ul_req_tmp_body->ul_config_pdu_list[ul_req_index].ulsch_harq_pdu.initial_transmission_parameters.initial_transmission_parameters_rel8.initial_number_of_resource_blocks = - UE_template_ptr->nb_rb_ul[harq_pid]; - } + if (dlsch_flag == 1) { + if (cqi_req == 1) { + ul_req_tmp_body->ul_config_pdu_list[ul_req_index].pdu_type = NFAPI_UL_CONFIG_ULSCH_CQI_HARQ_RI_PDU_TYPE; + ulsch_harq_information = &ul_req_tmp_body->ul_config_pdu_list[ul_req_index].ulsch_cqi_harq_ri_pdu.harq_information; + ul_req_tmp_body->ul_config_pdu_list[ul_req_index].ulsch_cqi_harq_ri_pdu.initial_transmission_parameters.initial_transmission_parameters_rel8.tl.tag = NFAPI_UL_CONFIG_REQUEST_INITIAL_TRANSMISSION_PARAMETERS_REL8_TAG; + ul_req_tmp_body->ul_config_pdu_list[ul_req_index].ulsch_cqi_harq_ri_pdu.initial_transmission_parameters.initial_transmission_parameters_rel8.n_srs_initial = 0; // last symbol not punctured + ul_req_tmp_body->ul_config_pdu_list[ul_req_index].ulsch_cqi_harq_ri_pdu.initial_transmission_parameters.initial_transmission_parameters_rel8.initial_number_of_resource_blocks = UE_template_ptr->nb_rb_ul[harq_pid]; + } else { + ul_req_tmp_body->ul_config_pdu_list[ul_req_index].pdu_type = NFAPI_UL_CONFIG_ULSCH_HARQ_PDU_TYPE; + ulsch_harq_information = &ul_req_tmp_body->ul_config_pdu_list[ul_req_index].ulsch_harq_pdu.harq_information; + ul_req_tmp_body->ul_config_pdu_list[ul_req_index].ulsch_harq_pdu.initial_transmission_parameters.initial_transmission_parameters_rel8.tl.tag = NFAPI_UL_CONFIG_REQUEST_INITIAL_TRANSMISSION_PARAMETERS_REL8_TAG; + ul_req_tmp_body->ul_config_pdu_list[ul_req_index].ulsch_harq_pdu.initial_transmission_parameters.initial_transmission_parameters_rel8.n_srs_initial = 0; // last symbol not punctured + ul_req_tmp_body->ul_config_pdu_list[ul_req_index].ulsch_harq_pdu.initial_transmission_parameters.initial_transmission_parameters_rel8.initial_number_of_resource_blocks = UE_template_ptr->nb_rb_ul[harq_pid]; + } - fill_nfapi_ulsch_harq_information(module_idP, CC_id,rnti, ulsch_harq_information, subframeP); - } else { - ul_req_tmp_body->number_of_pdus++; - } + fill_nfapi_ulsch_harq_information(module_idP, CC_id, rnti, ulsch_harq_information, subframeP); + } else { + ul_req_tmp_body->number_of_pdus++; + } - mac->ul_handle++; - ul_req_tmp_body->tl.tag = NFAPI_UL_CONFIG_REQUEST_BODY_TAG; - ul_req_tmp->sfn_sf = sched_frame<<4|sched_subframeP; - ul_req_tmp->header.message_id = NFAPI_UL_CONFIG_REQUEST; - LOG_D(MAC, "[PUSCH %d] Frame %d, Subframe %d: Adding UL CONFIG.Request for UE %d/%x, ulsch_frame %d, ulsch_subframe %d cqi_req %d\n", - harq_pid, - frameP, - subframeP, - UE_id, - rnti, - sched_frame, - sched_subframeP, - cqi_req); - - /* HACK: RBs used by retransmission have to be reserved. - * The current mechanism uses the notion of 'first_rb', so - * we skip all RBs below the ones retransmitted. This is - * not correct. Imagine only RB 23 is retransmitted, then all - * RBs < 23 will be marked unusable for new transmissions (case where round == 0). - * Note also that this code works only if the preprocessor orders - * UEs with retransmission with higher priority than UEs with new - * transmission. - * All this should be cleaned up properly. - */ - if (first_rb_slice[CC_id] < UE_template_ptr->first_rb_ul[harq_pid] + UE_template_ptr->nb_rb_ul[harq_pid]) - first_rb_slice[CC_id] = UE_template_ptr->first_rb_ul[harq_pid] + UE_template_ptr->nb_rb_ul[harq_pid]; - } // end of round > 0 - } // UE_is_to_be_scheduled - } // loop over all active CC_ids - } // loop over UE_ids + mac->ul_handle++; + ul_req_tmp_body->tl.tag = NFAPI_UL_CONFIG_REQUEST_BODY_TAG; + ul_req_tmp->sfn_sf = sched_frame << 4 | sched_subframeP; + ul_req_tmp->header.message_id = NFAPI_UL_CONFIG_REQUEST; + LOG_D(MAC, + "[PUSCH %d] Frame %d, Subframe %d: Adding UL CONFIG.Request for UE " + "%d/%x, ulsch_frame %d, ulsch_subframe %d cqi_req %d\n", + harq_pid, + frameP, + subframeP, + UE_id, + rnti, + sched_frame, + sched_subframeP, + cqi_req); + } // end of round > 0 + } // loop over UE_ids } @@ -1927,7 +1871,7 @@ void schedule_ulsch_rnti_emtc(module_id_t module_idP, eNB_MAC_INST *eNB = RC.mac[module_idP]; eNB_RRC_INST *rrc = RC.rrc[module_idP]; COMMON_channels_t *cc = eNB->common_channels; - UE_list_t *UE_list = &(eNB->UE_list); + UE_info_t *UE_info = &eNB->UE_info; UE_TEMPLATE *UE_template = NULL; UE_sched_ctrl_t *UE_sched_ctrl = NULL; uint8_t Total_Num_Rep_ULSCH,pusch_maxNumRepetitionCEmodeA_r13; @@ -1945,8 +1889,8 @@ void schedule_ulsch_rnti_emtc(module_id_t module_idP, nfapi_ul_config_request_pdu_t *ul_config_pdu_Rep; /* Loop over all active UEs */ - for (UE_id = UE_list->head_ul; UE_id >= 0; UE_id = UE_list->next_ul[UE_id]) { - UE_template = &(UE_list->UE_template[UE_PCCID(module_idP, UE_id)][UE_id]); + for (UE_id = UE_info->list.head; UE_id >= 0; UE_id = UE_info->list.next[UE_id]) { + UE_template = &UE_info->UE_template[UE_PCCID(module_idP, UE_id)][UE_id]; /* LTE-M device */ if (UE_template->rach_resource_type == 0) { @@ -1975,12 +1919,12 @@ void schedule_ulsch_rnti_emtc(module_id_t module_idP, } /* Loop over all active UL CC_ids for this UE */ - for (n = 0; n < UE_list->numactiveULCCs[UE_id]; n++) { + for (n = 0; n < UE_info->numactiveULCCs[UE_id]; n++) { /* This is the actual CC_id in the list */ - CC_id = UE_list->ordered_ULCCids[n][UE_id]; + CC_id = UE_info->ordered_ULCCids[n][UE_id]; N_RB_UL = to_prb(cc[CC_id].ul_Bandwidth); - UE_template = &(UE_list->UE_template[CC_id][UE_id]); - UE_sched_ctrl = &UE_list->UE_sched_ctrl[UE_id]; + UE_template = &UE_info->UE_template[CC_id][UE_id]; + UE_sched_ctrl = &UE_info->UE_sched_ctrl[UE_id]; harq_pid = 0; round_UL = UE_sched_ctrl->round_UL[CC_id][harq_pid]; AssertFatal(round_UL < 8,"round_UL %d > 7 for UE %d/%x\n", @@ -2028,6 +1972,12 @@ void schedule_ulsch_rnti_emtc(module_id_t module_idP, UE_sched_ctrl->cqi_req_timer); /* Reset the scheduling request */ emtc_active[CC_id] = 1; + cc[CC_id].vrb_map_UL[1] = 1; + cc[CC_id].vrb_map_UL[2] = 1; + cc[CC_id].vrb_map_UL[3] = 1; + cc[CC_id].vrb_map_UL[4] = 1; + cc[CC_id].vrb_map_UL[5] = 1; + cc[CC_id].vrb_map_UL[6] = 1; UE_template->ul_SR = 0; status = mac_eNB_get_rrc_status(module_idP,rnti); cqi_req = 0; @@ -2075,12 +2025,12 @@ void schedule_ulsch_rnti_emtc(module_id_t module_idP, UE_template->oldNDI_UL[harq_pid] = ndi; UE_template->mcs_UL[harq_pid] = 4; UE_template->TBS_UL[harq_pid] = get_TBS_UL(UE_template->mcs_UL[harq_pid], 6); - UE_list->eNB_UE_stats[CC_id][UE_id].snr = snr; - UE_list->eNB_UE_stats[CC_id][UE_id].target_snr = target_snr; - UE_list->eNB_UE_stats[CC_id][UE_id].ulsch_mcs1 = 4; - UE_list->eNB_UE_stats[CC_id][UE_id].ulsch_mcs2 = UE_template->mcs_UL[harq_pid]; - UE_list->eNB_UE_stats[CC_id][UE_id].total_rbs_used_rx += 6; - UE_list->eNB_UE_stats[CC_id][UE_id].ulsch_TBS = UE_template->TBS_UL[harq_pid]; + UE_info->eNB_UE_stats[CC_id][UE_id].snr = snr; + UE_info->eNB_UE_stats[CC_id][UE_id].target_snr = target_snr; + UE_info->eNB_UE_stats[CC_id][UE_id].ulsch_mcs1 = 4; + UE_info->eNB_UE_stats[CC_id][UE_id].ulsch_mcs2 = UE_template->mcs_UL[harq_pid]; + UE_info->eNB_UE_stats[CC_id][UE_id].total_rbs_used_rx += 6; + UE_info->eNB_UE_stats[CC_id][UE_id].ulsch_TBS = UE_template->TBS_UL[harq_pid]; T(T_ENB_MAC_UE_UL_SCHEDULE, T_INT(module_idP), T_INT(CC_id), @@ -2097,7 +2047,7 @@ void schedule_ulsch_rnti_emtc(module_id_t module_idP, UE_template->nb_rb_ul[harq_pid] = 6; UE_sched_ctrl->ul_scheduled |= (1 << harq_pid); - if (UE_id == UE_list->head) { + if (UE_id == UE_info->list.head) { VCD_SIGNAL_DUMPER_DUMP_VARIABLE_BY_NAME(VCD_SIGNAL_DUMPER_VARIABLES_UE0_SCHEDULED, UE_sched_ctrl->ul_scheduled); } diff --git a/openair2/LAYER2/MAC/mac.h b/openair2/LAYER2/MAC/mac.h index ac9819cfe283a1510505a5b99da6813dcbe7ce36..329e262c828e1008c4f74c712f91684ac1ec0ce4 100644 --- a/openair2/LAYER2/MAC/mac.h +++ b/openair2/LAYER2/MAC/mac.h @@ -824,11 +824,16 @@ typedef struct { uint16_t cshift[8]; // num_max_harq /// Number of Allocated RBs by the ulsch preprocessor - uint8_t pre_allocated_nb_rb_ul[MAX_NUM_SLICES]; + uint8_t pre_allocated_nb_rb_ul; + /// Start of Allocated RBs by the USLCH preprocessor + uint8_t pre_first_nb_rb_ul; /// index of Allocated RBs by the ulsch preprocessor int8_t pre_allocated_rb_table_index_ul; + /// index of allocated HI_DCI0 + int pre_dci_ul_pdu_idx; + /// total allocated RBs int8_t total_allocated_rbs; @@ -852,10 +857,10 @@ typedef struct { // Logical channel info for link with RLC - /// LCGID mapping + /// LCGID mapping (UL) long lcgidmap[11]; - ///UE logical channel priority + ///UE logical channel priority (UL) long lcgidpriority[11]; /// phr information @@ -913,31 +918,12 @@ typedef struct { /*! \brief scheduling control information set through an API (not used)*/ typedef struct { - ///UL transmission bandwidth in RBs - uint8_t ul_bandwidth[MAX_NUM_LCID]; - ///DL transmission bandwidth in RBs - uint8_t dl_bandwidth[MAX_NUM_LCID]; - - //To do GBR bearer - uint8_t min_ul_bandwidth[MAX_NUM_LCID]; - - uint8_t min_dl_bandwidth[MAX_NUM_LCID]; - - ///aggregated bit rate of non-gbr bearer per UE - uint64_t ue_AggregatedMaximumBitrateDL; - ///aggregated bit rate of non-gbr bearer per UE - uint64_t ue_AggregatedMaximumBitrateUL; - ///CQI scheduling interval in subframes. - uint16_t cqiSchedInterval; - ///Contention resolution timer used during random access - uint8_t mac_ContentionResolutionTimer; - - uint16_t max_rbs_allowed_slice[NFAPI_CC_MAX][MAX_NUM_SLICES]; - uint16_t max_rbs_allowed_slice_uplink[NFAPI_CC_MAX][MAX_NUM_SLICES]; - - uint8_t max_mcs[MAX_NUM_LCID]; - - uint16_t priority[MAX_NUM_LCID]; + /// number of active DL LCs + uint8_t dl_lc_num; + /// order in which DLSCH scheduler should allocate LCs + uint8_t dl_lc_ids[MAX_NUM_LCID]; + /// number of bytes to schedule for each LC + uint32_t dl_lc_bytes[MAX_NUM_LCID]; // resource scheduling information @@ -950,6 +936,7 @@ typedef struct { uint8_t dl_pow_off[NFAPI_CC_MAX]; uint16_t pre_nb_available_rbs[NFAPI_CC_MAX]; unsigned char rballoc_sub_UE[NFAPI_CC_MAX][N_RBG_MAX]; + int pre_dci_dl_pdu_idx; uint16_t ta_timer; int16_t ta_update; uint16_t ul_consecutive_errors; @@ -1130,7 +1117,15 @@ typedef struct { uint8_t sb_size; uint8_t nb_active_sb; } SBMAP_CONF; -/*! \brief UE list used by eNB to order UEs/CC for scheduling*/ + +/*! \brief UE_list_t is a "list" of users within UE_info_t. Especial useful in + * the scheduler and to keep "classes" of users. */ +typedef struct { + int head; + int next[MAX_MOBILES_PER_ENB]; +} UE_list_t; + +/*! \brief UE info used by eNB to order UEs/CC for scheduling*/ typedef struct { DLSCH_PDU DLSCH_pdu[NFAPI_CC_MAX][2][MAX_MOBILES_PER_ENB]; @@ -1152,21 +1147,13 @@ typedef struct { eNB_UE_STATS eNB_UE_stats[NFAPI_CC_MAX][MAX_MOBILES_PER_ENB]; /// scheduling control info UE_sched_ctrl_t UE_sched_ctrl[MAX_MOBILES_PER_ENB]; - int next[MAX_MOBILES_PER_ENB]; - int head; - int next_ul[MAX_MOBILES_PER_ENB]; - int head_ul; - int avail; + UE_list_t list; int num_UEs; boolean_t active[MAX_MOBILES_PER_ENB]; /// Sorting criteria for the UE list in the MAC preprocessor uint16_t sorting_criteria[MAX_NUM_SLICES][CR_NUM]; - uint16_t first_rb_offset[NFAPI_CC_MAX][MAX_NUM_SLICES]; - - int assoc_dl_slice_idx[MAX_MOBILES_PER_ENB]; - int assoc_ul_slice_idx[MAX_MOBILES_PER_ENB]; -} UE_list_t; +} UE_info_t; /*! \brief deleting control information*/ typedef struct { @@ -1184,20 +1171,6 @@ typedef struct { int tail_freelist; ///the tail position of the delete list } UE_free_list_t; -/// Structure for saving the output of each pre_processor instance -typedef struct { - uint16_t nb_rbs_required[NFAPI_CC_MAX][MAX_MOBILES_PER_ENB]; - uint16_t nb_rbs_accounted[NFAPI_CC_MAX][MAX_MOBILES_PER_ENB]; - uint16_t nb_rbs_remaining[NFAPI_CC_MAX][MAX_MOBILES_PER_ENB]; - uint8_t slice_allocation_mask[NFAPI_CC_MAX][N_RBG_MAX]; - uint8_t MIMO_mode_indicator[NFAPI_CC_MAX][N_RBG_MAX]; - - uint32_t bytes_lcid[MAX_MOBILES_PER_ENB][MAX_NUM_LCID]; - uint32_t wb_pmi[NFAPI_CC_MAX][MAX_MOBILES_PER_ENB]; - uint8_t mcs[NFAPI_CC_MAX][MAX_MOBILES_PER_ENB]; - -} pre_processor_results_t; - /** * slice specific scheduler for the DL */ @@ -1289,12 +1262,18 @@ typedef struct { int n_ul; slice_sched_conf_ul_t ul[MAX_NUM_SLICES]; - pre_processor_results_t pre_processor_results[MAX_NUM_SLICES]; - /// common rb allocation list between slices uint8_t rballoc_sub[NFAPI_CC_MAX][N_RBG_MAX]; } slice_info_t; +/** + * describes contiguous RBs + */ +typedef struct { + int start; + int length; +} contig_rbs_t; + /*! \brief eNB common channels */ typedef struct { int physCellId; @@ -1414,7 +1393,7 @@ typedef struct eNB_MAC_INST_s { nfapi_ue_release_request_t UE_release_req; /// UL handle uint32_t ul_handle; - UE_list_t UE_list; + UE_info_t UE_info; /// slice-related configuration slice_info_t slice_info; diff --git a/openair2/LAYER2/MAC/mac_proto.h b/openair2/LAYER2/MAC/mac_proto.h index 476fb6858482e93383222e71aaafb55d78499475..2cb86c25af221c003757dc961f51a8b7eea9c5f0 100644 --- a/openair2/LAYER2/MAC/mac_proto.h +++ b/openair2/LAYER2/MAC/mac_proto.h @@ -122,15 +122,14 @@ void schedule_ulsch(module_id_t module_idP, frame_t frameP, /** \brief ULSCH Scheduling per RNTI @param Mod_id Instance ID of eNB -@param slice_idx Slice instance index for this eNB +@param CC_id The component carrier to schedule @param frame Frame index @param subframe Subframe number on which to act @param sched_subframe Subframe number where PUSCH is transmitted (for DAI lookup) */ -void schedule_ulsch_rnti(module_id_t module_idP, int slice_idx, frame_t frameP, +void schedule_ulsch_rnti(module_id_t module_idP, int CC_id, frame_t frameP, sub_frame_t subframe, - unsigned char sched_subframe, - uint16_t *first_rb); + unsigned char sched_subframe); void schedule_ulsch_rnti_emtc(module_id_t module_idP, frame_t frameP, @@ -138,14 +137,6 @@ void schedule_ulsch_rnti_emtc(module_id_t module_idP, unsigned char sched_subframeP, int *emtc_active); -/** \brief Second stage of DLSCH scheduling, after schedule_SI, schedule_RA and schedule_dlsch have been called. This routine first allocates random frequency assignments for SI and RA SDUs using distributed VRB allocations and adds the corresponding DCI SDU to the DCI buffer for PHY. It then loops over the UE specific DCIs previously allocated and fills in the remaining DCI fields related to frequency allocation. It assumes localized allocation of type 0 (DCI.rah=0). The allocation is done for tranmission modes 1,2,4. -@param Mod_id Instance of eNB -@param frame Frame index -@param subframe Index of subframe -@param mbsfn_flag Indicates that this subframe is for MCH/MCCH -*/ -void fill_DLSCH_dci(module_id_t module_idP,frame_t frameP,sub_frame_t subframe,int *mbsfn_flag); - /** \brief UE specific DLSCH scheduling. Retrieves next ue to be schduled from round-robin scheduler and gets the appropriate harq_pid for the subframe from PHY. If the process is active and requires a retransmission, it schedules the retransmission with the same PRB count and MCS as the first transmission. Otherwise it consults RLC for DCCH/DTCH SDUs (status with maximum number of available PRBS), builds the MAC header (timing advance sent by default) and copies @param Mod_id Instance ID of eNB @param frame Frame index @@ -156,8 +147,10 @@ void fill_DLSCH_dci(module_id_t module_idP,frame_t frameP,sub_frame_t subframe,i void schedule_dlsch(module_id_t module_idP, frame_t frameP, sub_frame_t subframe, int *mbsfn_flag); -void schedule_ue_spec(module_id_t module_idP, int slice_idxP, - frame_t frameP,sub_frame_t subframe, int *mbsfn_flag); +void schedule_ue_spec(module_id_t module_idP, + int CC_id, + frame_t frameP, + sub_frame_t subframe); void schedule_ue_spec_br(module_id_t module_idP, frame_t frameP, sub_frame_t subframeP); @@ -192,7 +185,7 @@ void add_msg3(module_id_t module_idP, int CC_id, RA_t *ra, frame_t frameP, //main.c -void init_UE_list(UE_list_t *UE_list); +void init_UE_info(UE_info_t *UE_info); void init_slice_info(slice_info_t *sli); @@ -231,73 +224,9 @@ void clear_nfapi_information(eNB_MAC_INST *eNB, int CC_idP, void dlsch_scheduler_pre_processor(module_id_t module_idP, - int slice_idxP, + int CC_id, frame_t frameP, - sub_frame_t subframe, - int *mbsfn_flag, - uint8_t rballoc_sub[NFAPI_CC_MAX][N_RBG_MAX]); - -void dlsch_scheduler_pre_processor_reset(module_id_t module_idP, - int slice_idx, - frame_t frameP, - sub_frame_t subframeP, - int min_rb_unit[NFAPI_CC_MAX], - uint16_t nb_rbs_required[NFAPI_CC_MAX][MAX_MOBILES_PER_ENB], - uint8_t rballoc_sub[NFAPI_CC_MAX][N_RBG_MAX], - uint8_t MIMO_mode_indicator[NFAPI_CC_MAX][N_RBG_MAX], - int *mbsfn_flag); - -void dlsch_scheduler_pre_processor_partitioning(module_id_t Mod_id, - int slice_idx, - const uint8_t rbs_retx[NFAPI_CC_MAX]); - -void dlsch_scheduler_pre_processor_accounting(module_id_t Mod_id, - int slice_idx, - frame_t frameP, - sub_frame_t subframeP, - int min_rb_unit[NFAPI_CC_MAX], - uint16_t nb_rbs_required[NFAPI_CC_MAX][MAX_MOBILES_PER_ENB], - uint16_t nb_rbs_accounted[NFAPI_CC_MAX][MAX_MOBILES_PER_ENB]); - -void dlsch_scheduler_pre_processor_positioning(module_id_t Mod_id, - int slice_idx, - int min_rb_unit[NFAPI_CC_MAX], - uint16_t nb_rbs_required[NFAPI_CC_MAX][MAX_MOBILES_PER_ENB], - uint16_t nb_rbs_accounted[NFAPI_CC_MAX][MAX_MOBILES_PER_ENB], - uint16_t nb_rbs_remaining[NFAPI_CC_MAX][MAX_MOBILES_PER_ENB], - uint8_t rballoc_sub[NFAPI_CC_MAX][N_RBG_MAX], - uint8_t MIMO_mode_indicator[NFAPI_CC_MAX][N_RBG_MAX]); - -void dlsch_scheduler_pre_processor_intraslice_sharing(module_id_t Mod_id, - int slice_idx, - int min_rb_unit[NFAPI_CC_MAX], - uint16_t nb_rbs_required[NFAPI_CC_MAX][MAX_MOBILES_PER_ENB], - uint16_t nb_rbs_accounted[NFAPI_CC_MAX][MAX_MOBILES_PER_ENB], - uint16_t nb_rbs_remaining[NFAPI_CC_MAX][MAX_MOBILES_PER_ENB], - uint8_t rballoc_sub[NFAPI_CC_MAX][N_RBG_MAX], - uint8_t MIMO_mode_indicator[NFAPI_CC_MAX][N_RBG_MAX]); - -void slice_priority_sort(module_id_t Mod_id, int slice_list[MAX_NUM_SLICES]); - -void dlsch_scheduler_interslice_multiplexing(module_id_t Mod_id, - int frameP, - sub_frame_t subframeP, - uint8_t rballoc_sub[NFAPI_CC_MAX][N_RBG_MAX]); - -void dlsch_scheduler_qos_multiplexing(module_id_t Mod_id, - int frameP, - sub_frame_t subframeP); - -void dlsch_scheduler_pre_processor_allocate(module_id_t Mod_id, - int UE_id, - uint8_t CC_id, - int N_RBG, - int min_rb_unit, - uint16_t nb_rbs_required[NFAPI_CC_MAX][MAX_MOBILES_PER_ENB], - uint16_t nb_rbs_remaining[NFAPI_CC_MAX][MAX_MOBILES_PER_ENB], - uint8_t rballoc_sub[NFAPI_CC_MAX][N_RBG_MAX], - uint8_t slice_allocation_mask[NFAPI_CC_MAX][N_RBG_MAX], - uint8_t MIMO_mode_indicator[NFAPI_CC_MAX][N_RBG_MAX]); + sub_frame_t subframe); /* \brief Function to trigger the eNB scheduling procedure. It is called by PHY at the beginning of each subframe, \f$n$\f and generates all DLSCH allocations for subframe \f$n\f$ and ULSCH allocations for subframe \f$n+k$\f. @@ -484,10 +413,23 @@ boolean_t CCE_allocation_infeasible(int module_idP, int common_flag, int subframe, int aggregation, int rnti); +/* tries to allocate a CCE. If it succeeds, reserves NFAPI DCI and DLSCH config */ +int CCE_try_allocate_dlsch(int module_id, + int CC_id, + int subframe, + int UE_id, + uint8_t dl_cqi); + +/* tries to allocate a CCE for UL. If it succeeds, reserves the NFAPI DCI */ +int CCE_try_allocate_ulsch(int module_id, + int CC_id, + int subframe, + int UE_id, + uint8_t dl_cqi); void set_ue_dai(sub_frame_t subframeP, int UE_id, - uint8_t CC_id, uint8_t tdd_config, UE_list_t *UE_list); + uint8_t CC_id, uint8_t tdd_config, UE_info_t *UE_info); uint8_t frame_subframe2_dl_harq_pid(LTE_TDD_Config_t *tdd_Config, int abs_frameP, sub_frame_t subframeP); /** \brief First stage of PCH Scheduling. Gets a PCH SDU from RRC if available and computes the MCS required to transport it as a function of the SDU length. It assumes a length less than or equal to 64 bytes (MCS 6, 3 PRBs). @@ -510,14 +452,6 @@ uint8_t UE_is_to_be_scheduled(module_id_t module_idP, int CC_id, module_id_t schedule_next_ulue(module_id_t module_idP, int UE_id, sub_frame_t subframe); -/** \brief Round-robin scheduler for DLSCH traffic. -@param Mod_id Instance ID for eNB -@param subframe Subframe number on which to act -@returns UE index that is to be scheduled if needed/room -*/ -int schedule_next_dlue(module_id_t module_idP, int CC_id, - sub_frame_t subframe); - /* \brief Allocates a set of PRBS for a particular UE. This is a simple function for the moment, later it should process frequency-domain CQI information and/or PMI information. Currently it just returns the first PRBS that are available in the subframe based on the number requested. @param UE_id Index of UE on which to act @param nb_rb Number of PRBs allocated to UE by scheduler @@ -721,13 +655,13 @@ int mac_init(void); int add_new_ue(module_id_t Mod_id, int CC_id, rnti_t rnti, int harq_pid, uint8_t rach_resource_type); int rrc_mac_remove_ue(module_id_t Mod_id, rnti_t rntiP); -void store_dlsch_buffer(module_id_t Mod_id, int slice_idx, frame_t frameP, sub_frame_t subframeP); -void assign_rbs_required(module_id_t Mod_id, int slice_idx, frame_t frameP, sub_frame_t subframe, uint16_t nb_rbs_required[NFAPI_CC_MAX][MAX_MOBILES_PER_ENB], int min_rb_unit[NFAPI_CC_MAX]); +void store_dlsch_buffer(module_id_t Mod_id, int CC_id, frame_t frameP, sub_frame_t subframeP); -void swap_UEs(UE_list_t *listP, int nodeiP, int nodejP, int ul_flag); -int prev(UE_list_t *listP, int nodeP, int ul_flag); -void dump_ue_list(UE_list_t *listP, int ul_flag); -int UE_num_active_CC(UE_list_t *listP, int ue_idP); +int prev(UE_list_t *listP, int nodeP); +void add_ue_list(UE_list_t *listP, int UE_id); +int remove_ue_list(UE_list_t *listP, int UE_id); +void dump_ue_list(UE_list_t *listP); +int UE_num_active_CC(UE_info_t *listP, int ue_idP); int UE_PCCID(module_id_t mod_idP, int ue_idP); rnti_t UE_RNTI(module_id_t mod_idP, int ue_idP); @@ -739,20 +673,14 @@ void set_ul_DAI(int module_idP, int frameP, int subframeP); -void ulsch_scheduler_pre_processor(module_id_t module_idP, int slice_idx, int frameP, +void ulsch_scheduler_pre_processor(module_id_t module_idP, + int CC_id, + int frameP, sub_frame_t subframeP, int sched_frameP, - unsigned char sched_subframeP, - uint16_t *first_rb); -void store_ulsch_buffer(module_id_t module_idP, int frameP, - sub_frame_t subframeP); -void assign_max_mcs_min_rb(module_id_t module_idP, int slice_idx, int frameP, - sub_frame_t subframeP, uint16_t *first_rb); -void adjust_bsr_info(int buffer_occupancy, uint16_t TBS, - UE_TEMPLATE *UE_template); + unsigned char sched_subframeP); int phy_stats_exist(module_id_t Mod_id, int rnti); -void sort_UEs(module_id_t Mod_idP, int slice_idx, int frameP, sub_frame_t subframeP); /*! \fn UE_L2_state_t ue_scheduler(const module_id_t module_idP,const frame_t frameP, const sub_frame_t subframe, const lte_subframe_t direction,const uint8_t eNB_index) \brief UE scheduler where all the ue background tasks are done. This function performs the following: 1) Trigger PDCP every 5ms 2) Call RRC for link status return to PHY3) Perform SR/BSR procedures for scheduling feedback 4) Perform PHR procedures. @@ -913,8 +841,7 @@ void add_common_dci(DCI_PDU *DCI_pdu, uint8_t ra_flag); */ -uint32_t allocate_prbs_sub(int nb_rb, int N_RB_DL, int N_RBG, - uint8_t *rballoc); +uint32_t allocate_prbs_sub(int nb_rb, int N_RB_DL, int N_RBG, const uint8_t *rballoc); void update_ul_dci(module_id_t module_idP, uint8_t CC_id, rnti_t rnti, uint8_t dai, sub_frame_t subframe); @@ -1176,14 +1103,13 @@ void program_dlsch_acknak(module_id_t module_idP, int CC_idP, int UE_idP, frame_t frameP, sub_frame_t subframeP, uint8_t cce_idx); -void fill_nfapi_dlsch_config(eNB_MAC_INST *eNB, - nfapi_dl_config_request_body_t *dl_req, +void fill_nfapi_dlsch_config(nfapi_dl_config_request_pdu_t *dl_config_pdu, uint16_t length, int16_t pdu_index, uint16_t rnti, uint8_t resource_allocation_type, uint8_t virtual_resource_block_assignment_flag, - uint16_t resource_block_coding, + uint32_t resource_block_coding, uint8_t modulation, uint8_t redundancy_version, uint8_t transport_blocks, @@ -1277,11 +1203,6 @@ void pre_scd_nb_rbs_required( module_id_t module_idP, uint16_t nb_rbs_required[MAX_NUM_CCs][NUMBER_OF_UE_MAX]); #endif -/* Slice related functions */ -uint16_t nb_rbs_allowed_slice(float rb_percentage, int total_rbs); -int ue_dl_slice_membership(module_id_t mod_id, int UE_id, int slice_idx); -int ue_ul_slice_membership(module_id_t mod_id, int UE_id, int slice_idx); - /* DRX Configuration */ /* Configure local DRX timers and thresholds in UE context, following the drx_configuration input */ void eNB_Config_Local_DRX(instance_t Mod_id, rrc_mac_drx_config_req_t *rrc_mac_drx_config_req); diff --git a/openair2/LAYER2/MAC/main.c b/openair2/LAYER2/MAC/main.c index fe8980101dc34ddbc8e515de9d0b9f3d2e935f18..1a88623a1f3d31396cc362dbaff22a65caa279ea 100644 --- a/openair2/LAYER2/MAC/main.c +++ b/openair2/LAYER2/MAC/main.c @@ -43,26 +43,18 @@ extern RAN_CONTEXT_t RC; -void init_UE_list(UE_list_t *UE_list) +void init_UE_info(UE_info_t *UE_info) { int list_el; - UE_list->num_UEs = 0; - UE_list->head = -1; - UE_list->head_ul = -1; - UE_list->avail = 0; - for (list_el = 0; list_el < MAX_MOBILES_PER_ENB - 1; list_el++) { - UE_list->next[list_el] = list_el + 1; - UE_list->next_ul[list_el] = list_el + 1; - } - UE_list->next[list_el] = -1; - UE_list->next_ul[list_el] = -1; - memset(UE_list->DLSCH_pdu, 0, sizeof(UE_list->DLSCH_pdu)); - memset(UE_list->UE_template, 0, sizeof(UE_list->UE_template)); - memset(UE_list->eNB_UE_stats, 0, sizeof(UE_list->eNB_UE_stats)); - memset(UE_list->UE_sched_ctrl, 0, sizeof(UE_list->UE_sched_ctrl)); - memset(UE_list->active, 0, sizeof(UE_list->active)); - memset(UE_list->assoc_dl_slice_idx, 0, sizeof(UE_list->assoc_dl_slice_idx)); - memset(UE_list->assoc_ul_slice_idx, 0, sizeof(UE_list->assoc_ul_slice_idx)); + UE_info->num_UEs = 0; + UE_info->list.head = -1; + for (list_el = 0; list_el < MAX_MOBILES_PER_ENB; list_el++) + UE_info->list.next[list_el] = -1; + memset(UE_info->DLSCH_pdu, 0, sizeof(UE_info->DLSCH_pdu)); + memset(UE_info->UE_template, 0, sizeof(UE_info->UE_template)); + memset(UE_info->eNB_UE_stats, 0, sizeof(UE_info->eNB_UE_stats)); + memset(UE_info->UE_sched_ctrl, 0, sizeof(UE_info->UE_sched_ctrl)); + memset(UE_info->active, 0, sizeof(UE_info->active)); } void init_slice_info(slice_info_t *sli) @@ -137,7 +129,7 @@ void mac_top_init_eNB(void) mac[i]->if_inst = IF_Module_init(i); - init_UE_list(&mac[i]->UE_list); + init_UE_info(&mac[i]->UE_info); init_slice_info(&mac[i]->slice_info); } @@ -163,12 +155,12 @@ void mac_init_cell_params(int Mod_idP, int CC_idP) memset(&RC.mac[Mod_idP]->eNB_stats, 0, sizeof(eNB_STATS)); UE_template = - (UE_TEMPLATE *) & RC.mac[Mod_idP]->UE_list.UE_template[CC_idP][0]; + (UE_TEMPLATE *) & RC.mac[Mod_idP]->UE_info.UE_template[CC_idP][0]; for (j = 0; j < MAX_MOBILES_PER_ENB; j++) { UE_template[j].rnti = 0; // initiallize the eNB to UE statistics - memset(&RC.mac[Mod_idP]->UE_list.eNB_UE_stats[CC_idP][j], 0, + memset(&RC.mac[Mod_idP]->UE_info.eNB_UE_stats[CC_idP][j], 0, sizeof(eNB_UE_STATS)); } @@ -263,4 +255,4 @@ void *mac_enb_task(void *arg) } // end while return NULL; -} \ No newline at end of file +} diff --git a/openair2/LAYER2/MAC/pre_processor.c b/openair2/LAYER2/MAC/pre_processor.c index 13baeb8bae5d693f753010671d9e806a268a2a87..a032114022dde79673a4dfec436beb2834859332 100644 --- a/openair2/LAYER2/MAC/pre_processor.c +++ b/openair2/LAYER2/MAC/pre_processor.c @@ -50,109 +50,247 @@ extern RAN_CONTEXT_t RC; -#define DEBUG_eNB_SCHEDULER 1 +#define DEBUG_eNB_SCHEDULER #define DEBUG_HEADER_PARSING 1 -//#define DEBUG_PACKET_TRACE 1 -//#define ICIC 0 +int next_ue_list_looped(UE_list_t* list, int UE_id) { + if (UE_id < 0) + return list->head; + return list->next[UE_id] < 0 ? list->head : list->next[UE_id]; +} -void -sort_ue_ul(module_id_t module_idP, - int slice_idx, - int sched_frameP, - sub_frame_t sched_subframeP, - rnti_t *rntiTable); - -/* this function checks that get_eNB_UE_stats returns - * a non-NULL pointer for all the active CCs of an UE - */ -/* -int phy_stats_exist(module_id_t Mod_id, int rnti) -{ - int CC_id; - int i; - int UE_id = find_UE_id(Mod_id, rnti); - UE_list_t *UE_list = &RC.mac[Mod_id]->UE_list; - if (UE_id == -1) { - LOG_W(MAC, "[eNB %d] UE %x not found, should be there (in phy_stats_exist)\n", - Mod_id, rnti); - return 0; +int get_rbg_size_last(module_id_t Mod_id, int CC_id) { + const int RBGsize = get_min_rb_unit(Mod_id, CC_id); + const int N_RB_DL = to_prb(RC.mac[Mod_id]->common_channels[CC_id].mib->message.dl_Bandwidth); + if (N_RB_DL == 15 || N_RB_DL == 25 || N_RB_DL == 50 || N_RB_DL == 75) + return RBGsize - 1; + else + return RBGsize; +} + +int g_start_ue_dl = -1; +int round_robin_dl(module_id_t Mod_id, + int CC_id, + int frame, + int subframe, + UE_list_t *UE_list, + int max_num_ue, + int n_rbg_sched, + uint8_t *rbgalloc_mask) { + DevAssert(UE_list->head >= 0); + DevAssert(n_rbg_sched > 0); + const int N_RBG = to_rbg(RC.mac[Mod_id]->common_channels[CC_id].mib->message.dl_Bandwidth); + const int RBGsize = get_min_rb_unit(Mod_id, CC_id); + const int RBGlastsize = get_rbg_size_last(Mod_id, CC_id); + int num_ue_req = 0; + UE_info_t *UE_info = &RC.mac[Mod_id]->UE_info; + + int rb_required[MAX_MOBILES_PER_ENB]; // how much UEs request + memset(rb_required, 0, sizeof(rb_required)); + + int rbg = 0; + for (; !rbgalloc_mask[rbg]; rbg++) + ; /* fast-forward to first allowed RBG */ + + // Calculate the amount of RBs every UE wants to send. + for (int UE_id = UE_list->head; UE_id >= 0; UE_id = UE_list->next[UE_id]) { + // check whether there are HARQ retransmissions + const COMMON_channels_t *cc = &RC.mac[Mod_id]->common_channels[CC_id]; + const uint8_t harq_pid = frame_subframe2_dl_harq_pid(cc->tdd_Config, frame, subframe); + UE_sched_ctrl_t *ue_ctrl = &UE_info->UE_sched_ctrl[UE_id]; + const uint8_t round = ue_ctrl->round[CC_id][harq_pid]; + if (round != 8) { // retransmission: allocate + const int nb_rb = UE_info->UE_template[CC_id][UE_id].nb_rb[harq_pid]; + if (nb_rb == 0) + continue; + int nb_rbg = (nb_rb + (nb_rb % RBGsize)) / RBGsize; + // needs more RBGs than we can allocate + if (nb_rbg > n_rbg_sched) { + LOG_D(MAC, + "retransmission of UE %d needs more RBGs (%d) than we have (%d)\n", + UE_id, nb_rbg, n_rbg_sched); + continue; + } + // ensure that the number of RBs can be contained by the RBGs (!), i.e. + // if we allocate the last RBG this one should have the full RBGsize + if ((nb_rb % RBGsize) == 0 && nb_rbg == n_rbg_sched + && rbgalloc_mask[N_RBG - 1] && RBGlastsize != RBGsize) { + LOG_D(MAC, + "retransmission of UE %d needs %d RBs, but the last RBG %d is too small (%d, normal %d)\n", + UE_id, nb_rb, N_RBG - 1, RBGlastsize, RBGsize); + continue; + } + const uint8_t cqi = ue_ctrl->dl_cqi[CC_id]; + const int idx = CCE_try_allocate_dlsch(Mod_id, CC_id, subframe, UE_id, cqi); + if (idx < 0) + continue; // cannot allocate CCE + ue_ctrl->pre_dci_dl_pdu_idx = idx; + // retransmissions: directly allocate + n_rbg_sched -= nb_rbg; + ue_ctrl->pre_nb_available_rbs[CC_id] += nb_rb; + for (; nb_rbg > 0; rbg++) { + if (!rbgalloc_mask[rbg]) + continue; + ue_ctrl->rballoc_sub_UE[CC_id][rbg] = 1; + nb_rbg--; + } + LOG_D(MAC, + "%4d.%d n_rbg_sched %d after retransmission reservation for UE %d " + "round %d retx nb_rb %d pre_nb_available_rbs %d\n", + frame, subframe, n_rbg_sched, UE_id, round, + UE_info->UE_template[CC_id][UE_id].nb_rb[harq_pid], + ue_ctrl->pre_nb_available_rbs[CC_id]); + /* if there are no more RBG to give, return */ + if (n_rbg_sched <= 0) + return 0; + max_num_ue--; + /* if there are no UEs that can be allocated anymore, return */ + if (max_num_ue == 0) + return n_rbg_sched; + for (; !rbgalloc_mask[rbg]; rbg++) /* fast-forward */ ; + } else { + const int dlsch_mcs1 = cqi_to_mcs[UE_info->UE_sched_ctrl[UE_id].dl_cqi[CC_id]]; + UE_info->eNB_UE_stats[CC_id][UE_id].dlsch_mcs1 = dlsch_mcs1; + rb_required[UE_id] = + find_nb_rb_DL(dlsch_mcs1, + UE_info->UE_template[CC_id][UE_id].dl_buffer_total, + n_rbg_sched * RBGsize, + RBGsize); + if (rb_required[UE_id] > 0) + num_ue_req++; + LOG_D(MAC, + "%d/%d UE_id %d rb_required %d n_rbg_sched %d\n", + frame, + subframe, + UE_id, + rb_required[UE_id], + n_rbg_sched); + } + } + + if (num_ue_req == 0) + return n_rbg_sched; // no UE has a transmission + + // after allocating retransmissions: build list of UE to allocate. + // if start_UE does not exist anymore (detach etc), start at first UE + if (g_start_ue_dl == -1) + g_start_ue_dl = UE_list->head; + int UE_id = g_start_ue_dl; + UE_list_t UE_sched; + int rb_required_total = 0; + int num_ue_sched = 0; + max_num_ue = min(min(max_num_ue, num_ue_req), n_rbg_sched); + int *cur_UE = &UE_sched.head; + while (num_ue_sched < max_num_ue) { + while (rb_required[UE_id] == 0) + UE_id = next_ue_list_looped(UE_list, UE_id); + const uint8_t cqi = UE_info->UE_sched_ctrl[UE_id].dl_cqi[CC_id]; + const int idx = CCE_try_allocate_dlsch(Mod_id, CC_id, subframe, UE_id, cqi); + if (idx < 0) { + LOG_D(MAC, "cannot allocate CCE for UE %d, skipping\n", UE_id); + num_ue_req--; + max_num_ue = min(min(max_num_ue, num_ue_req), n_rbg_sched); + UE_id = next_ue_list_looped(UE_list, UE_id); // next candidate + continue; + } + UE_info->UE_sched_ctrl[UE_id].pre_dci_dl_pdu_idx = idx; + *cur_UE = UE_id; + cur_UE = &UE_sched.next[UE_id]; + rb_required_total += rb_required[UE_id]; + num_ue_sched++; + UE_id = next_ue_list_looped(UE_list, UE_id); // next candidate } - if (UE_list->numactiveCCs[UE_id] == 0) { - LOG_W(MAC, "[eNB %d] UE %x has no active CC (in phy_stats_exist)\n", - Mod_id, rnti); - return 0; + *cur_UE = -1; + + /* for one UE after the next: allocate resources */ + for (int UE_id = UE_sched.head; UE_id >= 0; + UE_id = next_ue_list_looped(&UE_sched, UE_id)) { + if (rb_required[UE_id] <= 0) + continue; + UE_sched_ctrl_t *ue_ctrl = &UE_info->UE_sched_ctrl[UE_id]; + ue_ctrl->rballoc_sub_UE[CC_id][rbg] = 1; + const int sRBG = rbg == N_RBG - 1 ? RBGlastsize : RBGsize; + ue_ctrl->pre_nb_available_rbs[CC_id] += sRBG; + rb_required[UE_id] -= sRBG; + rb_required_total -= sRBG; + if (rb_required_total <= 0) + break; + n_rbg_sched--; + if (n_rbg_sched <= 0) + break; + for (rbg++; !rbgalloc_mask[rbg]; rbg++) /* fast-forward */ ; } - for (i = 0; i < UE_list->numactiveCCs[UE_id]; i++) { - CC_id = UE_list->ordered_CCids[i][UE_id]; - if (mac_xface->get_eNB_UE_stats(Mod_id, CC_id, rnti) == NULL) - return 0; + + /* if not all UEs could be allocated in this round */ + if (num_ue_req > max_num_ue) { + /* go to the first one we missed */ + for (int i = 0; i < max_num_ue; ++i) + g_start_ue_dl = next_ue_list_looped(UE_list, g_start_ue_dl); + } else { + /* else, just start with the next UE next time */ + g_start_ue_dl = next_ue_list_looped(UE_list, g_start_ue_dl); } - return 1; + + return n_rbg_sched; } -*/ // This function stores the downlink buffer for all the logical channels void store_dlsch_buffer(module_id_t Mod_id, - int slice_idx, + int CC_id, frame_t frameP, sub_frame_t subframeP) { - int UE_id, lcid; - rnti_t rnti; - mac_rlc_status_resp_t rlc_status; - UE_list_t *UE_list = &RC.mac[Mod_id]->UE_list; - UE_TEMPLATE *UE_template; - - for (UE_id = 0; UE_id < MAX_MOBILES_PER_ENB; UE_id++) { - if (UE_list->active[UE_id] != TRUE) - continue; + UE_info_t *UE_info = &RC.mac[Mod_id]->UE_info; - if (!ue_dl_slice_membership(Mod_id, UE_id, slice_idx)) - continue; + for (int UE_id = UE_info->list.head; UE_id >= 0; UE_id = UE_info->list.next[UE_id]) { - UE_template = &UE_list->UE_template[UE_PCCID(Mod_id, UE_id)][UE_id]; - // clear logical channel interface variables + UE_TEMPLATE *UE_template = &UE_info->UE_template[CC_id][UE_id]; + UE_sched_ctrl_t *UE_sched_ctrl = &UE_info->UE_sched_ctrl[UE_id]; UE_template->dl_buffer_total = 0; UE_template->dl_pdus_total = 0; - for (lcid = 0; lcid < MAX_NUM_LCID; ++lcid) { - UE_template->dl_buffer_info[lcid] = 0; - UE_template->dl_pdus_in_buffer[lcid] = 0; - UE_template->dl_buffer_head_sdu_creation_time[lcid] = 0; - UE_template->dl_buffer_head_sdu_remaining_size_to_send[lcid] = 0; - } - - rnti = UE_RNTI(Mod_id, UE_id); - - for (lcid = 0; lcid < MAX_NUM_LCID; ++lcid) { // loop over all the logical channels - rlc_status = mac_rlc_status_ind(Mod_id, rnti, Mod_id, frameP, subframeP, - ENB_FLAG_YES, MBMS_FLAG_NO, lcid, 0,0, 0 - ); - UE_template->dl_buffer_info[lcid] = rlc_status.bytes_in_buffer; //storing the dlsch buffer for each logical channel + /* loop over all activated logical channels */ + for (int i = 0; i < UE_sched_ctrl->dl_lc_num; ++i) { + const int lcid = UE_sched_ctrl->dl_lc_ids[i]; + const mac_rlc_status_resp_t rlc_status = mac_rlc_status_ind(Mod_id, + UE_template->rnti, + Mod_id, + frameP, + subframeP, + ENB_FLAG_YES, + MBMS_FLAG_NO, + lcid, + 0, + 0 + ); + UE_template->dl_buffer_info[lcid] = rlc_status.bytes_in_buffer; UE_template->dl_pdus_in_buffer[lcid] = rlc_status.pdus_in_buffer; UE_template->dl_buffer_head_sdu_creation_time[lcid] = rlc_status.head_sdu_creation_time; UE_template->dl_buffer_head_sdu_creation_time_max = cmax(UE_template->dl_buffer_head_sdu_creation_time_max, rlc_status.head_sdu_creation_time); UE_template->dl_buffer_head_sdu_remaining_size_to_send[lcid] = rlc_status.head_sdu_remaining_size_to_send; UE_template->dl_buffer_head_sdu_is_segmented[lcid] = rlc_status.head_sdu_is_segmented; - UE_template->dl_buffer_total += UE_template->dl_buffer_info[lcid]; //storing the total dlsch buffer + UE_template->dl_buffer_total += UE_template->dl_buffer_info[lcid]; UE_template->dl_pdus_total += UE_template->dl_pdus_in_buffer[lcid]; -#ifdef DEBUG_eNB_SCHEDULER + /* update the number of bytes in the UE_sched_ctrl. The DLSCH will use + * this to request the corresponding data from the RLC, and this might be + * limited in the preprocessor */ + UE_sched_ctrl->dl_lc_bytes[i] = rlc_status.bytes_in_buffer; + +#ifdef DEBUG_eNB_SCHEDULER /* note for dl_buffer_head_sdu_remaining_size_to_send[lcid] : * 0 if head SDU has not been segmented (yet), else remaining size not already segmented and sent */ if (UE_template->dl_buffer_info[lcid] > 0) LOG_D(MAC, - "[eNB %d][SLICE %d] Frame %d Subframe %d : RLC status for UE %d in LCID%d: total of %d pdus and size %d, head sdu queuing time %d, remaining size %d, is segmeneted %d \n", - Mod_id, RC.mac[Mod_id]->slice_info.dl[slice_idx].id, frameP, + "[eNB %d] Frame %d Subframe %d : RLC status for UE %d in LCID%d: total of %d pdus and size %d, head sdu queuing time %d, remaining size %d, is segmeneted %d \n", + Mod_id, frameP, subframeP, UE_id, lcid, UE_template->dl_pdus_in_buffer[lcid], UE_template->dl_buffer_info[lcid], UE_template->dl_buffer_head_sdu_creation_time[lcid], UE_template->dl_buffer_head_sdu_remaining_size_to_send[lcid], UE_template->dl_buffer_head_sdu_is_segmented[lcid]); - #endif } @@ -165,1607 +303,565 @@ store_dlsch_buffer(module_id_t Mod_id, } } -int cqi2mcs(int cqi) { - return cqi_to_mcs[cqi]; -} -// This function returns the estimated number of RBs required by each UE for downlink scheduling +// This function assigns pre-available RBS to each UE in specified sub-bands before scheduling is done void -assign_rbs_required(module_id_t Mod_id, - int slice_idx, - frame_t frameP, - sub_frame_t subframe, - uint16_t nb_rbs_required[NFAPI_CC_MAX][MAX_MOBILES_PER_ENB], - int min_rb_unit[NFAPI_CC_MAX]) { - uint16_t TBS = 0; - int UE_id, n, i, j, CC_id, pCCid, tmp; - UE_list_t *UE_list = &RC.mac[Mod_id]->UE_list; - slice_info_t *sli = &RC.mac[Mod_id]->slice_info; - eNB_UE_STATS *eNB_UE_stats, *eNB_UE_stats_i, *eNB_UE_stats_j; - int N_RB_DL; - - // clear rb allocations across all CC_id - for (UE_id = 0; UE_id < MAX_MOBILES_PER_ENB; UE_id++) { - if (UE_list->active[UE_id] != TRUE) continue; - - if (!ue_dl_slice_membership(Mod_id, UE_id, slice_idx)) continue; - - pCCid = UE_PCCID(Mod_id, UE_id); - - //update CQI information across component carriers - for (n = 0; n < UE_list->numactiveCCs[UE_id]; n++) { - CC_id = UE_list->ordered_CCids[n][UE_id]; - eNB_UE_stats = &UE_list->eNB_UE_stats[CC_id][UE_id]; - // eNB_UE_stats->dlsch_mcs1 = cmin(cqi_to_mcs[UE_list->UE_sched_ctrl[UE_id].dl_cqi[CC_id]], sli->dl[slice_idx].maxmcs); - eNB_UE_stats->dlsch_mcs1 = cmin(cqi2mcs(UE_list->UE_sched_ctrl[UE_id].dl_cqi[CC_id]), sli->dl[slice_idx].maxmcs); - } - - // provide the list of CCs sorted according to MCS - for (i = 0; i < UE_list->numactiveCCs[UE_id]; ++i) { - eNB_UE_stats_i = &UE_list->eNB_UE_stats[UE_list->ordered_CCids[i][UE_id]][UE_id]; - - for (j = i + 1; j < UE_list->numactiveCCs[UE_id]; j++) { - DevAssert(j < NFAPI_CC_MAX); - eNB_UE_stats_j = &UE_list->eNB_UE_stats[UE_list->ordered_CCids[j][UE_id]][UE_id]; - - if (eNB_UE_stats_j->dlsch_mcs1 > eNB_UE_stats_i->dlsch_mcs1) { - tmp = UE_list->ordered_CCids[i][UE_id]; - UE_list->ordered_CCids[i][UE_id] = UE_list->ordered_CCids[j][UE_id]; - UE_list->ordered_CCids[j][UE_id] = tmp; - } - } - } - - if (UE_list->UE_template[pCCid][UE_id].dl_buffer_total > 0) { - LOG_D(MAC, "[preprocessor] assign RB for UE %d\n", UE_id); - - for (i = 0; i < UE_list->numactiveCCs[UE_id]; i++) { - CC_id = UE_list->ordered_CCids[i][UE_id]; - eNB_UE_stats = &UE_list->eNB_UE_stats[CC_id][UE_id]; - - if (eNB_UE_stats->dlsch_mcs1 == 0) { - nb_rbs_required[CC_id][UE_id] = 4; // don't let the TBS get too small - } else { - nb_rbs_required[CC_id][UE_id] = min_rb_unit[CC_id]; - } - - TBS = get_TBS_DL(eNB_UE_stats->dlsch_mcs1, nb_rbs_required[CC_id][UE_id]); - LOG_D(MAC, - "[preprocessor] start RB assignement for UE %d CC_id %d dl buffer %d (RB unit %d, MCS %d, TBS %d) \n", - UE_id, CC_id, - UE_list->UE_template[pCCid][UE_id].dl_buffer_total, - nb_rbs_required[CC_id][UE_id], - eNB_UE_stats->dlsch_mcs1, TBS); - N_RB_DL = to_prb(RC.mac[Mod_id]->common_channels[CC_id].mib->message.dl_Bandwidth); - UE_list->UE_sched_ctrl[UE_id].max_rbs_allowed_slice[CC_id][slice_idx] = - nb_rbs_allowed_slice(sli->dl[slice_idx].pct, N_RB_DL); - - /* calculating required number of RBs for each UE */ - while (TBS < UE_list->UE_template[pCCid][UE_id].dl_buffer_total) { - nb_rbs_required[CC_id][UE_id] += min_rb_unit[CC_id]; - - if (nb_rbs_required[CC_id][UE_id] > UE_list->UE_sched_ctrl[UE_id].max_rbs_allowed_slice[CC_id][slice_idx]) { - TBS = get_TBS_DL(eNB_UE_stats->dlsch_mcs1, UE_list->UE_sched_ctrl[UE_id].max_rbs_allowed_slice[CC_id][slice_idx]); - nb_rbs_required[CC_id][UE_id] = UE_list->UE_sched_ctrl[UE_id].max_rbs_allowed_slice[CC_id][slice_idx]; - break; - } - - TBS = get_TBS_DL(eNB_UE_stats->dlsch_mcs1, nb_rbs_required[CC_id][UE_id]); - } // end of while - - LOG_D(MAC, - "[eNB %d] Frame %d: UE %d on CC %d: RB unit %d, nb_required RB %d (TBS %d, mcs %d)\n", - Mod_id, frameP, UE_id, CC_id, min_rb_unit[CC_id], - nb_rbs_required[CC_id][UE_id], TBS, - eNB_UE_stats->dlsch_mcs1); - sli->pre_processor_results[slice_idx].mcs[CC_id][UE_id] = eNB_UE_stats->dlsch_mcs1; - } - } - } -} - - -// This function scans all CC_ids for a particular UE to find the maximum round index of its HARQ processes -int -maxround(module_id_t Mod_id, uint16_t rnti, int frame, - sub_frame_t subframe) { - uint8_t round, round_max = 0, UE_id; - int CC_id, harq_pid; - UE_list_t *UE_list = &RC.mac[Mod_id]->UE_list; - COMMON_channels_t *cc; - - for (CC_id = 0; CC_id < RC.nb_mac_CC[Mod_id]; CC_id++) { - cc = &RC.mac[Mod_id]->common_channels[CC_id]; - UE_id = find_UE_id(Mod_id, rnti); - - if(UE_id == -1) +dlsch_scheduler_pre_processor(module_id_t Mod_id, + int CC_id, + frame_t frameP, + sub_frame_t subframeP) { + UE_info_t *UE_info = &RC.mac[Mod_id]->UE_info; + const int N_RBG = to_rbg(RC.mac[Mod_id]->common_channels[CC_id].mib->message.dl_Bandwidth); + const int RBGsize = get_min_rb_unit(Mod_id, CC_id); + + store_dlsch_buffer(Mod_id, CC_id, frameP, subframeP); + + UE_list_t UE_to_sched; + UE_to_sched.head = -1; + for (int i = 0; i < MAX_MOBILES_PER_ENB; ++i) + UE_to_sched.next[i] = -1; + + int first = 1; + int last_UE_id = -1; + for (int UE_id = UE_info->list.head; UE_id >= 0; UE_id = UE_info->list.next[UE_id]) { + UE_sched_ctrl_t *ue_sched_ctrl = &UE_info->UE_sched_ctrl[UE_id]; + const UE_TEMPLATE *ue_template = &UE_info->UE_template[CC_id][UE_id]; + + /* initialize per-UE scheduling information */ + ue_sched_ctrl->pre_nb_available_rbs[CC_id] = 0; + ue_sched_ctrl->dl_pow_off[CC_id] = 2; + memset(ue_sched_ctrl->rballoc_sub_UE[CC_id], 0, sizeof(ue_sched_ctrl->rballoc_sub_UE[CC_id])); + ue_sched_ctrl->pre_dci_dl_pdu_idx = -1; + + const rnti_t rnti = UE_RNTI(Mod_id, UE_id); + if (rnti == NOT_A_RNTI) { + LOG_E(MAC, "UE %d has RNTI NOT_A_RNTI!\n", UE_id); continue; - - harq_pid = frame_subframe2_dl_harq_pid(cc->tdd_Config,frame,subframe); - round = UE_list->UE_sched_ctrl[UE_id].round[CC_id][harq_pid]; - - if (round > round_max) { - round_max = round; } - } - - return round_max; -} - -int -maxround_ul(module_id_t Mod_id, uint16_t rnti, int sched_frame, - sub_frame_t sched_subframe) { - uint8_t round, round_max = 0, UE_id; - int CC_id, harq_pid; - UE_list_t *UE_list = &RC.mac[Mod_id]->UE_list; - COMMON_channels_t *cc; - - for (CC_id = 0; CC_id < RC.nb_mac_CC[Mod_id]; CC_id++) { - cc = &RC.mac[Mod_id]->common_channels[CC_id]; - UE_id = find_UE_id(Mod_id, rnti); - - if(UE_id == -1) + if (UE_info->active[UE_id] != TRUE) { + LOG_E(MAC, "UE %d RNTI %x is NOT active!\n", UE_id, rnti); continue; - - harq_pid = subframe2harqpid(cc, sched_frame, sched_subframe); - round = UE_list->UE_sched_ctrl[UE_id].round_UL[CC_id][harq_pid]; - - if (round > round_max) { - round_max = round; } - } - - return round_max; -} - -// This function scans all CC_ids for a particular UE to find the maximum DL CQI -// it returns -1 if the UE is not found in PHY layer (get_eNB_UE_stats gives NULL) -int maxcqi(module_id_t Mod_id, int32_t UE_id) { - UE_list_t *UE_list = &RC.mac[Mod_id]->UE_list; - int CC_id, n; - int CQI = 0; - - for (n = 0; n < UE_list->numactiveCCs[UE_id]; n++) { - CC_id = UE_list->ordered_CCids[n][UE_id]; - - if (UE_list->UE_sched_ctrl[UE_id].dl_cqi[CC_id] > CQI) { - CQI = UE_list->UE_sched_ctrl[UE_id].dl_cqi[CC_id]; + if (ue_template->rach_resource_type > 0) { + LOG_D(MAC, + "UE %d is RACH resource type %d\n", + UE_id, + ue_template->rach_resource_type); + continue; } - } - - return CQI; -} - -long min_lcgidpriority(module_id_t Mod_id, int32_t UE_id) { - UE_list_t *UE_list = &RC.mac[Mod_id]->UE_list; - int i; - int pCC_id = UE_PCCID(Mod_id, UE_id); - long ret = UE_list->UE_template[pCC_id][UE_id].lcgidpriority[0]; - - for (i = 1; i < 11; ++i) { - if (UE_list->UE_template[pCC_id][UE_id].lcgidpriority[i] < ret) - ret = UE_list->UE_template[pCC_id][UE_id].lcgidpriority[i]; - } - - return ret; -} - -struct sort_ue_dl_params { - int Mod_idP; - int frameP; - int subframeP; - int slice_idx; -}; - -static int ue_dl_compare(const void *_a, const void *_b, void *_params) { - struct sort_ue_dl_params *params = _params; - UE_list_t *UE_list = &RC.mac[params->Mod_idP]->UE_list; - int i; - int slice_idx = params->slice_idx; - int UE_id1 = *(const int *) _a; - int UE_id2 = *(const int *) _b; - int rnti1 = UE_RNTI(params->Mod_idP, UE_id1); - int pCC_id1 = UE_PCCID(params->Mod_idP, UE_id1); - int round1 = maxround(params->Mod_idP, rnti1, params->frameP, params->subframeP); - int rnti2 = UE_RNTI(params->Mod_idP, UE_id2); - int pCC_id2 = UE_PCCID(params->Mod_idP, UE_id2); - int round2 = maxround(params->Mod_idP, rnti2, params->frameP, params->subframeP); - int cqi1 = maxcqi(params->Mod_idP, UE_id1); - int cqi2 = maxcqi(params->Mod_idP, UE_id2); - long lcgid1 = min_lcgidpriority(params->Mod_idP, UE_id1); - long lcgid2 = min_lcgidpriority(params->Mod_idP, UE_id2); - - for (i = 0; i < CR_NUM; ++i) { - switch (UE_list->sorting_criteria[slice_idx][i]) { - case CR_ROUND : - if (round1 > round2) - return -1; - - if (round1 < round2) - return 1; - - break; - - case CR_SRB12 : - if (UE_list->UE_template[pCC_id1][UE_id1].dl_buffer_info[1] + - UE_list->UE_template[pCC_id1][UE_id1].dl_buffer_info[2] > - UE_list->UE_template[pCC_id2][UE_id2].dl_buffer_info[1] + - UE_list->UE_template[pCC_id2][UE_id2].dl_buffer_info[2]) - return -1; - - if (UE_list->UE_template[pCC_id1][UE_id1].dl_buffer_info[1] + - UE_list->UE_template[pCC_id1][UE_id1].dl_buffer_info[2] < - UE_list->UE_template[pCC_id2][UE_id2].dl_buffer_info[1] + - UE_list->UE_template[pCC_id2][UE_id2].dl_buffer_info[2]) - return 1; - - break; - - case CR_HOL : - if (UE_list-> UE_template[pCC_id1][UE_id1].dl_buffer_head_sdu_creation_time_max > - UE_list-> UE_template[pCC_id2][UE_id2].dl_buffer_head_sdu_creation_time_max) - return -1; - - if (UE_list-> UE_template[pCC_id1][UE_id1].dl_buffer_head_sdu_creation_time_max < - UE_list-> UE_template[pCC_id2][UE_id2].dl_buffer_head_sdu_creation_time_max) - return 1; - - break; - - case CR_LC : - if (UE_list->UE_template[pCC_id1][UE_id1].dl_buffer_total > - UE_list->UE_template[pCC_id2][UE_id2].dl_buffer_total) - return -1; - - if (UE_list->UE_template[pCC_id1][UE_id1].dl_buffer_total < - UE_list->UE_template[pCC_id2][UE_id2].dl_buffer_total) - return 1; - - break; - - case CR_CQI : - if (cqi1 > cqi2) - return -1; - - if (cqi1 < cqi2) - return 1; - - break; - - case CR_LCP : - if (lcgid1 < lcgid2) - return -1; - - if (lcgid1 > lcgid2) - return 1; - - default : - break; + if (mac_eNB_get_rrc_status(Mod_id, rnti) < RRC_CONNECTED) { + LOG_D(MAC, "UE %d is not in RRC_CONNECTED\n", UE_id); + continue; } - } - - return 0; -} -void decode_sorting_policy(module_id_t Mod_idP, int slice_idx) { - int i; - UE_list_t *UE_list = &RC.mac[Mod_idP]->UE_list; - uint32_t policy = RC.mac[Mod_idP]->slice_info.dl[slice_idx].sorting; - uint32_t mask = 0x0000000F; - uint16_t criterion; - - for (i = 0; i < CR_NUM; ++i) { - criterion = (uint16_t) (policy >> 4 * (CR_NUM - 1 - i) & mask); - - if (criterion >= CR_NUM) { - LOG_W(MAC, - "Invalid criterion in slice index %d ID %d policy, revert to default policy \n", - slice_idx, RC.mac[Mod_idP]->slice_info.dl[slice_idx].id); - RC.mac[Mod_idP]->slice_info.dl[slice_idx].sorting = 0x12345; - break; + /* define UEs to schedule */ + if (first) { + first = 0; + UE_to_sched.head = UE_id; + } else { + UE_to_sched.next[last_UE_id] = UE_id; } - - UE_list->sorting_criteria[slice_idx][i] = criterion; + UE_to_sched.next[UE_id] = -1; + last_UE_id = UE_id; } -} -void decode_slice_positioning(module_id_t Mod_idP, - int slice_idx, - uint8_t slice_allocation_mask[NFAPI_CC_MAX][N_RBG_MAX]) { - uint8_t CC_id; - int RBG, start_frequency, end_frequency; - - // Init slice_alloc_mask - for (CC_id = 0; CC_id < RC.nb_mac_CC[Mod_idP]; ++CC_id) { - for (RBG = 0; RBG < N_RBG_MAX; ++RBG) { - slice_allocation_mask[CC_id][RBG] = 0; - } + if (UE_to_sched.head < 0) + return; + + uint8_t *vrb_map = RC.mac[Mod_id]->common_channels[CC_id].vrb_map; + uint8_t rbgalloc_mask[N_RBG_MAX]; + int n_rbg_sched = 0; + for (int i = 0; i < N_RBG; i++) { + // calculate mask: init to one + "AND" with vrb_map: + // if any RB in vrb_map is blocked (1), the current RBG will be 0 + rbgalloc_mask[i] = 1; + for (int j = 0; j < RBGsize; j++) + rbgalloc_mask[i] &= !vrb_map[RBGsize * i + j]; + n_rbg_sched += rbgalloc_mask[i]; } - start_frequency = RC.mac[Mod_idP]->slice_info.dl[slice_idx].pos_low; - end_frequency = RC.mac[Mod_idP]->slice_info.dl[slice_idx].pos_high; - - for (CC_id = 0; CC_id < RC.nb_mac_CC[Mod_idP]; ++CC_id) { - for (RBG = start_frequency; RBG <= end_frequency; ++RBG) { - slice_allocation_mask[CC_id][RBG] = 1; - } - } -} + round_robin_dl(Mod_id, + CC_id, + frameP, + subframeP, + &UE_to_sched, + 4, // max_num_ue + n_rbg_sched, + rbgalloc_mask); + + // the following block is meant for validation of the pre-processor to check + // whether all UE allocations are non-overlapping and is not necessary for + // scheduling functionality +#ifdef DEBUG_eNB_SCHEDULER + char t[26] = "_________________________"; + t[N_RBG] = 0; + for (int i = 0; i < N_RBG; i++) + for (int j = 0; j < RBGsize; j++) + if (vrb_map[RBGsize*i+j] != 0) + t[i] = 'x'; + int print = 0; + for (int UE_id = UE_info->list.head; UE_id >= 0; UE_id = UE_info->list.next[UE_id]) { + const UE_sched_ctrl_t *ue_sched_ctrl = &UE_info->UE_sched_ctrl[UE_id]; + + if (ue_sched_ctrl->pre_nb_available_rbs[CC_id] == 0) + continue; -//----------------------------------------------------------------------------- -/* - * This function sorts the UEs in order, depending on their dlsch buffer and CQI - */ -void sort_UEs(module_id_t Mod_idP, - int slice_idx, - int frameP, - sub_frame_t subframeP) -//----------------------------------------------------------------------------- -{ - int list[MAX_MOBILES_PER_ENB]; - int list_size = 0; - struct sort_ue_dl_params params = {Mod_idP, frameP, subframeP, slice_idx}; - UE_list_t *UE_list = &(RC.mac[Mod_idP]->UE_list); - UE_sched_ctrl_t *UE_scheduling_control = NULL; + LOG_D(MAC, + "%4d.%d UE%d %d RBs allocated, pre MCS %d\n", + frameP, + subframeP, + UE_id, + ue_sched_ctrl->pre_nb_available_rbs[CC_id], + UE_info->eNB_UE_stats[CC_id][UE_id].dlsch_mcs1); - for (int i = 0; i < MAX_MOBILES_PER_ENB; i++) { - UE_scheduling_control = &(UE_list->UE_sched_ctrl[i]); + print = 1; - /* Check CDRX configuration and if UE is in active time for this subframe */ - if (UE_scheduling_control->cdrx_configured == TRUE) { - if (UE_scheduling_control->in_active_time == FALSE) { + for (int i = 0; i < N_RBG; i++) { + if (!ue_sched_ctrl->rballoc_sub_UE[CC_id][i]) continue; + for (int j = 0; j < RBGsize; j++) { + if (vrb_map[RBGsize*i+j] != 0) { + LOG_I(MAC, "%4d.%d DL scheduler allocation list: %s\n", frameP, subframeP, t); + LOG_E(MAC, "%4d.%d: UE %d allocated at locked RB %d/RBG %d\n", frameP, + subframeP, UE_id, RBGsize * i + j, i); + } + vrb_map[RBGsize*i+j] = 1; } + t[i] = '0' + UE_id; } - - if (UE_list->active[i] == TRUE && - UE_RNTI(Mod_idP, i) != NOT_A_RNTI && - UE_list->UE_sched_ctrl[i].ul_out_of_sync != 1 && - ue_dl_slice_membership(Mod_idP, i, slice_idx)) { - list[list_size++] = i; - } - } - - decode_sorting_policy(Mod_idP, slice_idx); - qsort_r(list, list_size, sizeof(int), ue_dl_compare, ¶ms); - - if (list_size) { - for (int i = 0; i < list_size - 1; ++i) { - UE_list->next[list[i]] = list[i + 1]; - } - - UE_list->next[list[list_size - 1]] = -1; - UE_list->head = list[0]; - } else { - UE_list->head = -1; } + if (print) + LOG_D(MAC, "%4d.%d DL scheduler allocation list: %s\n", frameP, subframeP, t); +#endif } -void dlsch_scheduler_pre_processor_partitioning(module_id_t Mod_id, - int slice_idx, - const uint8_t rbs_retx[NFAPI_CC_MAX]) { - int UE_id, CC_id, N_RB_DL, i; - UE_list_t *UE_list = &RC.mac[Mod_id]->UE_list; - UE_sched_ctrl_t *ue_sched_ctl; - uint16_t available_rbs; - - for (UE_id = UE_list->head; UE_id >= 0; UE_id = UE_list->next[UE_id]) { - if (UE_RNTI(Mod_id, UE_id) == NOT_A_RNTI) continue; - - if (UE_list->UE_sched_ctrl[UE_id].ul_out_of_sync == 1) continue; - - if (!ue_dl_slice_membership(Mod_id, UE_id, slice_idx)) continue; - - ue_sched_ctl = &UE_list->UE_sched_ctrl[UE_id]; - - for (i = 0; i < UE_num_active_CC(UE_list, UE_id); ++i) { - CC_id = UE_list->ordered_CCids[i][UE_id]; - N_RB_DL = to_prb(RC.mac[Mod_id]->common_channels[CC_id].mib->message.dl_Bandwidth); - available_rbs = nb_rbs_allowed_slice(RC.mac[Mod_id]->slice_info.dl[slice_idx].pct, N_RB_DL); +/// ULSCH PRE_PROCESSOR - if (rbs_retx[CC_id] < available_rbs) - ue_sched_ctl->max_rbs_allowed_slice[CC_id][slice_idx] = available_rbs - rbs_retx[CC_id]; - else - ue_sched_ctl->max_rbs_allowed_slice[CC_id][slice_idx] = 0; - } +void calculate_max_mcs_min_rb(module_id_t mod_id, + int CC_id, + int bytes, + int phr, + int max_mcs, + int *mcs, + int max_rbs, + int *rb_index, + int *tx_power) { + const int Ncp = RC.mac[mod_id]->common_channels[CC_id].Ncp; + /* TODO shouldn't we consider the SRS or other quality indicators? */ + *mcs = max_mcs; + *rb_index = 2; + int tbs = get_TBS_UL(*mcs, rb_table[*rb_index]); + + // fixme: set use_srs flag + *tx_power = estimate_ue_tx_power(tbs * 8, rb_table[*rb_index], 0, Ncp, 0); + + /* find maximum MCS */ + while ((phr - *tx_power < 0 || tbs > bytes) && *mcs > 3) { + mcs--; + tbs = get_TBS_UL(*mcs, rb_table[*rb_index]); + *tx_power = estimate_ue_tx_power(tbs * 8, rb_table[*rb_index], 0, Ncp, 0); } -} -void dlsch_scheduler_pre_processor_accounting(module_id_t Mod_id, - int slice_idx, - frame_t frameP, - sub_frame_t subframeP, - int min_rb_unit[NFAPI_CC_MAX], - uint16_t nb_rbs_required[NFAPI_CC_MAX][MAX_MOBILES_PER_ENB], - uint16_t nb_rbs_accounted[NFAPI_CC_MAX][MAX_MOBILES_PER_ENB]) { - int UE_id, CC_id; - int i; - rnti_t rnti; - uint8_t harq_pid, round; - uint16_t available_rbs[NFAPI_CC_MAX]; - uint8_t rbs_retx[NFAPI_CC_MAX]; - uint16_t average_rbs_per_user[NFAPI_CC_MAX]; - int total_ue_count[NFAPI_CC_MAX]; - int ue_count_newtx[NFAPI_CC_MAX]; - int ue_count_retx[NFAPI_CC_MAX]; - //uint8_t ue_retx_flag[NFAPI_CC_MAX][MAX_MOBILES_PER_ENB]; - UE_list_t *UE_list = &RC.mac[Mod_id]->UE_list; - UE_sched_ctrl_t *ue_sched_ctl; - COMMON_channels_t *cc; - - // Reset - for (CC_id = 0; CC_id < RC.nb_mac_CC[Mod_id]; CC_id++) { - total_ue_count[CC_id] = 0; - ue_count_newtx[CC_id] = 0; - ue_count_retx[CC_id] = 0; - rbs_retx[CC_id] = 0; - average_rbs_per_user[CC_id] = 0; - available_rbs[CC_id] = 0; - //for (UE_id = 0; UE_id < NFAPI_CC_MAX; ++UE_id) { - // ue_retx_flag[CC_id][UE_id] = 0; - //} + /* find minimum necessary RBs */ + while (tbs < bytes + && *rb_index < 32 + && rb_table[*rb_index] < max_rbs + && phr - *tx_power > 0) { + (*rb_index)++; + tbs = get_TBS_UL(*mcs, rb_table[*rb_index]); + *tx_power = estimate_ue_tx_power(tbs * 8, rb_table[*rb_index], 0, Ncp, 0); } - // Find total UE count, and account the RBs required for retransmissions - for (UE_id = UE_list->head; UE_id >= 0; UE_id = UE_list->next[UE_id]) { - rnti = UE_RNTI(Mod_id, UE_id); + /* Decrease if we went to far in last iteration */ + if (rb_table[*rb_index] > max_rbs) + (*rb_index)--; - if (rnti == NOT_A_RNTI) continue; - - if (UE_list->UE_sched_ctrl[UE_id].ul_out_of_sync == 1) continue; - - if (!ue_dl_slice_membership(Mod_id, UE_id, slice_idx)) continue; - - for (i = 0; i < UE_num_active_CC(UE_list, UE_id); ++i) { - CC_id = UE_list->ordered_CCids[i][UE_id]; - ue_sched_ctl = &UE_list->UE_sched_ctrl[UE_id]; - cc = &RC.mac[Mod_id]->common_channels[CC_id]; - harq_pid = frame_subframe2_dl_harq_pid(cc->tdd_Config,frameP,subframeP); - round = ue_sched_ctl->round[CC_id][harq_pid]; - - if (nb_rbs_required[CC_id][UE_id] > 0) { - total_ue_count[CC_id]++; - } - - if (round != 8) { - nb_rbs_required[CC_id][UE_id] = UE_list->UE_template[CC_id][UE_id].nb_rb[harq_pid]; - rbs_retx[CC_id] += nb_rbs_required[CC_id][UE_id]; - ue_count_retx[CC_id]++; - //ue_retx_flag[CC_id][UE_id] = 1; - } else { - ue_count_newtx[CC_id]++; - } - } + // 1 or 2 PRB with cqi enabled does not work well + if (rb_table[*rb_index] < 3) { + *rb_index = 2; //3PRB } +} - // PARTITIONING - // Reduces the available RBs according to slicing configuration - dlsch_scheduler_pre_processor_partitioning(Mod_id, slice_idx, rbs_retx); - - for (CC_id = 0; CC_id < RC.nb_mac_CC[Mod_id]; ++CC_id) { - if (UE_list->head < 0) continue; // no UEs in list - - // max_rbs_allowed_slice is saved in every UE, so take it from the first one - ue_sched_ctl = &UE_list->UE_sched_ctrl[UE_list->head]; - available_rbs[CC_id] = ue_sched_ctl->max_rbs_allowed_slice[CC_id][slice_idx]; +int pp_find_rb_table_index(int approximate) { + int lo = 2; + if (approximate <= rb_table[lo]) + return lo; + int hi = sizeof(rb_table) - 1; + if (approximate >= rb_table[hi]) + return hi; + int p = (hi + lo) / 2; + for (; lo + 1 != hi; p = (hi + lo) / 2) { + if (approximate <= rb_table[p]) + hi = p; + else + lo = p; } + return p + 1; +} - switch (RC.mac[Mod_id]->slice_info.dl[slice_idx].accounting) { - // If greedy scheduling, try to account all the required RBs - case POL_GREEDY: - for (UE_id = UE_list->head; UE_id >= 0; UE_id = UE_list->next[UE_id]) { - rnti = UE_RNTI(Mod_id, UE_id); - - if (rnti == NOT_A_RNTI) continue; - - if (UE_list->UE_sched_ctrl[UE_id].ul_out_of_sync == 1) continue; - - if (!ue_dl_slice_membership(Mod_id, UE_id, slice_idx)) continue; - - for (i = 0; i < UE_num_active_CC(UE_list, UE_id); i++) { - CC_id = UE_list->ordered_CCids[i][UE_id]; - - if (available_rbs[CC_id] == 0) continue; - - nb_rbs_accounted[CC_id][UE_id] = cmin(nb_rbs_required[CC_id][UE_id], available_rbs[CC_id]); - available_rbs[CC_id] -= nb_rbs_accounted[CC_id][UE_id]; - } +int g_start_ue_ul = -1; +int round_robin_ul(module_id_t Mod_id, + int CC_id, + int frame, + int subframe, + int sched_frame, + int sched_subframe, + UE_list_t *UE_list, + int max_num_ue, + int num_contig_rb, + contig_rbs_t *rbs) { + AssertFatal(num_contig_rb <= 2, "cannot handle more than two contiguous RB regions\n"); + UE_info_t *UE_info = &RC.mac[Mod_id]->UE_info; + const int max_rb = num_contig_rb > 1 ? MAX(rbs[0].length, rbs[1].length) : rbs[0].length; + + /* for every UE: check whether we have to handle a retransmission (and + * allocate, if so). If not, compute how much RBs this UE would need */ + int rb_idx_required[MAX_MOBILES_PER_ENB]; + memset(rb_idx_required, 0, sizeof(rb_idx_required)); + int num_ue_req = 0; + for (int UE_id = UE_list->head; UE_id >= 0; UE_id = UE_list->next[UE_id]) { + UE_TEMPLATE *UE_template = &UE_info->UE_template[CC_id][UE_id]; + uint8_t harq_pid = subframe2harqpid(&RC.mac[Mod_id]->common_channels[CC_id], + sched_frame, sched_subframe); + if (UE_info->UE_sched_ctrl[UE_id].round_UL[CC_id][harq_pid] > 0) { + /* this UE has a retransmission, allocate it right away */ + const int nb_rb = UE_template->nb_rb_ul[harq_pid]; + if (nb_rb == 0) { + LOG_E(MAC, + "%4d.%d UE %d retransmission of 0 RBs in round %d, ignoring\n", + sched_frame, sched_subframe, UE_id, + UE_info->UE_sched_ctrl[UE_id].round_UL[CC_id][harq_pid]); + continue; } - - break; - - // Use the old, fair algorithm - // Loop over all active UEs and account the avg number of RBs to each UE, based on all non-retx UEs. - // case POL_FAIR: - default: - - // FIXME: This is not ideal, why loop on UEs to find average_rbs_per_user[], that is per-CC? - // TODO: Look how to loop on active CCs only without using the UE_num_active_CC() function. - for (UE_id = UE_list->head; UE_id >= 0; UE_id = UE_list->next[UE_id]) { - rnti = UE_RNTI(Mod_id, UE_id); - - if (rnti == NOT_A_RNTI) continue; - - if (UE_list->UE_sched_ctrl[UE_id].ul_out_of_sync == 1) continue; - - if (!ue_dl_slice_membership(Mod_id, UE_id, slice_idx)) continue; - - for (i = 0; i < UE_num_active_CC(UE_list, UE_id); ++i) { - CC_id = UE_list->ordered_CCids[i][UE_id]; - ue_sched_ctl = &UE_list->UE_sched_ctrl[UE_id]; - available_rbs[CC_id] = ue_sched_ctl->max_rbs_allowed_slice[CC_id][slice_idx]; - - if (ue_count_newtx[CC_id] == 0) { - average_rbs_per_user[CC_id] = 0; - } else if (min_rb_unit[CC_id]*ue_count_newtx[CC_id] <= available_rbs[CC_id]) { - average_rbs_per_user[CC_id] = (uint16_t)floor(available_rbs[CC_id]/ue_count_newtx[CC_id]); - } else { - // consider the total number of use that can be scheduled UE - average_rbs_per_user[CC_id] = (uint16_t)min_rb_unit[CC_id]; - } + const uint8_t cqi = UE_info->UE_sched_ctrl[UE_id].dl_cqi[CC_id]; + const int idx = CCE_try_allocate_ulsch(Mod_id, CC_id, subframe, UE_id, cqi); + if (idx < 0) + continue; // cannot allocate CCE + UE_template->pre_dci_ul_pdu_idx = idx; + if (rbs[0].length >= nb_rb) { // fits in first contiguous region + UE_template->pre_first_nb_rb_ul = rbs[0].start; + rbs[0].length -= nb_rb; + rbs[0].start += nb_rb; + } else if (num_contig_rb == 2 && rbs[1].length >= nb_rb) { // in second + UE_template->pre_first_nb_rb_ul = rbs[1].start; + rbs[1].length -= nb_rb; + rbs[1].start += nb_rb; + } else if (num_contig_rb == 2 + && rbs[1].start + rbs[1].length - rbs[0].start >= nb_rb) { // overlapping the middle + UE_template->pre_first_nb_rb_ul = rbs[0].start; + rbs[0].length = 0; + int ol = nb_rb - (rbs[1].start - rbs[0].start); // how much overlap in second region + if (ol > 0) { + rbs[1].length -= ol; + rbs[1].start += ol; } - } - - // note: nb_rbs_required is assigned according to total_buffer_dl - // extend nb_rbs_required to capture per LCID RB required - for (UE_id = UE_list->head; UE_id >= 0; UE_id = UE_list->next[UE_id]) { - rnti = UE_RNTI(Mod_id, UE_id); - - if (rnti == NOT_A_RNTI) continue; - - if (UE_list->UE_sched_ctrl[UE_id].ul_out_of_sync == 1) continue; - - if (!ue_dl_slice_membership(Mod_id, UE_id, slice_idx)) continue; - - for (i = 0; i < UE_num_active_CC(UE_list, UE_id); i++) { - CC_id = UE_list->ordered_CCids[i][UE_id]; - nb_rbs_accounted[CC_id][UE_id] = cmin(average_rbs_per_user[CC_id], nb_rbs_required[CC_id][UE_id]); - } - } - - break; - } - - // Check retransmissions - // TODO: Do this once at the beginning - for (UE_id = UE_list->head; UE_id >= 0; UE_id = UE_list->next[UE_id]) { - rnti = UE_RNTI(Mod_id, UE_id); - - if (rnti == NOT_A_RNTI) continue; - - if (UE_list->UE_sched_ctrl[UE_id].ul_out_of_sync == 1) continue; - - if (!ue_dl_slice_membership(Mod_id, UE_id, slice_idx)) continue; - - for (i = 0; i < UE_num_active_CC(UE_list, UE_id); i++) { - CC_id = UE_list->ordered_CCids[i][UE_id]; - ue_sched_ctl = &UE_list->UE_sched_ctrl[UE_id]; - cc = &RC.mac[Mod_id]->common_channels[CC_id]; - harq_pid = frame_subframe2_dl_harq_pid(cc->tdd_Config,frameP,subframeP); - round = ue_sched_ctl->round[CC_id][harq_pid]; - - // control channel or retransmission - /* TODO: do we have to check for retransmission? */ - if (mac_eNB_get_rrc_status(Mod_id, rnti) < RRC_RECONFIGURED || round != 8) { - nb_rbs_accounted[CC_id][UE_id] = nb_rbs_required[CC_id][UE_id]; - } - } - } -} - -void dlsch_scheduler_pre_processor_positioning(module_id_t Mod_id, - int slice_idx, - int min_rb_unit[NFAPI_CC_MAX], - uint16_t nb_rbs_required[NFAPI_CC_MAX][MAX_MOBILES_PER_ENB], - uint16_t nb_rbs_accounted[NFAPI_CC_MAX][MAX_MOBILES_PER_ENB], - uint16_t nb_rbs_remaining[NFAPI_CC_MAX][MAX_MOBILES_PER_ENB], - uint8_t rballoc_sub[NFAPI_CC_MAX][N_RBG_MAX], - uint8_t MIMO_mode_indicator[NFAPI_CC_MAX][N_RBG_MAX]) { - int UE_id, CC_id; - int i; -#ifdef TM5 - uint8_t transmission_mode; -#endif - uint8_t slice_allocation_mask[NFAPI_CC_MAX][N_RBG_MAX]; - int N_RBG[NFAPI_CC_MAX]; - UE_list_t *UE_list = &RC.mac[Mod_id]->UE_list; - decode_slice_positioning(Mod_id, slice_idx, slice_allocation_mask); - - for (CC_id = 0; CC_id < RC.nb_mac_CC[Mod_id]; CC_id++) { - COMMON_channels_t *cc = &RC.mac[Mod_id]->common_channels[CC_id]; - N_RBG[CC_id] = to_rbg(cc->mib->message.dl_Bandwidth); - } - - // Try to allocate accounted RBs - for (UE_id = UE_list->head; UE_id >= 0; UE_id = UE_list->next[UE_id]) { - if (UE_RNTI(Mod_id, UE_id) == NOT_A_RNTI) continue; - - if (UE_list->UE_sched_ctrl[UE_id].ul_out_of_sync == 1) continue; - - if (!ue_dl_slice_membership(Mod_id, UE_id, slice_idx)) continue; - - for (i = 0; i < UE_num_active_CC(UE_list, UE_id); i++) { - CC_id = UE_list->ordered_CCids[i][UE_id]; - nb_rbs_remaining[CC_id][UE_id] = nb_rbs_accounted[CC_id][UE_id]; -#ifdef TM5 - transmission_mode = get_tmode(Mod_id, CC_id, UE_id); -#endif - - if (nb_rbs_required[CC_id][UE_id] > 0) - LOG_D(MAC, - "Step 1: nb_rbs_remaining[%d][%d]= %d (accounted %d, required %d, pre_nb_available_rbs %d, N_RBG %d, rb_unit %d)\n", - CC_id, + } else { + LOG_W(MAC, + "cannot allocate UL retransmission for UE %d (nb_rb %d)\n", UE_id, - nb_rbs_remaining[CC_id][UE_id], - nb_rbs_accounted[CC_id][UE_id], - nb_rbs_required[CC_id][UE_id], - UE_list->UE_sched_ctrl[UE_id].pre_nb_available_rbs[CC_id], - N_RBG[CC_id], - min_rb_unit[CC_id]); - - LOG_T(MAC, "calling dlsch_scheduler_pre_processor_allocate .. \n "); - dlsch_scheduler_pre_processor_allocate(Mod_id, - UE_id, - CC_id, - N_RBG[CC_id], - min_rb_unit[CC_id], - nb_rbs_required, - nb_rbs_remaining, - rballoc_sub, - slice_allocation_mask, - MIMO_mode_indicator); -#ifdef TM5 - - // data chanel TM5: to be revisited - if ((round == 0) && - (transmission_mode == 5) && - (ue_sched_ctl->dl_pow_off[CC_id] != 1)) { - for (j = 0; j < N_RBG[CC_id]; j += 2) { - if ((((j == (N_RBG[CC_id] - 1)) - && (rballoc_sub[CC_id][j] == 0) - && (ue_sched_ctl-> - rballoc_sub_UE[CC_id][j] == 0)) - || ((j < (N_RBG[CC_id] - 1)) - && (rballoc_sub[CC_id][j + 1] == 0) - && - (ue_sched_ctl->rballoc_sub_UE - [CC_id][j + 1] == 0))) - && (nb_rbs_remaining[CC_id][UE_id] - > 0)) { - for (i = UE_list->next[UE_id + 1]; i >= 0; - i = UE_list->next[i]) { - UE_id2 = i; - rnti2 = UE_RNTI(Mod_id, UE_id2); - ue_sched_ctl2 = - &UE_list->UE_sched_ctrl[UE_id2]; - round2 = ue_sched_ctl2->round[CC_id]; - - if (rnti2 == NOT_A_RNTI) - continue; - - if (UE_list-> - UE_sched_ctrl - [UE_id2].ul_out_of_sync == 1) - continue; - - eNB_UE_stats2 = - UE_list-> - eNB_UE_stats[CC_id][UE_id2]; - //mac_xface->get_ue_active_harq_pid(Mod_id,CC_id,rnti2,frameP,subframeP,&harq_pid2,&round2,0); - - if ((mac_eNB_get_rrc_status - (Mod_id, - rnti2) >= RRC_RECONFIGURED) - && (round2 == 0) - && - (get_tmode(Mod_id, CC_id, UE_id2) - == 5) - && (ue_sched_ctl-> - dl_pow_off[CC_id] != 1)) { - if ((((j == (N_RBG[CC_id] - 1)) - && - (ue_sched_ctl->rballoc_sub_UE - [CC_id][j] == 0)) - || ((j < (N_RBG[CC_id] - 1)) - && - (ue_sched_ctl-> - rballoc_sub_UE[CC_id][j + - 1] - == 0))) - && - (nb_rbs_remaining - [CC_id] - [UE_id2] > 0)) { - if ((((eNB_UE_stats2-> - DL_pmi_single ^ - eNB_UE_stats1-> - DL_pmi_single) - << (14 - j)) & 0xc000) == 0x4000) { //MU-MIMO only for 25 RBs configuration - rballoc_sub[CC_id][j] = 1; - ue_sched_ctl-> - rballoc_sub_UE[CC_id] - [j] = 1; - ue_sched_ctl2-> - rballoc_sub_UE[CC_id] - [j] = 1; - MIMO_mode_indicator[CC_id] - [j] = 0; - - if (j < N_RBG[CC_id] - 1) { - rballoc_sub[CC_id][j + - 1] = - 1; - ue_sched_ctl-> - rballoc_sub_UE - [CC_id][j + 1] = 1; - ue_sched_ctl2->rballoc_sub_UE - [CC_id][j + 1] = 1; - MIMO_mode_indicator - [CC_id][j + 1] - = 0; - } - - ue_sched_ctl-> - dl_pow_off[CC_id] - = 0; - ue_sched_ctl2-> - dl_pow_off[CC_id] - = 0; - - if ((j == N_RBG[CC_id] - 1) - && ((N_RB_DL == 25) - || (N_RB_DL == - 50))) { - nb_rbs_remaining - [CC_id][UE_id] = - nb_rbs_remaining - [CC_id][UE_id] - - min_rb_unit[CC_id] - + 1; - ue_sched_ctl->pre_nb_available_rbs - [CC_id] = - ue_sched_ctl->pre_nb_available_rbs - [CC_id] + - min_rb_unit[CC_id] - - 1; - nb_rbs_remaining - [CC_id][UE_id2] = - nb_rbs_remaining - [CC_id][UE_id2] - - min_rb_unit[CC_id] - + 1; - ue_sched_ctl2->pre_nb_available_rbs - [CC_id] = - ue_sched_ctl2->pre_nb_available_rbs - [CC_id] + - min_rb_unit[CC_id] - - 1; - } else { - nb_rbs_remaining - [CC_id][UE_id] = - nb_rbs_remaining - [CC_id][UE_id] - 4; - ue_sched_ctl->pre_nb_available_rbs - [CC_id] = - ue_sched_ctl->pre_nb_available_rbs - [CC_id] + 4; - nb_rbs_remaining - [CC_id][UE_id2] = - nb_rbs_remaining - [CC_id][UE_id2] - - 4; - ue_sched_ctl2->pre_nb_available_rbs - [CC_id] = - ue_sched_ctl2->pre_nb_available_rbs - [CC_id] + 4; - } - - break; - } - } - } - } - } - } + nb_rb); + UE_template->pre_dci_ul_pdu_idx = -1; // do not need CCE + RC.mac[Mod_id]->HI_DCI0_req[CC_id][subframe].hi_dci0_request_body.number_of_dci--; + continue; } - -#endif + LOG_D(MAC, "%4d.%d UE %d retx %d RBs at start %d\n", + sched_frame, + sched_subframe, + UE_id, + UE_template->pre_allocated_nb_rb_ul, + UE_template->pre_first_nb_rb_ul); + UE_template->pre_allocated_nb_rb_ul = nb_rb; + max_num_ue--; + if (max_num_ue == 0) /* in this case, cannot allocate any other UE anymore */ + return rbs[0].length + (num_contig_rb > 1 ? rbs[1].length : 0); + continue; } - } -} -void dlsch_scheduler_pre_processor_intraslice_sharing(module_id_t Mod_id, - int slice_idx, - int min_rb_unit[NFAPI_CC_MAX], - uint16_t nb_rbs_required[NFAPI_CC_MAX][MAX_MOBILES_PER_ENB], - uint16_t nb_rbs_accounted[NFAPI_CC_MAX][MAX_MOBILES_PER_ENB], - uint16_t nb_rbs_remaining[NFAPI_CC_MAX][MAX_MOBILES_PER_ENB], - uint8_t rballoc_sub[NFAPI_CC_MAX][N_RBG_MAX], - uint8_t MIMO_mode_indicator[NFAPI_CC_MAX][N_RBG_MAX]) { - int UE_id, CC_id; - int i; -#ifdef TM5 - uint8_t transmission_mode; -#endif - UE_list_t *UE_list = &RC.mac[Mod_id]->UE_list; - int N_RBG[NFAPI_CC_MAX]; - slice_info_t *sli = &RC.mac[Mod_id]->slice_info; - uint8_t (*slice_allocation_mask)[N_RBG_MAX] = sli->pre_processor_results[slice_idx].slice_allocation_mask; - decode_slice_positioning(Mod_id, slice_idx, slice_allocation_mask); - - for (CC_id = 0; CC_id < RC.nb_mac_CC[Mod_id]; CC_id++) { - COMMON_channels_t *cc = &RC.mac[Mod_id]->common_channels[CC_id]; - N_RBG[CC_id] = to_rbg(cc->mib->message.dl_Bandwidth); - } - - // Remaining RBs are allocated to high priority UEs - for (UE_id = UE_list->head; UE_id >= 0; UE_id = UE_list->next[UE_id]) { - if (UE_RNTI(Mod_id, UE_id) == NOT_A_RNTI) continue; - - if (UE_list->UE_sched_ctrl[UE_id].ul_out_of_sync == 1) continue; - - if (!ue_dl_slice_membership(Mod_id, UE_id, slice_idx)) continue; - - for (i = 0; i < UE_num_active_CC(UE_list, UE_id); i++) { - CC_id = UE_list->ordered_CCids[i][UE_id]; - nb_rbs_remaining[CC_id][UE_id] = - nb_rbs_required[CC_id][UE_id] - nb_rbs_accounted[CC_id][UE_id] + nb_rbs_remaining[CC_id][UE_id]; - - if (nb_rbs_remaining[CC_id][UE_id] < 0) - abort(); - -#ifdef TM5 - transmission_mode = get_tmode(Mod_id, CC_id, UE_id); -#endif - - if (nb_rbs_required[CC_id][UE_id] > 0) - LOG_D(MAC, - "Step 2: nb_rbs_remaining[%d][%d]= %d (accounted %d, required %d, pre_nb_available_rbs %d, N_RBG %d, rb_unit %d)\n", - CC_id, - UE_id, - nb_rbs_remaining[CC_id][UE_id], - nb_rbs_accounted[CC_id][UE_id], - nb_rbs_required[CC_id][UE_id], - UE_list->UE_sched_ctrl[UE_id].pre_nb_available_rbs[CC_id], - N_RBG[CC_id], - min_rb_unit[CC_id]); - - LOG_T(MAC, "calling dlsch_scheduler_pre_processor_allocate .. \n "); - dlsch_scheduler_pre_processor_allocate(Mod_id, - UE_id, - CC_id, - N_RBG[CC_id], - min_rb_unit[CC_id], - nb_rbs_required, - nb_rbs_remaining, - rballoc_sub, - slice_allocation_mask, - MIMO_mode_indicator); -#ifdef TM5 - - // data chanel TM5: to be revisited - if ((round == 0) && - (transmission_mode == 5) && - (ue_sched_ctl->dl_pow_off[CC_id] != 1)) { - for (j = 0; j < N_RBG[CC_id]; j += 2) { - if ((((j == (N_RBG[CC_id] - 1)) - && (rballoc_sub[CC_id][j] == 0) - && (ue_sched_ctl-> - rballoc_sub_UE[CC_id][j] == 0)) - || ((j < (N_RBG[CC_id] - 1)) - && (rballoc_sub[CC_id][j + 1] == 0) - && - (ue_sched_ctl->rballoc_sub_UE - [CC_id][j + 1] == 0))) - && (nb_rbs_remaining[CC_id][UE_id] - > 0)) { - for (i = UE_list->next[UE_id + 1]; i >= 0; - i = UE_list->next[i]) { - UE_id2 = i; - rnti2 = UE_RNTI(Mod_id, UE_id2); - ue_sched_ctl2 = - &UE_list->UE_sched_ctrl[UE_id2]; - round2 = ue_sched_ctl2->round[CC_id]; - - if (rnti2 == NOT_A_RNTI) - continue; - - if (UE_list-> - UE_sched_ctrl - [UE_id2].ul_out_of_sync == 1) - continue; - - eNB_UE_stats2 = - UE_list-> - eNB_UE_stats[CC_id][UE_id2]; - //mac_xface->get_ue_active_harq_pid(Mod_id,CC_id,rnti2,frameP,subframeP,&harq_pid2,&round2,0); - - if ((mac_eNB_get_rrc_status - (Mod_id, - rnti2) >= RRC_RECONFIGURED) - && (round2 == 0) - && - (get_tmode(Mod_id, CC_id, UE_id2) - == 5) - && (ue_sched_ctl-> - dl_pow_off[CC_id] != 1)) { - if ((((j == (N_RBG[CC_id] - 1)) - && - (ue_sched_ctl->rballoc_sub_UE - [CC_id][j] == 0)) - || ((j < (N_RBG[CC_id] - 1)) - && - (ue_sched_ctl-> - rballoc_sub_UE[CC_id][j + - 1] - == 0))) - && - (nb_rbs_remaining - [CC_id] - [UE_id2] > 0)) { - if ((((eNB_UE_stats2-> - DL_pmi_single ^ - eNB_UE_stats1-> - DL_pmi_single) - << (14 - j)) & 0xc000) == 0x4000) { //MU-MIMO only for 25 RBs configuration - rballoc_sub[CC_id][j] = 1; - ue_sched_ctl-> - rballoc_sub_UE[CC_id] - [j] = 1; - ue_sched_ctl2-> - rballoc_sub_UE[CC_id] - [j] = 1; - MIMO_mode_indicator[CC_id] - [j] = 0; - - if (j < N_RBG[CC_id] - 1) { - rballoc_sub[CC_id][j + - 1] = - 1; - ue_sched_ctl-> - rballoc_sub_UE - [CC_id][j + 1] = 1; - ue_sched_ctl2->rballoc_sub_UE - [CC_id][j + 1] = 1; - MIMO_mode_indicator - [CC_id][j + 1] - = 0; - } - - ue_sched_ctl-> - dl_pow_off[CC_id] - = 0; - ue_sched_ctl2-> - dl_pow_off[CC_id] - = 0; - - if ((j == N_RBG[CC_id] - 1) - && ((N_RB_DL == 25) - || (N_RB_DL == - 50))) { - nb_rbs_remaining - [CC_id][UE_id] = - nb_rbs_remaining - [CC_id][UE_id] - - min_rb_unit[CC_id] - + 1; - ue_sched_ctl->pre_nb_available_rbs - [CC_id] = - ue_sched_ctl->pre_nb_available_rbs - [CC_id] + - min_rb_unit[CC_id] - - 1; - nb_rbs_remaining - [CC_id][UE_id2] = - nb_rbs_remaining - [CC_id][UE_id2] - - min_rb_unit[CC_id] - + 1; - ue_sched_ctl2->pre_nb_available_rbs - [CC_id] = - ue_sched_ctl2->pre_nb_available_rbs - [CC_id] + - min_rb_unit[CC_id] - - 1; - } else { - nb_rbs_remaining - [CC_id][UE_id] = - nb_rbs_remaining - [CC_id][UE_id] - 4; - ue_sched_ctl->pre_nb_available_rbs - [CC_id] = - ue_sched_ctl->pre_nb_available_rbs - [CC_id] + 4; - nb_rbs_remaining - [CC_id][UE_id2] = - nb_rbs_remaining - [CC_id][UE_id2] - - 4; - ue_sched_ctl2->pre_nb_available_rbs - [CC_id] = - ue_sched_ctl2->pre_nb_available_rbs - [CC_id] + 4; - } - - break; - } - } - } - } - } - } - } + const int B = cmax(UE_template->estimated_ul_buffer - UE_template->scheduled_ul_bytes, 0); + const int UE_to_be_scheduled = UE_is_to_be_scheduled(Mod_id, CC_id, UE_id); + if (B == 0 && !UE_to_be_scheduled) + continue; -#endif - } - } -} + num_ue_req++; -// This function assigns pre-available RBS to each UE in specified sub-bands before scheduling is done -void -dlsch_scheduler_pre_processor(module_id_t Mod_id, - int slice_idx, - frame_t frameP, - sub_frame_t subframeP, - int *mbsfn_flag, - uint8_t rballoc_sub[NFAPI_CC_MAX][N_RBG_MAX]) { - int UE_id; - uint8_t CC_id; - uint16_t i, j; - int min_rb_unit[NFAPI_CC_MAX]; - eNB_MAC_INST *eNB = RC.mac[Mod_id]; - slice_info_t *sli = &eNB->slice_info; - uint16_t (*nb_rbs_required)[MAX_MOBILES_PER_ENB] = sli->pre_processor_results[slice_idx].nb_rbs_required; - uint16_t (*nb_rbs_accounted)[MAX_MOBILES_PER_ENB] = sli->pre_processor_results[slice_idx].nb_rbs_accounted; - uint16_t (*nb_rbs_remaining)[MAX_MOBILES_PER_ENB] = sli->pre_processor_results[slice_idx].nb_rbs_remaining; - uint8_t (*MIMO_mode_indicator)[N_RBG_MAX] = sli->pre_processor_results[slice_idx].MIMO_mode_indicator; - UE_list_t *UE_list = &eNB->UE_list; - UE_sched_ctrl_t *ue_sched_ctl; - // int rrc_status = RRC_IDLE; -#ifdef TM5 - int harq_pid1 = 0; - int round1 = 0, round2 = 0; - int UE_id2; - uint16_t i1, i2, i3; - rnti_t rnti1, rnti2; - LTE_eNB_UE_stats *eNB_UE_stats1 = NULL; - LTE_eNB_UE_stats *eNB_UE_stats2 = NULL; - UE_sched_ctrl_t *ue_sched_ctl1, *ue_sched_ctl2; -#endif - // Initialize scheduling information for all active UEs - memset(&sli->pre_processor_results[slice_idx], 0, sizeof(sli->pre_processor_results[slice_idx])); - // FIXME: After the memset above, some of the resets in reset() are redundant - dlsch_scheduler_pre_processor_reset(Mod_id, - slice_idx, - frameP, - subframeP, - min_rb_unit, - nb_rbs_required, - rballoc_sub, - MIMO_mode_indicator, - mbsfn_flag); // FIXME: Not sure if useful - // STATUS - // Store the DLSCH buffer for each logical channel - store_dlsch_buffer(Mod_id, - slice_idx, - frameP, - subframeP); - // Calculate the number of RBs required by each UE on the basis of logical channel's buffer - assign_rbs_required(Mod_id, - slice_idx, - frameP, - subframeP, - nb_rbs_required, - min_rb_unit); - // Sorts the user on the basis of dlsch logical channel buffer and CQI - sort_UEs(Mod_id, - slice_idx, - frameP, - subframeP); - // ACCOUNTING - // This procedure decides the number of RBs to allocate - dlsch_scheduler_pre_processor_accounting(Mod_id, - slice_idx, - frameP, - subframeP, - min_rb_unit, - nb_rbs_required, - nb_rbs_accounted); - // POSITIONING - // This procedure does the main allocation of the RBs - dlsch_scheduler_pre_processor_positioning(Mod_id, - slice_idx, - min_rb_unit, - nb_rbs_required, - nb_rbs_accounted, - nb_rbs_remaining, - rballoc_sub, - MIMO_mode_indicator); - - // SHARING - // If there are available RBs left in the slice, allocate them to the highest priority UEs - if (eNB->slice_info.intraslice_share_active) { - dlsch_scheduler_pre_processor_intraslice_sharing(Mod_id, - slice_idx, - min_rb_unit, - nb_rbs_required, - nb_rbs_accounted, - nb_rbs_remaining, - rballoc_sub, - MIMO_mode_indicator); - } - -#ifdef TM5 - - // This has to be revisited!!!! - for (CC_id = 0; CC_id < RC.nb_mac_CC[Mod_id]; CC_id++) { - COMMON_channels_t *cc = &eNB->common_channels[CC_id]; - int N_RBG = to_rbg(cc->mib->message.dl_Bandwidth); - i1 = 0; - i2 = 0; - i3 = 0; - - for (j = 0; j < N_RBG; j++) { - if (MIMO_mode_indicator[CC_id][j] == 2) { - i1++; - } else if (MIMO_mode_indicator[CC_id][j] == 1) { - i2++; - } else if (MIMO_mode_indicator[CC_id][j] == 0) { - i3++; - } + /* if UE has pending scheduling request then pre-allocate 3 RBs */ + if (B == 0 && UE_to_be_scheduled) { + UE_template->pre_assigned_mcs_ul = 10; /* use QPSK mcs only */ + rb_idx_required[UE_id] = 2; + //UE_template->pre_allocated_nb_rb_ul = 3; + continue; } - if (i1 < N_RBG) { - if (i2 > 0 && i3 == 0) { - PHY_vars_eNB_g[Mod_id][CC_id]->check_for_SUMIMO_transmissions = PHY_vars_eNB_g[Mod_id][CC_id]->check_for_SUMIMO_transmissions + 1; - } else if (i3 > 0) { - PHY_vars_eNB_g[Mod_id][CC_id]->check_for_MUMIMO_transmissions = PHY_vars_eNB_g[Mod_id][CC_id]->check_for_MUMIMO_transmissions + 1; - } - } else if (i3 == N_RBG && i1 == 0 && i2 == 0) { - PHY_vars_eNB_g[Mod_id][CC_id]->FULL_MUMIMO_transmissions = PHY_vars_eNB_g[Mod_id][CC_id]->FULL_MUMIMO_transmissions + 1; + int mcs; + int rb_table_index; + int tx_power; + calculate_max_mcs_min_rb( + Mod_id, + CC_id, + B, + UE_template->phr_info, + UE_info->UE_sched_ctrl[UE_id].phr_received == 1 ? 20 : 10, + &mcs, + max_rb, + &rb_table_index, + &tx_power); + + UE_template->pre_assigned_mcs_ul = mcs; + rb_idx_required[UE_id] = rb_table_index; + //UE_template->pre_allocated_nb_rb_ul = rb_table[rb_table_index]; + /* only print log when PHR changed */ + static int phr = 0; + if (phr != UE_template->phr_info) { + phr = UE_template->phr_info; + LOG_D(MAC, "%d.%d UE %d CC %d: pre mcs %d, pre rb_table[%d]=%d RBs (phr %d, tx power %d, bytes %d)\n", + frame, + subframe, + UE_id, + CC_id, + UE_template->pre_assigned_mcs_ul, + UE_template->pre_allocated_rb_table_index_ul, + UE_template->pre_allocated_nb_rb_ul, + UE_template->phr_info, + tx_power, + B); } - - PHY_vars_eNB_g[Mod_id][CC_id]->check_for_total_transmissions = PHY_vars_eNB_g[Mod_id][CC_id]->check_for_total_transmissions + 1; } -#endif - - for (UE_id = UE_list->head; UE_id >= 0; UE_id = UE_list->next[UE_id]) { - ue_sched_ctl = &UE_list->UE_sched_ctrl[UE_id]; - - for (i = 0; i < UE_num_active_CC(UE_list, UE_id); i++) { - CC_id = UE_list->ordered_CCids[i][UE_id]; - //PHY_vars_eNB_g[Mod_id]->mu_mimo_mode[UE_id].dl_pow_off = dl_pow_off[UE_id]; - COMMON_channels_t *cc = &eNB->common_channels[CC_id]; - int N_RBG = to_rbg(cc->mib->message.dl_Bandwidth); - - if (ue_sched_ctl->pre_nb_available_rbs[CC_id] > 0) { - LOG_D(MAC, "******************DL Scheduling Information for UE%d ************************\n", - UE_id); - LOG_D(MAC, "dl power offset UE%d = %d \n", - UE_id, - ue_sched_ctl->dl_pow_off[CC_id]); - LOG_D(MAC, "***********RB Alloc for every subband for UE%d ***********\n", - UE_id); - - for (j = 0; j < N_RBG; j++) { - //PHY_vars_eNB_g[Mod_id]->mu_mimo_mode[UE_id].rballoc_sub[UE_id] = rballoc_sub_UE[CC_id][UE_id][UE_id]; - LOG_D(MAC, "RB Alloc for UE%d and Subband%d = %d\n", - UE_id, j, - ue_sched_ctl->rballoc_sub_UE[CC_id][j]); - } - - //PHY_vars_eNB_g[Mod_id]->mu_mimo_mode[UE_id].pre_nb_available_rbs = pre_nb_available_rbs[CC_id][UE_id]; - LOG_D(MAC, "[eNB %d][SLICE %d]Total RBs allocated for UE%d = %d\n", - Mod_id, - eNB->slice_info.dl[slice_idx].id, - UE_id, - ue_sched_ctl->pre_nb_available_rbs[CC_id]); - } - } + if (num_ue_req == 0) + return rbs[0].length + (num_contig_rb > 1 ? rbs[1].length : 0); + + // calculate how many users should be in both regions, and to maximize usage, + // go from the larger to the smaller one which at least will handle a single + // full load case better. + const int n = min(num_ue_req, max_num_ue); + int nr[2] = {n, 0}; + int step = 1; // the order if we have two regions + int start = 0; + int end = 1; + if (num_contig_rb > 1) { + // proportionally divide between both regions + int la = rbs[0].length > 0 ? rbs[0].length : 1; + int lb = rbs[1].length > 0 ? rbs[1].length : 1; + nr[1] = min(max(n/(la/lb + 1), 1), n - 1); + nr[0] = n - nr[1]; + step = la > lb ? 1 : -1; // 1: from 0 to 1, -1: from 1 to 0 + start = la > lb ? 0 : 1; + end = la > lb ? 2 : -1; } -} -#define SF0_LIMIT 1 + if (g_start_ue_ul == -1) + g_start_ue_ul = UE_list->head; + int sUE_id = g_start_ue_ul; + int rb_idx_given[MAX_MOBILES_PER_ENB]; + memset(rb_idx_given, 0, sizeof(rb_idx_given)); -void -dlsch_scheduler_pre_processor_reset(module_id_t module_idP, - int slice_idx, - frame_t frameP, - sub_frame_t subframeP, - int min_rb_unit[NFAPI_CC_MAX], - uint16_t nb_rbs_required[NFAPI_CC_MAX][MAX_MOBILES_PER_ENB], - uint8_t rballoc_sub[NFAPI_CC_MAX][N_RBG_MAX], - uint8_t MIMO_mode_indicator[NFAPI_CC_MAX][N_RBG_MAX], - int *mbsfn_flag) { - int UE_id; - uint8_t CC_id; - int i, j; - UE_list_t *UE_list; - UE_sched_ctrl_t *ue_sched_ctl; - int N_RB_DL, RBGsize, RBGsize_last; - int N_RBG[NFAPI_CC_MAX]; -#ifdef SF0_LIMIT - int sf0_lower, sf0_upper; -#endif - rnti_t rnti; - uint8_t *vrb_map; - COMMON_channels_t *cc; - - // - for (CC_id = 0; CC_id < RC.nb_mac_CC[module_idP]; CC_id++) { - // initialize harq_pid and round - cc = &RC.mac[module_idP]->common_channels[CC_id]; - N_RBG[CC_id] = to_rbg(cc->mib->message.dl_Bandwidth); - min_rb_unit[CC_id] = get_min_rb_unit(module_idP, CC_id); - - if (mbsfn_flag[CC_id] > 0) // If this CC is allocated for MBSFN skip it here + for (int r = start; r != end; r += step) { + // don't allocate if we have too little RBs + if (rbs[r].length < 3) + continue; + if (nr[r] <= 0) continue; - for (UE_id = 0; UE_id < MAX_MOBILES_PER_ENB; ++UE_id) { - UE_list = &RC.mac[module_idP]->UE_list; - ue_sched_ctl = &UE_list->UE_sched_ctrl[UE_id]; - rnti = UE_RNTI(module_idP, UE_id); - - if (rnti == NOT_A_RNTI) - continue; - - if (UE_list->active[UE_id] != TRUE) - continue; - - if (!ue_dl_slice_membership(module_idP, UE_id, slice_idx)) + UE_list_t UE_sched; + // average RB index: just below the index that fits all UEs + int start_idx = pp_find_rb_table_index(rbs[r].length / nr[r]) - 1; + int num_ue_sched = 0; + int rb_required_add = 0; + int *cur_UE = &UE_sched.head; + while (num_ue_sched < nr[r]) { + while (rb_idx_required[sUE_id] == 0) + sUE_id = next_ue_list_looped(UE_list, sUE_id); + const int cqi = UE_info->UE_sched_ctrl[sUE_id].dl_cqi[CC_id]; + const int idx = CCE_try_allocate_ulsch(Mod_id, CC_id, subframe, sUE_id, cqi); + if (idx < 0) { + LOG_D(MAC, "cannot allocate CCE for UE %d, skipping\n", sUE_id); + nr[r]--; + sUE_id = next_ue_list_looped(UE_list, sUE_id); // next candidate continue; - - LOG_D(MAC, "Running preprocessor for UE %d (%x)\n", UE_id, rnti); - - // initialize harq_pid and round - if (ue_sched_ctl->ta_timer) - ue_sched_ctl->ta_timer--; - - /* - eNB_UE_stats *eNB_UE_stats; - - if (eNB_UE_stats == NULL) - return; - - - mac_xface->get_ue_active_harq_pid(module_idP,CC_id,rnti, - frameP,subframeP, - &ue_sched_ctl->harq_pid[CC_id], - &ue_sched_ctl->round[CC_id], - openair_harq_DL); - - - if (ue_sched_ctl->ta_timer == 0) { - - // WE SHOULD PROTECT the eNB_UE_stats with a mutex here ... - - ue_sched_ctl->ta_timer = 20; // wait 20 subframes before taking TA measurement from PHY - switch (N_RB_DL) { - case 6: - ue_sched_ctl->ta_update = eNB_UE_stats->timing_advance_update; - break; - - case 15: - ue_sched_ctl->ta_update = eNB_UE_stats->timing_advance_update/2; - break; - - case 25: - ue_sched_ctl->ta_update = eNB_UE_stats->timing_advance_update/4; - break; - - case 50: - ue_sched_ctl->ta_update = eNB_UE_stats->timing_advance_update/8; - break; - - case 75: - ue_sched_ctl->ta_update = eNB_UE_stats->timing_advance_update/12; - break; - - case 100: - ue_sched_ctl->ta_update = eNB_UE_stats->timing_advance_update/16; - break; - } - // clear the update in case PHY does not have a new measurement after timer expiry - eNB_UE_stats->timing_advance_update = 0; - } - else { - ue_sched_ctl->ta_timer--; - ue_sched_ctl->ta_update =0; // don't trigger a timing advance command - } - - - if (UE_id==0) { - VCD_SIGNAL_DUMPER_DUMP_VARIABLE_BY_NAME(VCD_SIGNAL_DUMPER_VARIABLES_UE0_TIMING_ADVANCE,ue_sched_ctl->ta_update); - } - */ - nb_rbs_required[CC_id][UE_id] = 0; - ue_sched_ctl->pre_nb_available_rbs[CC_id] = 0; - ue_sched_ctl->dl_pow_off[CC_id] = 2; - - for (i = 0; i < N_RBG[CC_id]; i++) { - ue_sched_ctl->rballoc_sub_UE[CC_id][i] = 0; } + UE_info->UE_template[CC_id][sUE_id].pre_dci_ul_pdu_idx = idx; + *cur_UE = sUE_id; + cur_UE = &UE_sched.next[sUE_id]; + rb_idx_given[sUE_id] = min(start_idx, rb_idx_required[sUE_id]); + rb_required_add += rb_table[rb_idx_required[sUE_id]] - rb_table[rb_idx_given[sUE_id]]; + rbs[r].length -= rb_table[rb_idx_given[sUE_id]]; + num_ue_sched++; + sUE_id = next_ue_list_looped(UE_list, sUE_id); } - - N_RB_DL = to_prb(RC.mac[module_idP]->common_channels[CC_id].mib->message.dl_Bandwidth); -#ifdef SF0_LIMIT - - switch (N_RBG[CC_id]) { - case 6: - sf0_lower = 0; - sf0_upper = 5; - break; - - case 8: - sf0_lower = 2; - sf0_upper = 5; - break; - - case 13: - sf0_lower = 4; - sf0_upper = 7; - break; - - case 17: - sf0_lower = 7; - sf0_upper = 9; - break; - - case 25: - sf0_lower = 11; - sf0_upper = 13; - break; - - default: - AssertFatal(1 == 0, "unsupported RBs (%d)\n", N_RB_DL); - } - -#endif - - switch (N_RB_DL) { - case 6: - RBGsize = 1; - RBGsize_last = 1; - break; - - case 15: - RBGsize = 2; - RBGsize_last = 1; - break; - - case 25: - RBGsize = 2; - RBGsize_last = 1; - break; - - case 50: - RBGsize = 3; - RBGsize_last = 2; - break; - - case 75: - RBGsize = 4; - RBGsize_last = 3; - break; - - case 100: - RBGsize = 4; - RBGsize_last = 4; - break; - - default: - AssertFatal(1 == 0, "unsupported RBs (%d)\n", N_RB_DL); - } - - vrb_map = RC.mac[module_idP]->common_channels[CC_id].vrb_map; - - // Initialize Subbands according to VRB map - for (i = 0; i < N_RBG[CC_id]; i++) { - int rb_size = i == N_RBG[CC_id] - 1 ? RBGsize_last : RBGsize; -#ifdef SF0_LIMIT - - // for avoiding 6+ PRBs around DC in subframe 0 (avoid excessive errors) - /* TODO: make it proper - allocate those RBs, do not "protect" them, but - * compute number of available REs and limit MCS according to the - * TBS table 36.213 7.1.7.2.1-1 (can be done after pre-processor) - */ - if (subframeP == 0 && i >= sf0_lower && i <= sf0_upper) - rballoc_sub[CC_id][i] = 1; - -#endif - - // for SI-RNTI,RA-RNTI and P-RNTI allocations - for (j = 0; j < rb_size; j++) { - if (vrb_map[j + (i*RBGsize)] != 0) { - rballoc_sub[CC_id][i] = 1; - LOG_D(MAC, "Frame %d, subframe %d : vrb %d allocated\n", frameP, subframeP, j + (i*RBGsize)); - break; - } + *cur_UE = -1; + + /* give remaining RBs in RR fashion. Since we don't know in advance the + * amount of RBs we can give (the "step size" in rb_table is non-linear), go + * through all UEs and try to give a bit more. Continue until no UE can be + * given a higher index because the remaining RBs do not suffice to increase */ + int UE_id = UE_sched.head; + int rb_required_add_old; + do { + rb_required_add_old = rb_required_add; + for (int UE_id = UE_sched.head; UE_id >= 0; UE_id = UE_sched.next[UE_id]) { + if (rb_idx_given[UE_id] >= rb_idx_required[UE_id]) + continue; // this UE does not need more + const int new_idx = rb_idx_given[UE_id] + 1; + const int rb_inc = rb_table[new_idx] - rb_table[rb_idx_given[UE_id]]; + if (rbs[r].length < rb_inc) + continue; + rb_idx_given[UE_id] = new_idx; + rbs[r].length -= rb_inc; + rb_required_add -= rb_inc; } - - //LOG_D(MAC, "Frame %d Subframe %d CC_id %d RBG %i : rb_alloc %d\n", - //frameP, subframeP, CC_id, i, rballoc_sub[CC_id][i]); - MIMO_mode_indicator[CC_id][i] = 2; + } while (rb_required_add != rb_required_add_old); + + for (UE_id = UE_sched.head; UE_id >= 0; UE_id = UE_sched.next[UE_id]) { + UE_TEMPLATE *UE_template = &UE_info->UE_template[CC_id][UE_id]; + + /* MCS has been allocated previously */ + UE_template->pre_first_nb_rb_ul = rbs[r].start; + UE_template->pre_allocated_rb_table_index_ul = rb_idx_given[UE_id]; + UE_template->pre_allocated_nb_rb_ul = rb_table[rb_idx_given[UE_id]]; + rbs[r].start += rb_table[rb_idx_given[UE_id]]; + LOG_D(MAC, "%4d.%d UE %d allocated %d RBs start %d new start %d\n", + sched_frame, + sched_subframe, + UE_id, + UE_template->pre_allocated_nb_rb_ul, + UE_template->pre_first_nb_rb_ul, + rbs[r].start); } } -} - - -void -dlsch_scheduler_pre_processor_allocate(module_id_t Mod_id, - int UE_id, - uint8_t CC_id, - int N_RBG, - int min_rb_unit, - uint16_t nb_rbs_required[NFAPI_CC_MAX][MAX_MOBILES_PER_ENB], - uint16_t nb_rbs_remaining[NFAPI_CC_MAX][MAX_MOBILES_PER_ENB], - uint8_t rballoc_sub[NFAPI_CC_MAX][N_RBG_MAX], - uint8_t slice_allocation_mask[NFAPI_CC_MAX][N_RBG_MAX], - uint8_t MIMO_mode_indicator[NFAPI_CC_MAX][N_RBG_MAX]) { - int i; - int tm = get_tmode(Mod_id, CC_id, UE_id); - UE_list_t *UE_list = &RC.mac[Mod_id]->UE_list; - UE_sched_ctrl_t *ue_sched_ctl = &UE_list->UE_sched_ctrl[UE_id]; - int N_RB_DL = to_prb(RC.mac[Mod_id]->common_channels[CC_id].mib->message.dl_Bandwidth); - - for (i = 0; i < N_RBG; i++) { - if (rballoc_sub[CC_id][i] != 0) continue; - - if (ue_sched_ctl->rballoc_sub_UE[CC_id][i] != 0) continue; - - if (nb_rbs_remaining[CC_id][UE_id] <= 0) continue; - - if (ue_sched_ctl->pre_nb_available_rbs[CC_id] >= nb_rbs_required[CC_id][UE_id]) continue; - - if (ue_sched_ctl->dl_pow_off[CC_id] == 0) continue; - - if (slice_allocation_mask[CC_id][i] == 0) continue; - - if ((i == N_RBG - 1) && ((N_RB_DL == 25) || (N_RB_DL == 50))) { - // Allocating last, smaller RBG - if (nb_rbs_remaining[CC_id][UE_id] >= min_rb_unit - 1) { - rballoc_sub[CC_id][i] = 1; - ue_sched_ctl->rballoc_sub_UE[CC_id][i] = 1; - MIMO_mode_indicator[CC_id][i] = 1; - - if (tm == 5) { - ue_sched_ctl->dl_pow_off[CC_id] = 1; - } - - nb_rbs_remaining[CC_id][UE_id] = nb_rbs_remaining[CC_id][UE_id] - min_rb_unit + 1; - ue_sched_ctl->pre_nb_available_rbs[CC_id] = ue_sched_ctl->pre_nb_available_rbs[CC_id] + min_rb_unit - 1; - } - } else { - // Allocating a standard-sized RBG - if (nb_rbs_remaining[CC_id][UE_id] >= min_rb_unit) { - rballoc_sub[CC_id][i] = 1; - ue_sched_ctl->rballoc_sub_UE[CC_id][i] = 1; - MIMO_mode_indicator[CC_id][i] = 1; - - if (tm == 5) { - ue_sched_ctl->dl_pow_off[CC_id] = 1; - } - nb_rbs_remaining[CC_id][UE_id] = nb_rbs_remaining[CC_id][UE_id] - min_rb_unit; - ue_sched_ctl->pre_nb_available_rbs[CC_id] = ue_sched_ctl->pre_nb_available_rbs[CC_id] + min_rb_unit; - } - } + /* if not all UEs could be allocated in this round */ + if (num_ue_req > max_num_ue) { + /* go to the first one we missed */ + for (int i = 0; i < max_num_ue; ++i) + g_start_ue_ul = next_ue_list_looped(UE_list, g_start_ue_ul); + } else { + /* else, just start with the next UE next time */ + g_start_ue_ul = next_ue_list_looped(UE_list, g_start_ue_ul); } -} - -/// ULSCH PRE_PROCESSOR + return rbs[0].length + (num_contig_rb > 1 ? rbs[1].length : 0); +} -void ulsch_scheduler_pre_processor(module_id_t module_idP, - int slice_idx, +void ulsch_scheduler_pre_processor(module_id_t Mod_id, + int CC_id, int frameP, sub_frame_t subframeP, int sched_frameP, - unsigned char sched_subframeP, - uint16_t *first_rb) { - int UE_id; - uint16_t n; - uint8_t CC_id, harq_pid; - uint16_t nb_allocated_rbs[NFAPI_CC_MAX][MAX_MOBILES_PER_ENB]; - uint16_t total_allocated_rbs[NFAPI_CC_MAX]; - uint16_t average_rbs_per_user[NFAPI_CC_MAX]; - int16_t total_remaining_rbs[NFAPI_CC_MAX]; - uint16_t total_ue_count[NFAPI_CC_MAX]; - eNB_MAC_INST *eNB = RC.mac[module_idP]; - UE_list_t *UE_list = &eNB->UE_list; - slice_info_t *sli = &eNB->slice_info; - UE_TEMPLATE *UE_template = 0; - UE_sched_ctrl_t *ue_sched_ctl; - int N_RB_UL = 0; - uint16_t available_rbs, first_rb_offset; - rnti_t rntiTable[MAX_MOBILES_PER_ENB]; - // sort ues - LOG_D(MAC, "In ulsch_preprocessor: sort ue \n"); - sort_ue_ul(module_idP, slice_idx, sched_frameP, sched_subframeP, rntiTable); - // maximize MCS and then allocate required RB according to the buffer occupancy with the limit of max available UL RB - LOG_D(MAC, "In ulsch_preprocessor: assign max mcs min rb\n"); - assign_max_mcs_min_rb(module_idP, slice_idx, frameP, subframeP, first_rb); - // we need to distribute RBs among UEs - // step1: reset the vars - uint8_t CC_nb = (uint8_t) RC.nb_mac_CC[module_idP]; - - for (CC_id = 0; CC_id < CC_nb; CC_id++) { - total_allocated_rbs[CC_id] = 0; - total_remaining_rbs[CC_id] = 0; - average_rbs_per_user[CC_id] = 0; - total_ue_count[CC_id] = 0; - } + unsigned char sched_subframeP) { + UE_info_t *UE_info = &RC.mac[Mod_id]->UE_info; + const int N_RB_UL = to_prb(RC.mac[Mod_id]->common_channels[CC_id].ul_Bandwidth); + COMMON_channels_t *cc = &RC.mac[Mod_id]->common_channels[CC_id]; + + UE_list_t UE_to_sched; + UE_to_sched.head = -1; + for (int i = 0; i < MAX_MOBILES_PER_ENB; ++i) + UE_to_sched.next[i] = -1; + + int last_UE_id = -1; + for (int UE_id = UE_info->list.head; UE_id >= 0; UE_id = UE_info->list.next[UE_id]) { + UE_TEMPLATE *UE_template = &UE_info->UE_template[CC_id][UE_id]; + UE_sched_ctrl_t *ue_sched_ctrl = &UE_info->UE_sched_ctrl[UE_id]; + + /* initialize per-UE scheduling information */ + UE_template->pre_assigned_mcs_ul = 0; + UE_template->pre_allocated_nb_rb_ul = 0; + UE_template->pre_allocated_rb_table_index_ul = -1; + UE_template->pre_first_nb_rb_ul = 0; + UE_template->pre_dci_ul_pdu_idx = -1; + + const rnti_t rnti = UE_RNTI(Mod_id, UE_id); + if (rnti == NOT_A_RNTI) { + LOG_E(MAC, "UE %d has RNTI NOT_A_RNTI!\n", UE_id); + continue; + } + if (ue_sched_ctrl->cdrx_configured && !ue_sched_ctrl->in_active_time) + continue; + if (UE_info->UE_template[CC_id][UE_id].rach_resource_type > 0) + continue; - // Step 1.5: Calculate total_ue_count - for (UE_id = UE_list->head_ul; UE_id >= 0; UE_id = UE_list->next_ul[UE_id]) { - // This is not the actual CC_id in the list - for (n = 0; n < UE_list->numactiveULCCs[UE_id]; n++) { - CC_id = UE_list->ordered_ULCCids[n][UE_id]; - UE_template = &UE_list->UE_template[CC_id][UE_id]; + /* define UEs to schedule */ + if (UE_to_sched.head < 0) + UE_to_sched.head = UE_id; + else + UE_to_sched.next[last_UE_id] = UE_id; + UE_to_sched.next[UE_id] = -1; + last_UE_id = UE_id; + } - if (UE_template->pre_allocated_nb_rb_ul[slice_idx] > 0) { - total_ue_count[CC_id]++; - } + if (UE_to_sched.head < 0) + return; + + int last_rb_blocked = 1; + int n_contig = 0; + contig_rbs_t rbs[2]; // up to two contig RBs for PRACH in between + for (int i = 0; i < N_RB_UL; ++i) { + if (cc->vrb_map_UL[i] == 0 && last_rb_blocked == 1) { + last_rb_blocked = 0; + n_contig++; + AssertFatal(n_contig <= 2, "cannot handle more than two contiguous RB regions\n"); + rbs[n_contig - 1].start = i; + } + if (cc->vrb_map_UL[i] == 1 && last_rb_blocked == 0) { + last_rb_blocked = 1; + rbs[n_contig - 1].length = i - rbs[n_contig - 1].start; } } - // step 2: calculate the average rb per UE - LOG_D(MAC, "In ulsch_preprocessor: step2 \n"); - - for (UE_id = UE_list->head_ul; UE_id >= 0; UE_id = UE_list->next_ul[UE_id]) { - if (UE_list->UE_template[CC_id][UE_id].rach_resource_type > 0) continue; + round_robin_ul(Mod_id, + CC_id, + frameP, + subframeP, + sched_frameP, + sched_subframeP, + &UE_to_sched, + 4, // max_num_ue + n_contig, + rbs); + + // the following block is meant for validation of the pre-processor to check + // whether all UE allocations are non-overlapping and is not necessary for + // scheduling functionality +#ifdef DEBUG_eNB_SCHEDULER + char t[101] = "__________________________________________________" + "__________________________________________________"; + t[N_RB_UL] = 0; + for (int j = 0; j < N_RB_UL; j++) + if (cc->vrb_map_UL[j] != 0) + t[j] = 'x'; + int print = 0; + for (int UE_id = UE_info->list.head; UE_id >= 0; UE_id = UE_info->list.next[UE_id]) { + UE_TEMPLATE *UE_template = &UE_info->UE_template[CC_id][UE_id]; + if (UE_template->pre_allocated_nb_rb_ul == 0) + continue; - LOG_D(MAC, "In ulsch_preprocessor: handling UE %d/%x\n", + print = 1; + uint8_t harq_pid = subframe2harqpid(&RC.mac[Mod_id]->common_channels[CC_id], + sched_frameP, sched_subframeP); + LOG_D(MAC, "%4d.%d UE%d %d RBs (index %d) at start %d, pre MCS %d %s\n", + frameP, + subframeP, UE_id, - rntiTable[UE_id]); - - for (n = 0; n < UE_list->numactiveULCCs[UE_id]; n++) { - // This is the actual CC_id in the list - CC_id = UE_list->ordered_ULCCids[n][UE_id]; - LOG_D(MAC, "In ulsch_preprocessor: handling UE %d/%x CCid %d\n", - UE_id, - rntiTable[UE_id], - CC_id); - /* - if((mac_xface->get_nCCE_max(module_idP,CC_id,3,subframeP) - nCCE_to_be_used[CC_id]) > (1<<aggregation)) { - nCCE_to_be_used[CC_id] = nCCE_to_be_used[CC_id] + (1<<aggregation); - max_num_ue_to_be_scheduled+=1; - } */ - N_RB_UL = to_prb(eNB->common_channels[CC_id].ul_Bandwidth); - ue_sched_ctl = &UE_list->UE_sched_ctrl[UE_id]; - ue_sched_ctl->max_rbs_allowed_slice_uplink[CC_id][slice_idx] = - nb_rbs_allowed_slice(sli->ul[slice_idx].pct, N_RB_UL); - first_rb_offset = UE_list->first_rb_offset[CC_id][slice_idx]; - available_rbs = - cmin(ue_sched_ctl->max_rbs_allowed_slice_uplink[CC_id][slice_idx], N_RB_UL - first_rb[CC_id] - first_rb_offset); - - if (available_rbs < 0) - available_rbs = 0; - - if (total_ue_count[CC_id] == 0) { - average_rbs_per_user[CC_id] = 0; - } else if (total_ue_count[CC_id] == 1) { // increase the available RBs, special case, - average_rbs_per_user[CC_id] = (uint16_t) (available_rbs + 1); - } else if (total_ue_count[CC_id] <= available_rbs) { - average_rbs_per_user[CC_id] = (uint16_t) floor(available_rbs / total_ue_count[CC_id]); - } else { - average_rbs_per_user[CC_id] = 1; - LOG_W(MAC, "[eNB %d] frame %d subframe %d: UE %d CC %d: can't get average rb per user (should not be here)\n", - module_idP, - frameP, - subframeP, - UE_id, - CC_id); - } - - if (total_ue_count[CC_id] > 0) { - LOG_D(MAC, "[eNB %d] Frame %d subframe %d: total ue to be scheduled %d\n", - module_idP, - frameP, - subframeP, - total_ue_count[CC_id]); + UE_template->pre_allocated_nb_rb_ul, + UE_template->pre_allocated_rb_table_index_ul, + UE_template->pre_first_nb_rb_ul, + UE_template->pre_assigned_mcs_ul, + UE_info->UE_sched_ctrl[UE_id].round_UL[CC_id][harq_pid] > 0 ? "(retx)" : ""); + + for (int i = 0; i < UE_template->pre_allocated_nb_rb_ul; ++i) { + /* only check if this is not a retransmission */ + if (UE_info->UE_sched_ctrl[UE_id].round_UL[CC_id][harq_pid] == 0 + && cc->vrb_map_UL[UE_template->pre_first_nb_rb_ul + i] == 1) { + + LOG_I(MAC, "%4d.%d UL scheduler allocation list: %s\n", frameP, subframeP, t); + LOG_E(MAC, + "%4d.%d: UE %d allocated at locked RB %d (is: allocated start " + "%d/length %d)\n", + frameP, subframeP, UE_id, UE_template->pre_first_nb_rb_ul + i, + UE_template->pre_first_nb_rb_ul, + UE_template->pre_allocated_nb_rb_ul); } + cc->vrb_map_UL[UE_template->pre_first_nb_rb_ul + i] = 1; + t[UE_template->pre_first_nb_rb_ul + i] = UE_id + '0'; } } diff --git a/openair2/LAYER2/MAC/ra_procedures.c b/openair2/LAYER2/MAC/ra_procedures.c index 19b1c7708bdda98058923adc2365d5d3f890e22f..0d1afdf2a247814aed4ecac945051130544b4339 100644 --- a/openair2/LAYER2/MAC/ra_procedures.c +++ b/openair2/LAYER2/MAC/ra_procedures.c @@ -390,7 +390,7 @@ PRACH_RESOURCES_t *ue_get_rach(module_id_t module_idP, int CC_id, LOG_USEDINLOG_VAR(mac_rlc_status_resp_t,rlc_status)=mac_rlc_status_ind(module_idP, UE_mac_inst[module_idP].crnti, eNB_indexP, frameP, subframeP, - ENB_FLAG_NO, MBMS_FLAG_NO, DCCH, 6,0, 0 + ENB_FLAG_NO, MBMS_FLAG_NO, DCCH, 0, 0 ); if (UE_mac_inst[module_idP].crnti_before_ho) @@ -406,7 +406,7 @@ PRACH_RESOURCES_t *ue_get_rach(module_id_t module_idP, int CC_id, module_idP, frameP, rlc_status.bytes_in_buffer, dcch_header_len); - sdu_lengths = mac_rlc_data_req(module_idP, UE_mac_inst[module_idP].crnti, eNB_indexP, frameP, ENB_FLAG_NO, MBMS_FLAG_NO, DCCH, 6, //not used + sdu_lengths = mac_rlc_data_req(module_idP, UE_mac_inst[module_idP].crnti, eNB_indexP, frameP, ENB_FLAG_NO, MBMS_FLAG_NO, DCCH, 6, (char *) &ulsch_buff[0],0, 0 ); diff --git a/openair2/LAYER2/MAC/ue_procedures.c b/openair2/LAYER2/MAC/ue_procedures.c index 12058519152f1ac212f7b5248e38c78a81314410..c151c061bdc4defc0f5d082e3559403272eacfcb 100644 --- a/openair2/LAYER2/MAC/ue_procedures.c +++ b/openair2/LAYER2/MAC/ue_procedures.c @@ -2809,7 +2809,6 @@ update_bsr(module_id_t module_idP, frame_t frameP, rlc_status = mac_rlc_status_ind(module_idP, UE_mac_inst[module_idP].crnti,eNB_index,frameP,subframeP,ENB_FLAG_NO,MBMS_FLAG_NO, lcid, - 0xFFFF, //TBS is not used in RLC at this step, set a special value for debug 0, 0 ); lcid_bytes_in_buffer[lcid] = rlc_status.bytes_in_buffer; @@ -3176,7 +3175,7 @@ SLSCH_t *ue_get_slsch(module_id_t module_idP,int CC_id,frame_t frameP,sub_frame_ for (int j = 0; j < ue->numCommFlows; j++) { if ((ue->sourceL2Id > 0) && (ue->destinationList[j] >0) ) { rlc_status = mac_rlc_status_ind(module_idP, 0x1234,0,frameP,subframeP,ENB_FLAG_NO,MBMS_FLAG_NO, - ue->SL_LCID[i], 0xFFFF, ue->sourceL2Id, ue->destinationList[j]); + ue->SL_LCID[i], ue->sourceL2Id, ue->destinationList[j]); if (rlc_status.bytes_in_buffer > 2) { LOG_I(MAC,"SFN.SF %d.%d: Scheduling for %d bytes in Sidelink buffer\n",frameP,subframeP,rlc_status.bytes_in_buffer); diff --git a/openair2/LAYER2/NR_MAC_gNB/gNB_scheduler_phytest.c b/openair2/LAYER2/NR_MAC_gNB/gNB_scheduler_phytest.c index 1e0fd8d9a22b053328c8c9d59894790e99271170..6aba6e7e63c401bbdd521d7e62c261c6b3687837 100644 --- a/openair2/LAYER2/NR_MAC_gNB/gNB_scheduler_phytest.c +++ b/openair2/LAYER2/NR_MAC_gNB/gNB_scheduler_phytest.c @@ -562,7 +562,6 @@ void nr_schedule_uss_dlsch_phytest(module_id_t module_idP, ENB_FLAG_YES, MBMS_FLAG_NO, lcid, - TBS_bytes - ta_len - header_length_total - sdu_length_total - 3, 0, 0); @@ -579,7 +578,7 @@ void nr_schedule_uss_dlsch_phytest(module_id_t module_idP, ENB_FLAG_YES, MBMS_FLAG_NO, lcid, - TBS_bytes, + TBS_bytes - ta_len - header_length_total - sdu_length_total - 3, (char *)&mac_sdus[sdu_length_total], 0, 0); diff --git a/openair2/LAYER2/NR_MAC_gNB/gNB_scheduler_ulsch.c b/openair2/LAYER2/NR_MAC_gNB/gNB_scheduler_ulsch.c index ade520062734fe493d0431b960c4155c45cd431f..2fcccd682b3dbd1c6724d79be0fdb3f5ef218098 100644 --- a/openair2/LAYER2/NR_MAC_gNB/gNB_scheduler_ulsch.c +++ b/openair2/LAYER2/NR_MAC_gNB/gNB_scheduler_ulsch.c @@ -236,7 +236,7 @@ void nr_process_mac_pdu( void nr_rx_sdu(const module_id_t gnb_mod_idP, const int CC_idP, const frame_t frameP, - const sub_frame_t subframeP, + const sub_frame_t slotP, const rnti_t rntiP, uint8_t *sduP, const uint16_t sdu_lenP, @@ -260,7 +260,7 @@ void nr_rx_sdu(const module_id_t gnb_mod_idP, harq_pid, CC_idP, frameP, - subframeP, + slotP, UE_scheduling_control->round_UL[CC_idP][harq_pid], current_rnti, UE_id, diff --git a/openair2/LAYER2/RLC/AM_v9.3.0/rlc_am.c b/openair2/LAYER2/RLC/AM_v9.3.0/rlc_am.c index 865a81535946cd927d847a5e17d5c5c643982313..de947225bbd4e03ed1fa4f32bd8ab384f8d98346 100644 --- a/openair2/LAYER2/RLC/AM_v9.3.0/rlc_am.c +++ b/openair2/LAYER2/RLC/AM_v9.3.0/rlc_am.c @@ -459,7 +459,6 @@ struct mac_status_resp rlc_am_mac_status_indication ( const protocol_ctxt_t *const ctxt_pP, void *const rlc_pP, - const uint16_t tb_sizeP, struct mac_status_ind tx_statusP, const eNB_flag_t enb_flagP) { struct mac_status_resp status_resp; @@ -491,10 +490,6 @@ rlc_am_mac_status_indication ( rlc->last_absolute_subframe_status_indication = PROTOCOL_CTXT_TIME_MILLI_SECONDS(ctxt_pP); - if (tb_sizeP > 0) { - rlc->nb_bytes_requested_by_mac = tb_sizeP; - } - status_resp.buffer_occupancy_in_bytes = rlc_am_get_buffer_occupancy_in_bytes(ctxt_pP, rlc); // For eNB scheduler : Add Max RLC header size for new PDU @@ -549,8 +544,7 @@ rlc_am_mac_status_indication ( NULL,0, MSC_AS_TIME_FMT" "PROTOCOL_RLC_AM_MSC_FMT" STATUS-IND %u", MSC_AS_TIME_ARGS(ctxt_pP), - PROTOCOL_RLC_AM_MSC_ARGS(ctxt_pP, rlc), - tb_sizeP); + PROTOCOL_RLC_AM_MSC_ARGS(ctxt_pP, rlc)); MSC_LOG_TX_MESSAGE( (ctxt_pP->enb_flag == ENB_FLAG_YES) ? MSC_RLC_ENB:MSC_RLC_UE, (ctxt_pP->enb_flag == ENB_FLAG_YES) ? MSC_MAC_ENB:MSC_MAC_UE, @@ -565,26 +559,14 @@ rlc_am_mac_status_indication ( } if (LOG_DEBUGFLAG(DEBUG_RLC)) { - if (tb_sizeP > 0) { - LOG_UI(RLC, PROTOCOL_RLC_AM_CTXT_FMT" MAC_STATUS_INDICATION (DATA) %d bytes -> %d bytes\n", - PROTOCOL_RLC_AM_CTXT_ARGS(ctxt_pP,rlc), - tb_sizeP, - status_resp.buffer_occupancy_in_bytes); - } + LOG_UI(RLC, PROTOCOL_RLC_AM_CTXT_FMT" MAC_STATUS_INDICATION (DATA) -> %d bytes\n", + PROTOCOL_RLC_AM_CTXT_ARGS(ctxt_pP,rlc), + status_resp.buffer_occupancy_in_bytes); } return status_resp; } -//----------------------------------------------------------------------------- -void -rlc_am_set_nb_bytes_requested_by_mac ( - void *const rlc_pP, - const tb_size_t tb_sizeP -) { - ((rlc_am_entity_t *) rlc_pP)->nb_bytes_requested_by_mac = tb_sizeP; -} - //----------------------------------------------------------------------------- struct mac_data_req rlc_am_mac_data_request ( diff --git a/openair2/LAYER2/RLC/AM_v9.3.0/rlc_am.h b/openair2/LAYER2/RLC/AM_v9.3.0/rlc_am.h index f2cb456e8cfb94816d46d77cecbb4e260cec5990..3127f67eca85a575bba23d012267d5acb16f9ed6 100644 --- a/openair2/LAYER2/RLC/AM_v9.3.0/rlc_am.h +++ b/openair2/LAYER2/RLC/AM_v9.3.0/rlc_am.h @@ -255,23 +255,15 @@ rlc_am_get_pdus ( */ void rlc_am_rx (const protocol_ctxt_t* const ctxtP,void * const rlc_pP, struct mac_data_ind); -/*! \fn struct mac_status_resp rlc_am_mac_status_indication (const protocol_ctxt_t* const ctxtP,void * const rlc_pP, uint16_t tbs_sizeP, struct mac_status_ind tx_statusP,const eNB_flag_t enb_flagP) +/*! \fn struct mac_status_resp rlc_am_mac_status_indication (const protocol_ctxt_t* const ctxtP,void * const rlc_pP, struct mac_status_ind tx_statusP,const eNB_flag_t enb_flagP) * \brief Request the maximum number of bytes that can be served by RLC instance to MAC and fix the amount of bytes requested by MAC for next RLC transmission. * \param[in] ctxt_pP Running context. * \param[in] rlc_pP RLC AM protocol instance pointer. -* \param[in] tbs_sizeP Number of bytes requested by MAC for next transmission. * \param[in] tx_statusP Transmission status given by MAC on previous MAC transmission of the PDU. * \param[in] enb_flagP eNB or UE flag indication. * \return The maximum number of bytes that can be served by RLC instance to MAC. */ -struct mac_status_resp rlc_am_mac_status_indication (const protocol_ctxt_t* const ctxtP, void * const rlc_pP, uint16_t tbs_sizeP, struct mac_status_ind tx_statusP,const eNB_flag_t enb_flagP); - -/*! \fn void rlc_am_set_nb_bytes_requested_by_mac (void * const rlc_pP,const tb_size_t tb_sizeP) -* \brief Set available TBS for RLC Tx just before am_mac_data_request. Used for UE only. -* \param[in] rlc_pP RLC AM protocol instance pointer. -* \param[in] tb_sizeP Available Tx Transport Block size in bytes. -*/ -void rlc_am_set_nb_bytes_requested_by_mac (void * const rlc_pP,const tb_size_t tb_sizeP); +struct mac_status_resp rlc_am_mac_status_indication (const protocol_ctxt_t* const ctxtP, void * const rlc_pP, struct mac_status_ind tx_statusP,const eNB_flag_t enb_flagP); /*! \fn struct mac_data_req rlc_am_mac_data_request (const protocol_ctxt_t* const ctxtP,void * const rlc_pP,const eNB_flag_t enb_flagP) * \brief Gives PDUs to lower layer MAC. diff --git a/openair2/LAYER2/RLC/TM_v9.3.0/rlc_tm.c b/openair2/LAYER2/RLC/TM_v9.3.0/rlc_tm.c index e481550a4604dd508575ba89271b5c71764a881a..4e3fffe176e3ba32917a38bf44c9d13e21536fc8 100644 --- a/openair2/LAYER2/RLC/TM_v9.3.0/rlc_tm.c +++ b/openair2/LAYER2/RLC/TM_v9.3.0/rlc_tm.c @@ -151,13 +151,10 @@ struct mac_status_resp rlc_tm_mac_status_indication ( const protocol_ctxt_t* const ctxt_pP, void * const rlc_pP, - const tb_size_t tb_sizeP, struct mac_status_ind tx_statusP) { struct mac_status_resp status_resp; - ((rlc_tm_entity_t *) rlc_pP)->rlc_pdu_size = tb_sizeP; - status_resp.buffer_occupancy_in_bytes = ((rlc_tm_entity_t *) rlc_pP)->buffer_occupancy; status_resp.buffer_occupancy_in_pdus = status_resp.buffer_occupancy_in_bytes / ((rlc_tm_entity_t *) rlc_pP)->rlc_pdu_size; status_resp.rlc_info.rlc_protocol_state = ((rlc_tm_entity_t *) rlc_pP)->protocol_state; diff --git a/openair2/LAYER2/RLC/TM_v9.3.0/rlc_tm.h b/openair2/LAYER2/RLC/TM_v9.3.0/rlc_tm.h index 1ea99887071397ebccb8c2b9f9c7d5ceaf92ff3d..d2bab33b1a428fe703cac72a8fd094c5b9f35a0c 100644 --- a/openair2/LAYER2/RLC/TM_v9.3.0/rlc_tm.h +++ b/openair2/LAYER2/RLC/TM_v9.3.0/rlc_tm.h @@ -88,11 +88,10 @@ void rlc_tm_rx ( struct mac_data_ind data_indP); -/*! \fn struct mac_status_resp rlc_tm_mac_status_indication (const protocol_ctxt_t* const ctxt_pP, void * const rlcP, const uint16_t tbs_sizeP, struct mac_status_ind tx_statusP) +/*! \fn struct mac_status_resp rlc_tm_mac_status_indication (const protocol_ctxt_t* const ctxt_pP, void * const rlcP, struct mac_status_ind tx_statusP) * \brief Request the maximum number of bytes that can be served by RLC instance to MAC and fix the amount of bytes requested by MAC for next RLC transmission. * \param[in] ctxtP Running context. * \param[in] rlcP RLC TM protocol instance pointer. -* \param[in] tbs_sizeP Number of bytes requested by MAC for next transmission. * \param[in] tx_statusP Transmission status given by MAC on previous MAC transmission of the PDU. * \return The maximum number of bytes that can be served by RLC instance to MAC. */ @@ -100,7 +99,6 @@ struct mac_status_resp rlc_tm_mac_status_indication ( const protocol_ctxt_t* const ctxt_pP, void * const rlc_pP, - const tb_size_t tb_sizeP, struct mac_status_ind tx_statusP); diff --git a/openair2/LAYER2/RLC/UM_v9.3.0/rlc_um.c b/openair2/LAYER2/RLC/UM_v9.3.0/rlc_um.c index c7dc11f51dc62dfe4d615d427b5d45ce2d3edbd5..654ddb8da7e5d13c69a53cac2e045f086c8dbe61 100644 --- a/openair2/LAYER2/RLC/UM_v9.3.0/rlc_um.c +++ b/openair2/LAYER2/RLC/UM_v9.3.0/rlc_um.c @@ -370,7 +370,7 @@ rlc_um_rx (const protocol_ctxt_t *const ctxt_pP, void *argP, struct mac_data_ind //----------------------------------------------------------------------------- struct mac_status_resp -rlc_um_mac_status_indication (const protocol_ctxt_t *const ctxt_pP, void *rlc_pP, uint16_t tbs_sizeP, struct mac_status_ind tx_statusP,const eNB_flag_t enb_flagP) { +rlc_um_mac_status_indication (const protocol_ctxt_t *const ctxt_pP, void *rlc_pP, struct mac_status_ind tx_statusP,const eNB_flag_t enb_flagP) { struct mac_status_resp status_resp; uint16_t sdu_size = 0; uint16_t sdu_remaining_size = 0; @@ -386,7 +386,6 @@ rlc_um_mac_status_indication (const protocol_ctxt_t *const ctxt_pP, void *rlc_pP if (rlc_pP) { status_resp.rlc_info.rlc_protocol_state = rlc_p->protocol_state; rlc_um_check_timer_dar_time_out(ctxt_pP, rlc_p); - rlc_p->nb_bytes_requested_by_mac = tbs_sizeP; status_resp.buffer_occupancy_in_bytes = rlc_um_get_buffer_occupancy (rlc_p); if ((status_resp.buffer_occupancy_in_bytes > 0) && ((mb_p = list_get_head(&rlc_p->input_sdus)) != NULL)) { @@ -416,9 +415,8 @@ rlc_um_mac_status_indication (const protocol_ctxt_t *const ctxt_pP, void *rlc_pP if (LOG_DEBUGFLAG(DEBUG_RLC)) { if (( rlc_p->rb_id > 0) && (status_resp.buffer_occupancy_in_bytes > 0)) { - LOG_UI(RLC, PROTOCOL_RLC_UM_CTXT_FMT"MAC_STATUS_INDICATION (DATA) %d bytes requested -> %d bytes available\n", + LOG_UI(RLC, PROTOCOL_RLC_UM_CTXT_FMT"MAC_STATUS_INDICATION (DATA) -> %d bytes available\n", PROTOCOL_RLC_UM_CTXT_ARGS(ctxt_pP,rlc_p), - tbs_sizeP, status_resp.buffer_occupancy_in_bytes); if ((tx_statusP.tx_status == MAC_TX_STATUS_SUCCESSFUL) && (tx_statusP.no_pdu)) { @@ -441,15 +439,6 @@ rlc_um_mac_status_indication (const protocol_ctxt_t *const ctxt_pP, void *rlc_pP return status_resp; } -//----------------------------------------------------------------------------- -void -rlc_um_set_nb_bytes_requested_by_mac ( - void *rlc_pP, - const tb_size_t tb_sizeP -) { - ((rlc_um_entity_t *) rlc_pP)->nb_bytes_requested_by_mac = tb_sizeP; -} - //----------------------------------------------------------------------------- struct mac_data_req rlc_um_mac_data_request (const protocol_ctxt_t *const ctxt_pP, void *rlc_pP,const eNB_flag_t enb_flagP) { diff --git a/openair2/LAYER2/RLC/UM_v9.3.0/rlc_um.h b/openair2/LAYER2/RLC/UM_v9.3.0/rlc_um.h index 8000196b32d7ec033d0a9af9099320e8d9db2b79..be06551dde7c7ee50ac1d91be3e707ad3f019c7d 100644 --- a/openair2/LAYER2/RLC/UM_v9.3.0/rlc_um.h +++ b/openair2/LAYER2/RLC/UM_v9.3.0/rlc_um.h @@ -160,27 +160,15 @@ rlc_um_get_pdus (const protocol_ctxt_t* const ctxt_pP, void *argP); */ void rlc_um_rx (const protocol_ctxt_t* const ctxt_pP, void *argP, struct mac_data_ind data_indP); -/*! \fn struct mac_status_resp rlc_um_mac_status_indication (const protocol_ctxt_t* const ctxt_pP, rlc_um_entity_t * const rlc_pP, uint16_t tbs_sizeP, struct mac_status_ind tx_statusP) +/*! \fn struct mac_status_resp rlc_um_mac_status_indication (const protocol_ctxt_t* const ctxt_pP, rlc_um_entity_t * const rlc_pP, struct mac_status_ind tx_statusP) * \brief Request the maximum number of bytes that can be served by RLC instance to MAC and fix the amount of bytes requested by MAC for next RLC transmission. * \param[in] ctxt_pP Running context. * \param[in] rlc_pP RLC UM protocol instance pointer. -* \param[in] tbs_sizeP Number of bytes requested by MAC for next transmission. * \param[in] tx_statusP Transmission status given by MAC on previous MAC transmission of the PDU. * \return The maximum number of bytes that can be served by RLC instance to MAC. */ struct mac_status_resp -rlc_um_mac_status_indication (const protocol_ctxt_t* const ctxt_pP, void *rlc_pP, uint16_t tbs_sizeP, struct mac_status_ind tx_statusP,const eNB_flag_t enb_flagP); - -/*! \fn void rlc_um_set_nb_bytes_requested_by_mac (rlc_um_entity_t * const rlc_pP, const tb_size_t tb_sizeP) -* \brief Set available TBS size for MAC Tx. -* \param[in] rlc_pP RLC UM protocol instance pointer. -* \param[in] tb_sizeP remaining TBS in bytes. -*/ -void -rlc_um_set_nb_bytes_requested_by_mac ( - void * rlc_pP, - const tb_size_t tb_sizeP -); +rlc_um_mac_status_indication (const protocol_ctxt_t* const ctxt_pP, void *rlc_pP, struct mac_status_ind tx_statusP,const eNB_flag_t enb_flagP); /*! \fn struct mac_data_req rlc_um_mac_data_request (const protocol_ctxt_t* const ctxt_pP, rlc_um_entity_t * const rlc_pP,const eNB_flag_t enb_flagP) * \brief Gives PDUs to lower layer MAC. diff --git a/openair2/LAYER2/RLC/rlc.h b/openair2/LAYER2/RLC/rlc.h index b337bcac7eaa3b167debe04eb8d338540ef3a1a1..27ca18ed7ee9d2b712254eb43ffbb64850ac78c2 100644 --- a/openair2/LAYER2/RLC/rlc.h +++ b/openair2/LAYER2/RLC/rlc.h @@ -391,7 +391,7 @@ void rrc_rlc_register_rrc (rrc_data_ind_cb_t rrc_data_indP, rrc_data_conf_cb_t r * \param [in] eNB_flagP Flag to indicate eNB (1) or UE (0) * \param [in] MBMS_flagP Flag to indicate whether this is the MBMS service (1) or not (0) * \param [in] rb_idP Radio bearer identifier. -* \param [in] tb_sizeP Available Tx TBS in bytes. For UE only. +* \param [in] tb_sizeP Requested Tx TBS in bytes. * \param [in,out] bufferP Memory area to fill with the bytes requested by MAC. * \return A status about the processing, OK or error code. */ @@ -416,7 +416,7 @@ tbs_size_t mac_rlc_data_req (const module_id_t, const rnti_t, con void mac_rlc_data_ind (const module_id_t, const rnti_t, const eNB_index_t,const frame_t, const eNB_flag_t, const MBMS_flag_t, logical_chan_id_t, char *, tb_size_t, num_tb_t, crc_t * ); -/*! \fn mac_rlc_status_resp_t mac_rlc_status_ind (const module_id_t mod_idP, const rnti_t rntiP, const frame_t frameP, const sub_frame_t subframeP, const eNB_flag_t eNB_flagP, const MBMS_flag_t MBMS_flagP, logical_chan_id_t rb_idP, tb_size_t tb_sizeP) +/*! \fn mac_rlc_status_resp_t mac_rlc_status_ind (const module_id_t mod_idP, const rnti_t rntiP, const frame_t frameP, const sub_frame_t subframeP, const eNB_flag_t eNB_flagP, const MBMS_flag_t MBMS_flagP, logical_chan_id_t rb_idP) * \brief Interface with MAC layer, request and set the number of bytes scheduled for transmission by the RLC instance corresponding to the radio bearer identifier. * \param[in] mod_idP Virtualized module identifier. * \param[in] rntiP UE identifier. @@ -425,10 +425,9 @@ void mac_rlc_data_ind (const module_id_t, const rnti_t, con * \param[in] eNB_flagP Flag to indicate eNB operation (1 true, 0 false) * \param[in] MBMS_flagP Flag to indicate whether this is the MBMS service (1) or not (0) * \param[in] rb_idP Radio bearer identifier. -* \param[in] tb_sizeP Size of a transport block set in bytes. * \return The maximum number of bytes that the RLC instance can send in the next transmission sequence. */ -mac_rlc_status_resp_t mac_rlc_status_ind (const module_id_t, const rnti_t, const eNB_index_t, const frame_t, const sub_frame_t, const eNB_flag_t, const MBMS_flag_t, logical_chan_id_t, tb_size_t +mac_rlc_status_resp_t mac_rlc_status_ind (const module_id_t, const rnti_t, const eNB_index_t, const frame_t, const sub_frame_t, const eNB_flag_t, const MBMS_flag_t, logical_chan_id_t ,const uint32_t sourceL2Id ,const uint32_t destinationL2Id ); diff --git a/openair2/LAYER2/RLC/rlc_mac.c b/openair2/LAYER2/RLC/rlc_mac.c index 9cf6cb739a05f4f43523d004fb18911cb71f7b8b..89cbe4c406c0e34dc0c981ffd9e66d6c634c56a7 100644 --- a/openair2/LAYER2/RLC/rlc_mac.c +++ b/openair2/LAYER2/RLC/rlc_mac.c @@ -191,20 +191,19 @@ tbs_size_t mac_rlc_data_req( case RLC_MODE_AM: rlc_am_mui.rrc_mui_num = 0; - if (!enb_flagP) rlc_am_set_nb_bytes_requested_by_mac(&rlc_union_p->rlc.am,tb_sizeP); - + ((rlc_am_entity_t *) &rlc_union_p->rlc.am)->nb_bytes_requested_by_mac = tb_sizeP; data_request = rlc_am_mac_data_request(&ctxt, &rlc_union_p->rlc.am,enb_flagP); ret_tb_size =mac_rlc_serialize_tb(buffer_pP, data_request.data); break; case RLC_MODE_UM: - if (!enb_flagP) rlc_um_set_nb_bytes_requested_by_mac(&rlc_union_p->rlc.um,tb_sizeP); - + ((rlc_um_entity_t *) &rlc_union_p->rlc.um)->nb_bytes_requested_by_mac = tb_sizeP; data_request = rlc_um_mac_data_request(&ctxt, &rlc_union_p->rlc.um,enb_flagP); ret_tb_size = mac_rlc_serialize_tb(buffer_pP, data_request.data); break; case RLC_MODE_TM: + ((rlc_tm_entity_t *) &rlc_union_p->rlc.tm)->rlc_pdu_size = tb_sizeP; data_request = rlc_tm_mac_data_request(&ctxt, &rlc_union_p->rlc.tm); ret_tb_size = mac_rlc_serialize_tb(buffer_pP, data_request.data); break; @@ -317,7 +316,6 @@ mac_rlc_status_resp_t mac_rlc_status_ind( const eNB_flag_t enb_flagP, const MBMS_flag_t MBMS_flagP, const logical_chan_id_t channel_idP, - const tb_size_t tb_sizeP, const uint32_t sourceL2Id, const uint32_t destinationL2Id ) { @@ -370,7 +368,7 @@ mac_rlc_status_resp_t mac_rlc_status_ind( break; case RLC_MODE_AM: - status_resp = rlc_am_mac_status_indication(&ctxt, &rlc_union_p->rlc.am, tb_sizeP, tx_status,enb_flagP); + status_resp = rlc_am_mac_status_indication(&ctxt, &rlc_union_p->rlc.am, tx_status,enb_flagP); mac_rlc_status_resp.bytes_in_buffer = status_resp.buffer_occupancy_in_bytes; mac_rlc_status_resp.head_sdu_creation_time = status_resp.head_sdu_creation_time; mac_rlc_status_resp.head_sdu_remaining_size_to_send = status_resp.head_sdu_remaining_size_to_send; @@ -379,7 +377,7 @@ mac_rlc_status_resp_t mac_rlc_status_ind( break; case RLC_MODE_UM: - status_resp = rlc_um_mac_status_indication(&ctxt, &rlc_union_p->rlc.um, tb_sizeP, tx_status, enb_flagP); + status_resp = rlc_um_mac_status_indication(&ctxt, &rlc_union_p->rlc.um, tx_status, enb_flagP); mac_rlc_status_resp.bytes_in_buffer = status_resp.buffer_occupancy_in_bytes; mac_rlc_status_resp.pdus_in_buffer = status_resp.buffer_occupancy_in_pdus; mac_rlc_status_resp.head_sdu_creation_time = status_resp.head_sdu_creation_time; @@ -389,7 +387,7 @@ mac_rlc_status_resp_t mac_rlc_status_ind( break; case RLC_MODE_TM: - status_resp = rlc_tm_mac_status_indication(&ctxt, &rlc_union_p->rlc.tm, tb_sizeP, tx_status); + status_resp = rlc_tm_mac_status_indication(&ctxt, &rlc_union_p->rlc.tm, tx_status); mac_rlc_status_resp.bytes_in_buffer = status_resp.buffer_occupancy_in_bytes; mac_rlc_status_resp.pdus_in_buffer = status_resp.buffer_occupancy_in_pdus; // return mac_rlc_status_resp; diff --git a/openair2/LAYER2/nr_rlc/nr_rlc_oai_api.c b/openair2/LAYER2/nr_rlc/nr_rlc_oai_api.c index 88bde65107f5d3cf8d260175f53eb95bde85b505..20311ef9675c4e33f24d7c87eb83a241c62032d8 100644 --- a/openair2/LAYER2/nr_rlc/nr_rlc_oai_api.c +++ b/openair2/LAYER2/nr_rlc/nr_rlc_oai_api.c @@ -152,7 +152,6 @@ mac_rlc_status_resp_t mac_rlc_status_ind( const eNB_flag_t enb_flagP, const MBMS_flag_t MBMS_flagP, const logical_chan_id_t channel_idP, - const tb_size_t tb_sizeP, const uint32_t sourceL2Id, const uint32_t destinationL2Id ) @@ -189,7 +188,6 @@ mac_rlc_status_resp_t mac_rlc_status_ind( ret.bytes_in_buffer = buf_stat.status_size + buf_stat.retx_size + buf_stat.tx_size; - ue->saved_status_ind_tb_size[channel_idP - 1] = tb_sizeP; } else { ret.bytes_in_buffer = 0; } diff --git a/openair2/LAYER2/openair2_proc.c b/openair2/LAYER2/openair2_proc.c index 32c4d9788cf84a59afe502babf54db8fd4a6044c..bbdc55e0366098cf0e284bea75e758fda3bc5007 100644 --- a/openair2/LAYER2/openair2_proc.c +++ b/openair2/LAYER2/openair2_proc.c @@ -91,12 +91,12 @@ int dump_eNB_l2_stats(char *buffer, int length) { number_of_cards=NB_eNB_INST; #endif eNB_MAC_INST *eNB; - UE_list_t *UE_list; + UE_info_t *UE_info; for (eNB_id=0; eNB_id<number_of_cards; eNB_id++) { /* reset the values */ eNB = RC.mac[eNB_id]; - UE_list = &eNB->UE_list; + UE_info = &eNB->UE_info; for (CC_id=0 ; CC_id < MAX_NUM_CCs; CC_id++) { eNB->eNB_stats[CC_id].dlsch_bitrate= 0; @@ -141,76 +141,76 @@ int dump_eNB_l2_stats(char *buffer, int length) { len += sprintf(&buffer[len],"\n"); - for (UE_id=UE_list->head; UE_id>=0; UE_id=UE_list->next[UE_id]) { - for (i=0; i<UE_list->numactiveCCs[UE_id]; i++) { - CC_id=UE_list->ordered_CCids[i][UE_id]; - UE_list->eNB_UE_stats[CC_id][UE_id].dlsch_bitrate=((UE_list->eNB_UE_stats[CC_id][UE_id].TBS*8)/((eNB->frame + 1)*10)); - UE_list->eNB_UE_stats[CC_id][UE_id].total_dlsch_bitrate= ((UE_list->eNB_UE_stats[CC_id][UE_id].total_pdu_bytes*8)/((eNB->frame + 1)*10)); - UE_list->eNB_UE_stats[CC_id][UE_id].total_overhead_bytes+= UE_list->eNB_UE_stats[CC_id][UE_id].overhead_bytes; - UE_list->eNB_UE_stats[CC_id][UE_id].avg_overhead_bytes=((UE_list->eNB_UE_stats[CC_id][UE_id].total_overhead_bytes*8)/((eNB->frame + 1)*10)); - UE_list->eNB_UE_stats[CC_id][UE_id].ulsch_bitrate=((UE_list->eNB_UE_stats[CC_id][UE_id].ulsch_TBS*8)/((eNB->frame + 1)*10)); - UE_list->eNB_UE_stats[CC_id][UE_id].total_ulsch_bitrate= ((UE_list->eNB_UE_stats[CC_id][UE_id].total_pdu_bytes_rx*8)/((eNB->frame + 1)*10)); + for (UE_id=UE_info->list.head; UE_id>=0; UE_id=UE_info->list.next[UE_id]) { + for (i=0; i<UE_info->numactiveCCs[UE_id]; i++) { + CC_id=UE_info->ordered_CCids[i][UE_id]; + UE_info->eNB_UE_stats[CC_id][UE_id].dlsch_bitrate=((UE_info->eNB_UE_stats[CC_id][UE_id].TBS*8)/((eNB->frame + 1)*10)); + UE_info->eNB_UE_stats[CC_id][UE_id].total_dlsch_bitrate= ((UE_info->eNB_UE_stats[CC_id][UE_id].total_pdu_bytes*8)/((eNB->frame + 1)*10)); + UE_info->eNB_UE_stats[CC_id][UE_id].total_overhead_bytes+= UE_info->eNB_UE_stats[CC_id][UE_id].overhead_bytes; + UE_info->eNB_UE_stats[CC_id][UE_id].avg_overhead_bytes=((UE_info->eNB_UE_stats[CC_id][UE_id].total_overhead_bytes*8)/((eNB->frame + 1)*10)); + UE_info->eNB_UE_stats[CC_id][UE_id].ulsch_bitrate=((UE_info->eNB_UE_stats[CC_id][UE_id].ulsch_TBS*8)/((eNB->frame + 1)*10)); + UE_info->eNB_UE_stats[CC_id][UE_id].total_ulsch_bitrate= ((UE_info->eNB_UE_stats[CC_id][UE_id].total_pdu_bytes_rx*8)/((eNB->frame + 1)*10)); len += sprintf(&buffer[len],"[MAC] UE %d (DLSCH),status %s, RNTI %x : CQI %d, MCS1 %d, MCS2 %d, RB (tx %d, retx %d, total %d), ncce (tx %d, retx %d) \n", UE_id, - map_int_to_str(rrc_status_names, UE_list->eNB_UE_stats[CC_id][UE_id].rrc_status), - UE_list->eNB_UE_stats[CC_id][UE_id].crnti, - UE_list->UE_sched_ctrl[UE_id].dl_cqi[CC_id], - UE_list->eNB_UE_stats[CC_id][UE_id].dlsch_mcs1, - UE_list->eNB_UE_stats[CC_id][UE_id].dlsch_mcs2, - UE_list->eNB_UE_stats[CC_id][UE_id].rbs_used, - UE_list->eNB_UE_stats[CC_id][UE_id].rbs_used_retx, - UE_list->eNB_UE_stats[CC_id][UE_id].total_rbs_used, - UE_list->eNB_UE_stats[CC_id][UE_id].ncce_used, - UE_list->eNB_UE_stats[CC_id][UE_id].ncce_used_retx + map_int_to_str(rrc_status_names, UE_info->eNB_UE_stats[CC_id][UE_id].rrc_status), + UE_info->eNB_UE_stats[CC_id][UE_id].crnti, + UE_info->UE_sched_ctrl[UE_id].dl_cqi[CC_id], + UE_info->eNB_UE_stats[CC_id][UE_id].dlsch_mcs1, + UE_info->eNB_UE_stats[CC_id][UE_id].dlsch_mcs2, + UE_info->eNB_UE_stats[CC_id][UE_id].rbs_used, + UE_info->eNB_UE_stats[CC_id][UE_id].rbs_used_retx, + UE_info->eNB_UE_stats[CC_id][UE_id].total_rbs_used, + UE_info->eNB_UE_stats[CC_id][UE_id].ncce_used, + UE_info->eNB_UE_stats[CC_id][UE_id].ncce_used_retx ); len += sprintf(&buffer[len], "[MAC] DLSCH bitrate (TTI %d, avg %d), Transmitted bytes " "(TTI %d, total %"PRIu64"), Total Transmitted PDU %d, Overhead " "(TTI %"PRIu64", total %"PRIu64", avg %"PRIu64")\n", - UE_list->eNB_UE_stats[CC_id][UE_id].dlsch_bitrate, - UE_list->eNB_UE_stats[CC_id][UE_id].total_dlsch_bitrate, - UE_list->eNB_UE_stats[CC_id][UE_id].TBS, - UE_list->eNB_UE_stats[CC_id][UE_id].total_pdu_bytes, - UE_list->eNB_UE_stats[CC_id][UE_id].total_num_pdus, - UE_list->eNB_UE_stats[CC_id][UE_id].overhead_bytes, - UE_list->eNB_UE_stats[CC_id][UE_id].total_overhead_bytes, - UE_list->eNB_UE_stats[CC_id][UE_id].avg_overhead_bytes + UE_info->eNB_UE_stats[CC_id][UE_id].dlsch_bitrate, + UE_info->eNB_UE_stats[CC_id][UE_id].total_dlsch_bitrate, + UE_info->eNB_UE_stats[CC_id][UE_id].TBS, + UE_info->eNB_UE_stats[CC_id][UE_id].total_pdu_bytes, + UE_info->eNB_UE_stats[CC_id][UE_id].total_num_pdus, + UE_info->eNB_UE_stats[CC_id][UE_id].overhead_bytes, + UE_info->eNB_UE_stats[CC_id][UE_id].total_overhead_bytes, + UE_info->eNB_UE_stats[CC_id][UE_id].avg_overhead_bytes ); len += sprintf(&buffer[len],"[MAC] UE %d (ULSCH), Status %s, Failute timer %d, RNTI %x : snr (%d, target %d), MCS (pre %d, post %d), RB (rx %d, retx %d, total %d), Current TBS %d \n", UE_id, - map_int_to_str(rrc_status_names, UE_list->eNB_UE_stats[CC_id][UE_id].rrc_status), - UE_list->UE_sched_ctrl[UE_id].ul_failure_timer, - UE_list->eNB_UE_stats[CC_id][UE_id].crnti, - UE_list->eNB_UE_stats[CC_id][UE_id].snr, - UE_list->eNB_UE_stats[CC_id][UE_id].target_snr, - UE_list->eNB_UE_stats[CC_id][UE_id].ulsch_mcs1, - UE_list->eNB_UE_stats[CC_id][UE_id].ulsch_mcs2, - UE_list->eNB_UE_stats[CC_id][UE_id].rbs_used_rx, - UE_list->eNB_UE_stats[CC_id][UE_id].rbs_used_retx_rx, - UE_list->eNB_UE_stats[CC_id][UE_id].total_rbs_used_rx, - UE_list->eNB_UE_stats[CC_id][UE_id].ulsch_TBS + map_int_to_str(rrc_status_names, UE_info->eNB_UE_stats[CC_id][UE_id].rrc_status), + UE_info->UE_sched_ctrl[UE_id].ul_failure_timer, + UE_info->eNB_UE_stats[CC_id][UE_id].crnti, + UE_info->eNB_UE_stats[CC_id][UE_id].snr, + UE_info->eNB_UE_stats[CC_id][UE_id].target_snr, + UE_info->eNB_UE_stats[CC_id][UE_id].ulsch_mcs1, + UE_info->eNB_UE_stats[CC_id][UE_id].ulsch_mcs2, + UE_info->eNB_UE_stats[CC_id][UE_id].rbs_used_rx, + UE_info->eNB_UE_stats[CC_id][UE_id].rbs_used_retx_rx, + UE_info->eNB_UE_stats[CC_id][UE_id].total_rbs_used_rx, + UE_info->eNB_UE_stats[CC_id][UE_id].ulsch_TBS ); len += sprintf(&buffer[len], "[MAC] ULSCH bitrate (TTI %d, avg %d), received bytes (total %"PRIu64")," "Total received PDU %d, Total errors %d\n", - UE_list->eNB_UE_stats[CC_id][UE_id].ulsch_bitrate, - UE_list->eNB_UE_stats[CC_id][UE_id].total_ulsch_bitrate, - UE_list->eNB_UE_stats[CC_id][UE_id].total_pdu_bytes_rx, - UE_list->eNB_UE_stats[CC_id][UE_id].total_num_pdus_rx, - UE_list->eNB_UE_stats[CC_id][UE_id].num_errors_rx); - len+= sprintf(&buffer[len],"[MAC] Received PHR PH = %d (db)\n", UE_list->UE_template[CC_id][UE_id].phr_info); + UE_info->eNB_UE_stats[CC_id][UE_id].ulsch_bitrate, + UE_info->eNB_UE_stats[CC_id][UE_id].total_ulsch_bitrate, + UE_info->eNB_UE_stats[CC_id][UE_id].total_pdu_bytes_rx, + UE_info->eNB_UE_stats[CC_id][UE_id].total_num_pdus_rx, + UE_info->eNB_UE_stats[CC_id][UE_id].num_errors_rx); + len+= sprintf(&buffer[len],"[MAC] Received PHR PH = %d (db)\n", UE_info->UE_template[CC_id][UE_id].phr_info); len+= sprintf(&buffer[len],"[MAC] Estimated size LCGID[0][1][2][3] = %u %u %u %u\n", - UE_list->UE_template[CC_id][UE_id].ul_buffer_info[LCGID0], - UE_list->UE_template[CC_id][UE_id].ul_buffer_info[LCGID1], - UE_list->UE_template[CC_id][UE_id].ul_buffer_info[LCGID2], - UE_list->UE_template[CC_id][UE_id].ul_buffer_info[LCGID3] + UE_info->UE_template[CC_id][UE_id].ul_buffer_info[LCGID0], + UE_info->UE_template[CC_id][UE_id].ul_buffer_info[LCGID1], + UE_info->UE_template[CC_id][UE_id].ul_buffer_info[LCGID2], + UE_info->UE_template[CC_id][UE_id].ul_buffer_info[LCGID3] ); } PROTOCOL_CTXT_SET_BY_MODULE_ID(&ctxt, eNB_id, ENB_FLAG_YES, - UE_list->eNB_UE_stats[0][UE_id].crnti,//UE_PCCID(eNB_id,UE_id)][UE_id].crnti, + UE_info->eNB_UE_stats[0][UE_id].crnti,//UE_PCCID(eNB_id,UE_id)][UE_id].crnti, eNB->frame, eNB->subframe, eNB_id); @@ -509,7 +509,7 @@ int openair2_stats_read(char *buffer, char **my_buffer, off_t off, int length) { for(i=1; i<=NB_CNX_CH; i++) { if (CH_mac_inst[Mod_id].Dcch_lchan[i].Active==1) { len+=sprintf(&buffer[len],"\nMR index %u: DL SINR (feedback) %d dB, CQI: %s\n\n", - i,//CH_rrc_inst[Mod_id].Info.UE_list[i].L2_id[0], + i,//CH_rrc_inst[Mod_id].Info.UE_info[i].L2_id[0], CH_mac_inst[Mod_id].Def_meas[i].Wideband_sinr, print_cqi(CH_mac_inst[Mod_id].Def_meas[i].cqi)); len+=sprintf(&buffer[len], diff --git a/openair2/NR_PHY_INTERFACE/NR_IF_Module.c b/openair2/NR_PHY_INTERFACE/NR_IF_Module.c index 91c75ac67fdf1bf90644af4e76ae8bbad8352e5f..4dacef3dbb885be77fad003e260f51157025baa6 100644 --- a/openair2/NR_PHY_INTERFACE/NR_IF_Module.c +++ b/openair2/NR_PHY_INTERFACE/NR_IF_Module.c @@ -54,34 +54,32 @@ extern uint16_t sf_ahead; extern uint16_t sl_ahead; void handle_nr_rach(NR_UL_IND_t *UL_info) { - if (UL_info->rach_ind.rach_indication_body.number_of_preambles>0) { - AssertFatal(UL_info->rach_ind.rach_indication_body.number_of_preambles==1,"More than 1 preamble not supported\n"); - UL_info->rach_ind.rach_indication_body.number_of_preambles=0; - LOG_D(MAC,"UL_info[Frame %d, Slot %d] Calling initiate_ra_proc RACH:SFN/SF:%d\n",UL_info->frame,UL_info->slot, NFAPI_SFNSF2DEC(UL_info->rach_ind.sfn_sf)); - /* - initiate_ra_proc(UL_info->module_id, - - UL_info->CC_id, - NFAPI_SFNSF2SFN(UL_info->rach_ind.sfn_sf), - NFAPI_SFNSF2SF(UL_info->rach_ind.sfn_sf), - UL_info->rach_ind.rach_indication_body.preamble_list[0].preamble_rel8.preamble, - UL_info->rach_ind.rach_indication_body.preamble_list[0].preamble_rel8.timing_advance, - UL_info->rach_ind.rach_indication_body.preamble_list[0].preamble_rel8.rnti -#if (NR_RRC_VERSION >= MAKE_VERSION(14, 0, 0)) || (LTE_RRC_VERSION >= MAKE_VERSION(14, 0, 0)) -//#if (RRC_VERSION >= MAKE_VERSION(14, 0, 0)) - ,0 -#endif + if (UL_info->rach_ind.number_of_pdus>0) { + AssertFatal(UL_info->rach_ind.number_of_pdus==1,"More than 1 RACH pdu not supported\n"); + UL_info->rach_ind.number_of_pdus=0; + LOG_D(MAC,"UL_info[Frame %d, Slot %d] Calling initiate_ra_proc RACH:SFN/SLOT:%d/%d\n",UL_info->frame,UL_info->slot, UL_info->rach_ind.sfn,UL_info->rach_ind.slot); - ); - */ - } + if (UL_info->rach_ind.pdu_list[0].num_preamble>0) + AssertFatal(UL_info->rach_ind.pdu_list[0].num_preamble==1, + "More than 1 preamble not supported\n"); + /*nr_initiate_ra_proc(UL_info->module_id, + UL_info->CC_id, + UL_info->rach_ind.sfn, + UL_info->rach_ind.slot, + UL_info->rach_ind.pdu_list[0].preamble_list[0].preamble_index, + UL_info->rach_ind.pdu_list[0].freq_index, + UL_info->rach_ind.pdu_list[0].symbol_index, + UL_info->rach_ind.pdu_list[0].preamble_list[0].timing_advance);*/ + + } } + void handle_nr_sr(NR_UL_IND_t *UL_info) { - if (nfapi_mode == 1) // PNF + /* if (nfapi_mode == 1) // PNF { if (UL_info->sr_ind.sr_indication_body.number_of_srs>0) { @@ -91,20 +89,20 @@ void handle_nr_sr(NR_UL_IND_t *UL_info) { else { - /* + for (int i=0;i<UL_info->sr_ind.sr_indication_body.number_of_srs;i++) SR_indication(UL_info->module_id, UL_info->CC_id, UL_info->frame, UL_info->slot, UL_info->sr_ind.sr_indication_body.sr_pdu_list[i].rx_ue_information.rnti, - UL_info->sr_ind.sr_indication_body.sr_pdu_list[i].ul_cqi_information.ul_cqi);*/ + UL_info->sr_ind.sr_indication_body.sr_pdu_list[i].ul_cqi_information.ul_cqi); } - UL_info->sr_ind.sr_indication_body.number_of_srs=0; + UL_info->sr_ind.sr_indication_body.number_of_srs=0;*/ } void handle_nr_cqi(NR_UL_IND_t *UL_info) { @@ -119,103 +117,99 @@ void handle_nr_cqi(NR_UL_IND_t *UL_info) { &UL_info->cqi_ind.cqi_pdu_list[i].cqi_indication_rel9, UL_info->cqi_ind.cqi_raw_pdu_list[i].pdu, &UL_info->cqi_ind.cqi_pdu_list[i].ul_cqi_information); - */ - UL_info->cqi_ind.number_of_cqis=0; + + UL_info->cqi_ind.number_of_cqis=0;*/ } void handle_nr_harq(NR_UL_IND_t *UL_info) { - if (nfapi_mode == 1 && UL_info->harq_ind.harq_indication_body.number_of_harqs>0) { // PNF + /* if (nfapi_mode == 1 && UL_info->harq_ind.harq_indication_body.number_of_harqs>0) { // PNF //LOG_D(PHY, "UL_info->harq_ind.harq_indication_body.number_of_harqs:%d Send to VNF\n", UL_info->harq_ind.harq_indication_body.number_of_harqs); - /* int retval = oai_nfapi_harq_indication(&UL_info->harq_ind); + int retval = oai_nfapi_harq_indication(&UL_info->harq_ind); if (retval!=0) { LOG_E(PHY, "Failed to encode NFAPI HARQ_IND retval:%d\n", retval); } - */ + UL_info->harq_ind.harq_indication_body.number_of_harqs = 0; } else { - /* + for (int i=0;i<UL_info->harq_ind.harq_indication_body.number_of_harqs;i++) harq_indication(UL_info->module_id, UL_info->CC_id, NFAPI_SFNSF2SFN(UL_info->harq_ind.sfn_sf), NFAPI_SFNSF2SF(UL_info->harq_ind.sfn_sf), &UL_info->harq_ind.harq_indication_body.harq_pdu_list[i]); - */ + UL_info->harq_ind.harq_indication_body.number_of_harqs=0; - } + }*/ } void handle_nr_ulsch(NR_UL_IND_t *UL_info) { if(nfapi_mode == 1) { - if (UL_info->crc_ind.crc_indication_body.number_of_crcs>0) { + if (UL_info->crc_ind.number_crcs>0) { //LOG_D(PHY,"UL_info->crc_ind.crc_indication_body.number_of_crcs:%d CRC_IND:SFN/SF:%d\n", UL_info->crc_ind.crc_indication_body.number_of_crcs, NFAPI_SFNSF2DEC(UL_info->crc_ind.sfn_sf)); // oai_nfapi_crc_indication(&UL_info->crc_ind); - UL_info->crc_ind.crc_indication_body.number_of_crcs = 0; + UL_info->crc_ind.number_crcs = 0; } - if (UL_info->rx_ind.rx_indication_body.number_of_pdus>0) { + if (UL_info->rx_ind.number_of_pdus>0) { //LOG_D(PHY,"UL_info->rx_ind.number_of_pdus:%d RX_IND:SFN/SF:%d\n", UL_info->rx_ind.rx_indication_body.number_of_pdus, NFAPI_SFNSF2DEC(UL_info->rx_ind.sfn_sf)); // oai_nfapi_rx_ind(&UL_info->rx_ind); - UL_info->rx_ind.rx_indication_body.number_of_pdus = 0; + UL_info->rx_ind.number_of_pdus = 0; } } else { - if (UL_info->rx_ind.rx_indication_body.number_of_pdus>0 && UL_info->crc_ind.crc_indication_body.number_of_crcs>0) { - for (int i=0; i<UL_info->rx_ind.rx_indication_body.number_of_pdus; i++) { - for (int j=0; j<UL_info->crc_ind.crc_indication_body.number_of_crcs; j++) { + if (UL_info->rx_ind.number_of_pdus>0 && UL_info->crc_ind.number_crcs>0) { + for (int i=0; i<UL_info->rx_ind.number_of_pdus; i++) { + for (int j=0; j<UL_info->crc_ind.number_crcs; j++) { // find crc_indication j corresponding rx_indication i LOG_D(PHY,"UL_info->crc_ind.crc_indication_body.crc_pdu_list[%d].rx_ue_information.rnti:%04x UL_info->rx_ind.rx_indication_body.rx_pdu_list[%d].rx_ue_information.rnti:%04x\n", j, - UL_info->crc_ind.crc_indication_body.crc_pdu_list[j].rx_ue_information.rnti, i, UL_info->rx_ind.rx_indication_body.rx_pdu_list[i].rx_ue_information.rnti); + UL_info->crc_ind.crc_list[j].rnti, i, UL_info->rx_ind.pdu_list[i].rnti); - if (UL_info->crc_ind.crc_indication_body.crc_pdu_list[j].rx_ue_information.rnti == - UL_info->rx_ind.rx_indication_body.rx_pdu_list[i].rx_ue_information.rnti) { - LOG_D(PHY, "UL_info->crc_ind.crc_indication_body.crc_pdu_list[%d].crc_indication_rel8.crc_flag:%d\n", j, UL_info->crc_ind.crc_indication_body.crc_pdu_list[j].crc_indication_rel8.crc_flag); + if (UL_info->crc_ind.crc_list[j].rnti == + UL_info->rx_ind.pdu_list[i].rnti) { + LOG_D(PHY, "UL_info->crc_ind.crc_indication_body.crc_pdu_list[%d].crc_indication_rel8.crc_flag:%d\n", j, UL_info->crc_ind.crc_list[j].tb_crc_status); - if (UL_info->crc_ind.crc_indication_body.crc_pdu_list[j].crc_indication_rel8.crc_flag == 1) { // CRC error indication + if (UL_info->crc_ind.crc_list[j].tb_crc_status == 1) { // CRC error indication LOG_D(MAC,"Frame %d, Slot %d Calling rx_sdu (CRC error) \n",UL_info->frame,UL_info->slot); nr_rx_sdu(UL_info->module_id, UL_info->CC_id, - NFAPI_SFNSF2SFN(UL_info->rx_ind.sfn_sf), //UL_info->frame, - NFAPI_SFNSF2SF(UL_info->rx_ind.sfn_sf), //UL_info->slot, - UL_info->rx_ind.rx_indication_body.rx_pdu_list[i].rx_ue_information.rnti, + UL_info->rx_ind.sfn, //UL_info->frame, + UL_info->rx_ind.slot, //UL_info->slot, + UL_info->rx_ind.pdu_list[i].rnti, (uint8_t *)NULL, - UL_info->rx_ind.rx_indication_body.rx_pdu_list[i].rx_indication_rel8.length, - UL_info->rx_ind.rx_indication_body.rx_pdu_list[i].rx_indication_rel8.timing_advance, - UL_info->rx_ind.rx_indication_body.rx_pdu_list[i].rx_indication_rel8.ul_cqi); + UL_info->rx_ind.pdu_list[i].pdu_length, + UL_info->rx_ind.pdu_list[i].timing_advance, + UL_info->rx_ind.pdu_list[i].ul_cqi); } else { LOG_D(MAC,"Frame %d, Slot %d Calling rx_sdu (CRC ok) \n",UL_info->frame,UL_info->slot); nr_rx_sdu(UL_info->module_id, UL_info->CC_id, - NFAPI_SFNSF2SFN(UL_info->rx_ind.sfn_sf), //UL_info->frame, - NFAPI_SFNSF2SF(UL_info->rx_ind.sfn_sf), //UL_info->slot, - UL_info->rx_ind.rx_indication_body.rx_pdu_list[i].rx_ue_information.rnti, - UL_info->rx_ind.rx_indication_body.rx_pdu_list[i].data, - UL_info->rx_ind.rx_indication_body.rx_pdu_list[i].rx_indication_rel8.length, - UL_info->rx_ind.rx_indication_body.rx_pdu_list[i].rx_indication_rel8.timing_advance, - UL_info->rx_ind.rx_indication_body.rx_pdu_list[i].rx_indication_rel8.ul_cqi); + UL_info->rx_ind.sfn, //UL_info->frame, + UL_info->rx_ind.slot, //UL_info->slot, + UL_info->rx_ind.pdu_list[i].rnti, + UL_info->rx_ind.pdu_list[i].pdu, + UL_info->rx_ind.pdu_list[i].pdu_length, + UL_info->rx_ind.pdu_list[i].timing_advance, + UL_info->rx_ind.pdu_list[i].ul_cqi); } - //printf("rx_indication_rel8.timing_advance %d\n", UL_info->rx_ind.rx_indication_body.rx_pdu_list[i].rx_indication_rel8.timing_advance); break; - } //if (UL_info->crc_ind.crc_pdu_list[j].rx_ue_information.rnti == - - // UL_info->rx_ind.rx_pdu_list[i].rx_ue_information.rnti) - } // for (j=0;j<UL_info->crc_ind.crc_indication_body.number_of_crcs;j++) + } + } // for (j=0;j<UL_info->crc_ind.number_crcs;j++) } // for (i=0;i<UL_info->rx_ind.number_of_pdus;i++) - UL_info->crc_ind.crc_indication_body.number_of_crcs=0; - UL_info->rx_ind.rx_indication_body.number_of_pdus = 0; - } // UL_info->rx_ind.rx_indication_body.number_of_pdus>0 && UL_info->slot && UL_info->crc_ind.crc_indication_body.number_of_crcs>0 - else if (UL_info->rx_ind.rx_indication_body.number_of_pdus!=0 || UL_info->crc_ind.crc_indication_body.number_of_crcs!=0) { - LOG_E(PHY,"hoping not to have mis-match between CRC ind and RX ind - hopefully the missing message is coming shortly rx_ind:%d(SFN/SF:%05d) crc_ind:%d(SFN/SF:%05d) UL_info(SFN/SF):%04d%d\n", - UL_info->rx_ind.rx_indication_body.number_of_pdus, NFAPI_SFNSF2DEC(UL_info->rx_ind.sfn_sf), - UL_info->crc_ind.crc_indication_body.number_of_crcs, NFAPI_SFNSF2DEC(UL_info->crc_ind.sfn_sf), - UL_info->frame, UL_info->slot); + UL_info->crc_ind.number_crcs=0; + UL_info->rx_ind.number_of_pdus = 0; + } + else if (UL_info->rx_ind.number_of_pdus!=0 || UL_info->crc_ind.number_crcs!=0) { + LOG_E(PHY,"hoping not to have mis-match between CRC ind and RX ind - hopefully the missing message is coming shortly rx_ind:%d(SFN/SL:%d/%d) crc_ind:%d(SFN/SL:%d/%d) \n", + UL_info->rx_ind.number_of_pdus, UL_info->rx_ind.sfn, UL_info->rx_ind.slot, + UL_info->crc_ind.number_crcs, UL_info->rx_ind.sfn, UL_info->rx_ind.slot); } } } @@ -230,11 +224,10 @@ void NR_UL_indication(NR_UL_IND_t *UL_info) { NR_Sched_Rsp_t *sched_info = &Sched_INFO[module_id][CC_id]; NR_IF_Module_t *ifi = if_inst[module_id]; gNB_MAC_INST *mac = RC.nrmac[module_id]; - LOG_D(PHY,"SFN/SF:%d%d module_id:%d CC_id:%d UL_info[rx_ind:%d harqs:%d crcs:%d cqis:%d preambles:%d sr_ind:%d]\n", + LOG_D(PHY,"SFN/SF:%d%d module_id:%d CC_id:%d UL_info[rx_ind:%d crcs:%d]\n", UL_info->frame,UL_info->slot, module_id,CC_id, - UL_info->rx_ind.rx_indication_body.number_of_pdus, UL_info->harq_ind.harq_indication_body.number_of_harqs, UL_info->crc_ind.crc_indication_body.number_of_crcs, UL_info->cqi_ind.number_of_cqis, - UL_info->rach_ind.rach_indication_body.number_of_preambles, UL_info->sr_ind.sr_indication_body.number_of_srs); + UL_info->rx_ind.number_of_pdus, UL_info->crc_ind.number_crcs); if (nfapi_mode != 1) { if (ifi->CC_mask==0) { diff --git a/openair2/NR_PHY_INTERFACE/NR_IF_Module.h b/openair2/NR_PHY_INTERFACE/NR_IF_Module.h index 14355781d0138a970894194346a5c490cb53bdda..d523d6e0f0dd948db17b42dc714b0389d3aad4a4 100644 --- a/openair2/NR_PHY_INTERFACE/NR_IF_Module.h +++ b/openair2/NR_PHY_INTERFACE/NR_IF_Module.h @@ -61,29 +61,20 @@ typedef struct { /// slot slot_t slot; - /// harq indication list - nfapi_harq_indication_t harq_ind; - /// crc indication list - nfapi_crc_indication_t crc_ind; - - /// SR indication list - nfapi_sr_indication_t sr_ind; - - /// CQI indication list - nfapi_cqi_indication_body_t cqi_ind; + nfapi_nr_crc_indication_t crc_ind; /// RACH indication list - nfapi_rach_indication_t rach_ind; - - /// RACH indication list for BR UEs - nfapi_rach_indication_t rach_ind_br; + nfapi_nr_rach_indication_t rach_ind; /// SRS indication list - nfapi_srs_indication_body_t srs_ind; + nfapi_nr_srs_indication_t srs_ind; /// RX indication - nfapi_rx_indication_t rx_ind; + nfapi_nr_rx_data_indication_t rx_ind; + + /// UCI indication + nfapi_nr_uci_indication_t uci_ind; } NR_UL_IND_t; diff --git a/openair2/PHY_INTERFACE/phy_stub_UE.c b/openair2/PHY_INTERFACE/phy_stub_UE.c index 2025a0fdd0a55c27ea6ece5e88aeafda1b1f6511..8bd172f79f909eddb0330eeb592d020b6a9c1a2f 100644 --- a/openair2/PHY_INTERFACE/phy_stub_UE.c +++ b/openair2/PHY_INTERFACE/phy_stub_UE.c @@ -708,195 +708,142 @@ int tx_req_UE_MAC(nfapi_tx_request_t *req) { return 0; } -int dl_config_req_UE_MAC(nfapi_dl_config_request_t* req, module_id_t Mod_id) { - int sfn = NFAPI_SFNSF2SFN(req->sfn_sf); - int sf = NFAPI_SFNSF2SF(req->sfn_sf); +void dl_config_req_UE_MAC_dci(int sfn, + int sf, + nfapi_dl_config_request_pdu_t *dci, + nfapi_dl_config_request_pdu_t *dlsch, + int num_ue) { + DevAssert(dci->pdu_type == NFAPI_DL_CONFIG_DCI_DL_PDU_TYPE); + DevAssert(dlsch->pdu_type == NFAPI_DL_CONFIG_DLSCH_PDU_TYPE); + + const rnti_t rnti = dci->dci_dl_pdu.dci_dl_pdu_rel8.rnti; + const int rnti_type = dci->dci_dl_pdu.dci_dl_pdu_rel8.rnti_type; + if (rnti != dlsch->dlsch_pdu.dlsch_pdu_rel8.rnti) { + LOG_E(MAC, + "%s(): sfn/sf %d.%d DLSCH PDU RNTI %x does not match DCI RNTI %x\n", + __func__, sfn, sf, rnti, dlsch->dlsch_pdu.dlsch_pdu_rel8.rnti); + return; + } - nfapi_dl_config_request_pdu_t* dl_config_pdu_list = req->dl_config_request_body.dl_config_pdu_list; - - for (int i = 0; i < req->dl_config_request_body.number_pdu; i++) { - if (dl_config_pdu_list[i].pdu_type == NFAPI_DL_CONFIG_DCI_DL_PDU_TYPE) { - const rnti_t rnti = dl_config_pdu_list[i].dci_dl_pdu.dci_dl_pdu_rel8.rnti; - const int rnti_type = dl_config_pdu_list[i].dci_dl_pdu.dci_dl_pdu_rel8.rnti_type; - /* We assume the DCI DL PDU is followed by the DLSCH (the standard is - * more free), so advance by one more and directly process the - * following DLSCH PDU */ - i++; - AssertFatal(i < req->dl_config_request_body.number_pdu, - "Need PDU following DCI at index %d, but not found\n", - i); - nfapi_dl_config_request_pdu_t *dl_config_pdu_tmp = &dl_config_pdu_list[i]; - if (dl_config_pdu_tmp->pdu_type != NFAPI_DL_CONFIG_DLSCH_PDU_TYPE) { - LOG_E(MAC, "expected DLSCH PDU at index %d\n", i); - continue; - } - if (rnti != dl_config_pdu_tmp->dlsch_pdu.dlsch_pdu_rel8.rnti) { - LOG_I(MAC, - "%s(): sfn/sf %d DLSCH PDU RNTI %x does not match DCI RNTI %x\n", - __func__, - NFAPI_SFNSF2DEC(req->sfn_sf), - rnti, - dl_config_pdu_tmp->dlsch_pdu.dlsch_pdu_rel8.rnti); - continue; - } - const int pdu_index = dl_config_pdu_tmp->dlsch_pdu.dlsch_pdu_rel8.pdu_index; - if (pdu_index < 0 && pdu_index >= tx_req_num_elems) { - LOG_E(MAC, - "dl_config_req_UE_MAC 2: Problem with receiving data: " - "sfn/sf:%d PDU[%d] size:%d, TX_PDU index: %d\n", - NFAPI_SFNSF2DEC(req->sfn_sf), - i, - dl_config_pdu_list[i].pdu_size, - dl_config_pdu_tmp->dlsch_pdu.dlsch_pdu_rel8.pdu_index); - continue; - } - if (rnti_type == 1) { - // C-RNTI (Normal DLSCH case) - if (UE_mac_inst[Mod_id].crnti != rnti) { - LOG_D(MAC, - "sfn/sf %d/%d DCI not for UE %d/RNTI %x but for RNTI %x, " - "skipping\n", - sfn, sf, Mod_id, UE_mac_inst[Mod_id].crnti, rnti); - continue; - } + const int pdu_index = dlsch->dlsch_pdu.dlsch_pdu_rel8.pdu_index; + if (pdu_index < 0 || pdu_index >= tx_req_num_elems) { + LOG_E(MAC, + "%s(): Problem with receiving data: " + "sfn/sf:%d.%d PDU size:%d, TX_PDU index: %d\n", + __func__, + sfn, sf, dci->pdu_size, dlsch->dlsch_pdu.dlsch_pdu_rel8.pdu_index); + return; + } + if (rnti_type == 1) { // C-RNTI (Normal DLSCH case) + for (int ue_id = 0; ue_id < num_ue; ue_id++) { + if (UE_mac_inst[ue_id].crnti == rnti) { LOG_D(MAC, - "%s() Received data: sfn/sf:%d PDU[%d] " + "%s() Received data: sfn/sf:%d.%d " "size:%d, TX_PDU index: %d, tx_req_num_elems: %d \n", __func__, - NFAPI_SFNSF2DEC(req->sfn_sf), - i, - dl_config_pdu_list[i].pdu_size, - dl_config_pdu_tmp->dlsch_pdu.dlsch_pdu_rel8.pdu_index, + sfn, sf, dci->pdu_size, + dlsch->dlsch_pdu.dlsch_pdu_rel8.pdu_index, tx_req_num_elems); - ue_send_sdu(Mod_id, 0, sfn, sf, + ue_send_sdu(ue_id, 0, sfn, sf, tx_request_pdu_list[pdu_index].segments[0].segment_data, tx_request_pdu_list[pdu_index].segments[0].segment_length, 0); - } else if (rnti_type == 2) { - if (rnti == 0xFFFF) { /* SI-RNTI */ - if (UE_mac_inst[Mod_id].UE_mode[0] == NOT_SYNCHED) { - /* this check is in the code before refactoring, but I don't know - * why. Leave it in here for the moment */ - continue; - } - - ue_decode_si(Mod_id, 0, sfn, 0, + return; + } + } + } else if (rnti_type == 2) { + if (rnti == 0xFFFF) { /* SI-RNTI */ + for (int ue_id = 0; ue_id < num_ue; ue_id++) { + if (UE_mac_inst[ue_id].UE_mode[0] == NOT_SYNCHED) + continue; + + ue_decode_si(ue_id, 0, sfn, 0, + tx_request_pdu_list[pdu_index].segments[0].segment_data, + tx_request_pdu_list[pdu_index].segments[0].segment_length); + } + } else if (rnti == 0xFFFE) { /* PI-RNTI */ + for (int ue_id = 0; ue_id < num_ue; ue_id++) { + LOG_I(MAC, "%s() Received paging message: sfn/sf:%d.%d\n", + __func__, sfn, sf); + ue_decode_p(ue_id, 0, sfn, 0, + tx_request_pdu_list[pdu_index].segments[0].segment_data, + tx_request_pdu_list[pdu_index].segments[0].segment_length); + } + } else if (rnti == 0x0002) { /* RA-RNTI */ + for (int ue_id = 0; ue_id < num_ue; ue_id++) { + if (UE_mac_inst[ue_id].UE_mode[0] != RA_RESPONSE) { + LOG_D(MAC, "UE %d not awaiting RAR, is in mode %d\n", + ue_id, UE_mac_inst[ue_id].UE_mode[0]); + continue; + } + // RNTI parameter not actually used. Provided only to comply with + // existing function definition. Not sure about parameters to fill + // the preamble index. + const rnti_t ra_rnti = UE_mac_inst[ue_id].RA_prach_resources.ra_RNTI; + DevAssert(ra_rnti == 0x0002); + if (UE_mac_inst[ue_id].UE_mode[0] != PUSCH + && UE_mac_inst[ue_id].RA_prach_resources.Msg3 != NULL + && ra_rnti == dlsch->dlsch_pdu.dlsch_pdu_rel8.rnti) { + LOG_E(MAC, + "%s(): Received RAR, PreambleIndex: %d\n", + __func__, UE_mac_inst[ue_id].RA_prach_resources.ra_PreambleIndex); + ue_process_rar(ue_id, 0, sfn, + ra_rnti, //RA-RNTI tx_request_pdu_list[pdu_index].segments[0].segment_data, - tx_request_pdu_list[pdu_index].segments[0].segment_length); - } else if (rnti == 0xFFFE) { /* PI-RNTI */ - LOG_I(MAC, "%s() Received paging message: sfn/sf:%d PDU[%d]\n", - __func__, NFAPI_SFNSF2DEC(req->sfn_sf), i); - ue_decode_p(Mod_id, 0, sfn, 0, - tx_request_pdu_list[pdu_index].segments[0].segment_data, - tx_request_pdu_list[pdu_index].segments[0].segment_length); - } else if (rnti == 0x0002) { /* RA-RNTI */ - LOG_E(MAC, "%s(): Received RAR?\n", __func__); - // RNTI parameter not actually used. Provided only to comply with - // existing function definition. Not sure about parameters to fill - // the preamble index. - const rnti_t ra_rnti = UE_mac_inst[Mod_id].RA_prach_resources.ra_RNTI; - DevAssert(ra_rnti == 0x0002); - if (UE_mac_inst[Mod_id].UE_mode[0] != PUSCH - && UE_mac_inst[Mod_id].RA_prach_resources.Msg3 != NULL - && ra_rnti == dl_config_pdu_tmp->dlsch_pdu.dlsch_pdu_rel8.rnti) { - LOG_E(MAC, - "dl_config_req_UE_MAC 5 Received RAR, PreambleIndex: %d \n", - UE_mac_inst[Mod_id].RA_prach_resources.ra_PreambleIndex); - ue_process_rar(Mod_id, 0, sfn, - ra_rnti, //RA-RNTI - tx_request_pdu_list[pdu_index].segments[0].segment_data, - &dl_config_pdu_tmp->dlsch_pdu.dlsch_pdu_rel8.rnti, //t-crnti - UE_mac_inst[Mod_id].RA_prach_resources.ra_PreambleIndex, - tx_request_pdu_list[pdu_index].segments[0].segment_data); - UE_mac_inst[Mod_id].UE_mode[0] = RA_RESPONSE; - // Expecting an UL_CONFIG_ULSCH_PDU to enable Msg3 Txon (first - // ULSCH Txon for the UE) - UE_mac_inst[Mod_id].first_ULSCH_Tx = 1; - } - } else { - LOG_W(MAC, "can not handle special RNTI %x\n", rnti); + &UE_mac_inst[ue_id].crnti, //t-crnti + UE_mac_inst[ue_id].RA_prach_resources.ra_PreambleIndex, + tx_request_pdu_list[pdu_index].segments[0].segment_data); + UE_mac_inst[ue_id].UE_mode[0] = RA_RESPONSE; + // Expecting an UL_CONFIG_ULSCH_PDU to enable Msg3 Txon (first + // ULSCH Txon for the UE) + UE_mac_inst[ue_id].first_ULSCH_Tx = 1; } } - } else if (dl_config_pdu_list[i].pdu_type == NFAPI_DL_CONFIG_BCH_PDU_TYPE) { - // BCH case: Last parameter is 1 if first time synchronization and zero - // otherwise. Not sure which value to put for our case. - if (UE_mac_inst[Mod_id].UE_mode[0] == NOT_SYNCHED){ - dl_phy_sync_success(Mod_id, sfn, 0, 1); - LOG_E(MAC, - "%s(): Received MIB: UE_mode: %d, sfn/sf: %d.%d\n", - __func__, - UE_mac_inst[Mod_id].UE_mode[0], - sfn, - sf); - UE_mac_inst[Mod_id].UE_mode[0] = PRACH; - } else { - dl_phy_sync_success(Mod_id, sfn, 0, 0); - } + } else { + LOG_W(MAC, "can not handle special RNTI %x\n", rnti); } } - return 0; } -int hi_dci0_req_UE_MAC(nfapi_hi_dci0_request_t *req, module_id_t Mod_id) { - if (req != NULL && req->hi_dci0_request_body.hi_dci0_pdu_list != NULL) { - LOG_D(PHY, - "[UE-PHY_STUB] hi dci0 request sfn_sf:%d number_of_dci:%d " - "number_of_hi:%d\n", - NFAPI_SFNSF2DEC(req->sfn_sf), - req->hi_dci0_request_body.number_of_dci, - req->hi_dci0_request_body.number_of_hi); - - 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, - "[UE-PHY_STUB] 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, - "[UE-PHY_STUB] HI_DCI0_REQ sfn_sf:%d PDU[%d] - " - "NFAPI_HI_DCI0_DCI_PDU_TYPE\n", - NFAPI_SFNSF2DEC(req->sfn_sf), - i); - const nfapi_hi_dci0_dci_pdu_rel8_t *dci = - &req->hi_dci0_request_body.hi_dci0_pdu_list[i].dci_pdu.dci_pdu_rel8; - if (dci->rnti != UE_mac_inst[Mod_id].crnti) - continue; - const int sfn = NFAPI_SFNSF2SFN(req->sfn_sf); - const int sf = NFAPI_SFNSF2SF(req->sfn_sf); - if (dci->cqi_csi_request) - fill_ulsch_cqi_indication_UE_MAC(Mod_id, sfn, sf, UL_INFO, dci->rnti); - } else if (req->hi_dci0_request_body.hi_dci0_pdu_list[i].pdu_type - == NFAPI_HI_DCI0_HI_PDU_TYPE) { - nfapi_hi_dci0_request_pdu_t *hi_dci0_req_pdu = - &req->hi_dci0_request_body.hi_dci0_pdu_list[i]; - - // This is meaningful only after ACKnowledging the first ULSCH Txon - // (i.e. Msg3) - if (hi_dci0_req_pdu->hi_pdu.hi_pdu_rel8.hi_value == 1 - && UE_mac_inst[Mod_id].first_ULSCH_Tx == 1) { - // LOG_I(MAC,"[UE-PHY_STUB] HI_DCI0_REQ 2 sfn_sf:%d PDU[%d] - - // NFAPI_HI_DCI0_HI_PDU_TYPE\n", NFAPI_SFNSF2DEC(req->sfn_sf), i); - // UE_mac_inst[Mod_id].UE_mode[0] = PUSCH; - // UE_mac_inst[Mod_id].first_ULSCH_Tx = 0; - } - - } else { - LOG_E(PHY, - "[UE-PHY_STUB] 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); - } +void dl_config_req_UE_MAC_bch(int sfn, + int sf, + nfapi_dl_config_request_pdu_t *bch, + int num_ue) { + DevAssert(bch->pdu_type == NFAPI_DL_CONFIG_BCH_PDU_TYPE); + + for (int ue_id = 0; ue_id < num_ue; ue_id++) { + if (UE_mac_inst[ue_id].UE_mode[0] == NOT_SYNCHED){ + dl_phy_sync_success(ue_id, sfn, 0, 1); + LOG_E(MAC, + "%s(): Received MIB: UE_mode: %d, sfn/sf: %d.%d\n", + __func__, + UE_mac_inst[ue_id].UE_mode[0], + sfn, + sf); + UE_mac_inst[ue_id].UE_mode[0] = PRACH; + } else { + dl_phy_sync_success(ue_id, sfn, 0, 0); } } +} - return 0; +void hi_dci0_req_UE_MAC(int sfn, + int sf, + nfapi_hi_dci0_request_pdu_t* hi_dci0, + int num_ue) { + if (hi_dci0->pdu_type != NFAPI_HI_DCI0_DCI_PDU_TYPE) + return; + + const nfapi_hi_dci0_dci_pdu_rel8_t *dci = &hi_dci0->dci_pdu.dci_pdu_rel8; + if (!dci->cqi_csi_request) + return; + for (int ue_id = 0; ue_id < num_ue; ue_id++) { + if (dci->rnti == UE_mac_inst[ue_id].crnti) { + fill_ulsch_cqi_indication_UE_MAC(ue_id, sfn, sf, UL_INFO, dci->rnti); + return; + } + } } // The following set of memcpy functions should be getting called as callback diff --git a/openair2/PHY_INTERFACE/phy_stub_UE.h b/openair2/PHY_INTERFACE/phy_stub_UE.h index 0323efe6246bd0042cf1e62e37cf84dc77d1b995..0f9d0c1324467647604b6cc1d98ad8edd9327638 100644 --- a/openair2/PHY_INTERFACE/phy_stub_UE.h +++ b/openair2/PHY_INTERFACE/phy_stub_UE.h @@ -93,13 +93,23 @@ void handle_nfapi_ul_pdu_UE_MAC(module_id_t Mod_id, nfapi_ul_config_request_pdu_t *ul_config_pdu, uint16_t frame,uint8_t subframe,uint8_t srs_present, int index); -//int dl_config_req_UE_MAC(nfapi_dl_config_request_t* req, nfapi_tx_request_pdu_t* tx_request_pdu_list); -int dl_config_req_UE_MAC(nfapi_dl_config_request_t* req, module_id_t Mod_id); +void dl_config_req_UE_MAC_dci(int sfn, + int sf, + nfapi_dl_config_request_pdu_t *dci, + nfapi_dl_config_request_pdu_t *dlsch, + int num_ue); +void dl_config_req_UE_MAC_bch(int sfn, + int sf, + nfapi_dl_config_request_pdu_t *bch, + int num_ue); int tx_req_UE_MAC(nfapi_tx_request_t* req); -int hi_dci0_req_UE_MAC(nfapi_hi_dci0_request_t* req, module_id_t Mod_id); +void hi_dci0_req_UE_MAC(int sfn, + int sf, + nfapi_hi_dci0_request_pdu_t* bch, + int num_ue); // The following set of memcpy functions should be getting called as callback functions from // pnf_p7_subframe_ind. diff --git a/openair2/RRC/LTE/rrc_eNB.c b/openair2/RRC/LTE/rrc_eNB.c index bda49707d68356d90d2c6306fa32a9fc83193644..9cca00ca2ec6905139ed7808531c9a4f56183e6f 100644 --- a/openair2/RRC/LTE/rrc_eNB.c +++ b/openair2/RRC/LTE/rrc_eNB.c @@ -656,7 +656,7 @@ rrc_eNB_get_next_transaction_identifier( // AssertFatal(enb_mod_idP < NB_eNB_INST, "eNB index invalid (%d/%d)!", enb_mod_idP, NB_eNB_INST); // // for (i = 0; i < MAX_MOBILES_PER_ENB; i++) { -// if (RC.rrc[enb_mod_idP]->Info.UE_list[i] == UE_identity) { +// if (RC.rrc[enb_mod_idP]->Info.UE_info[i] == UE_identity) { // // UE_identity already registered // reg = TRUE; // break; @@ -1476,9 +1476,9 @@ rrc_eNB_generate_RRCConnectionReestablishment( if (UE_id != -1) { /* Activate reject timer, if RRCComplete not received after 10 frames, reject UE */ - RC.mac[module_id]->UE_list.UE_sched_ctrl[UE_id].ue_reestablishment_reject_timer = 1; + RC.mac[module_id]->UE_info.UE_sched_ctrl[UE_id].ue_reestablishment_reject_timer = 1; /* Reject UE after 10 frames, LTE_RRCConnectionReestablishmentReject is triggered */ - RC.mac[module_id]->UE_list.UE_sched_ctrl[UE_id].ue_reestablishment_reject_timer_thres = 100; + RC.mac[module_id]->UE_info.UE_sched_ctrl[UE_id].ue_reestablishment_reject_timer_thres = 100; } else { LOG_E(RRC, PROTOCOL_RRC_CTXT_UE_FMT" Generating LTE_RRCConnectionReestablishment without UE_id(MAC) rnti %x\n", PROTOCOL_RRC_CTXT_UE_ARGS(ctxt_pP), @@ -2086,8 +2086,8 @@ rrc_eNB_generate_RRCConnectionReestablishmentReject( int UE_id = find_UE_id(ctxt_pP->module_id, ctxt_pP->rnti); if(UE_id != -1) { - RC.mac[ctxt_pP->module_id]->UE_list.UE_sched_ctrl[UE_id].ue_reestablishment_reject_timer = 1; - RC.mac[ctxt_pP->module_id]->UE_list.UE_sched_ctrl[UE_id].ue_reestablishment_reject_timer_thres = 20; + RC.mac[ctxt_pP->module_id]->UE_info.UE_sched_ctrl[UE_id].ue_reestablishment_reject_timer = 1; + RC.mac[ctxt_pP->module_id]->UE_info.UE_sched_ctrl[UE_id].ue_reestablishment_reject_timer_thres = 20; } else { LOG_E(RRC, PROTOCOL_RRC_CTXT_UE_FMT" Generating LTE_RRCConnectionReestablishmentReject without UE_id(MAC) rnti %x\n", @@ -6168,7 +6168,7 @@ rrc_eNB_process_RRCConnectionReconfigurationComplete( return; } - UE_sched_ctrl_t *UE_scheduling_control = &(RC.mac[module_id]->UE_list.UE_sched_ctrl[UE_id_mac]); + UE_sched_ctrl_t *UE_scheduling_control = &(RC.mac[module_id]->UE_info.UE_sched_ctrl[UE_id_mac]); if (UE_scheduling_control->cdrx_waiting_ack == TRUE) { UE_scheduling_control->cdrx_waiting_ack = FALSE; @@ -6831,12 +6831,12 @@ rrc_eNB_decode_ccch( break; } - if((RC.mac[ctxt_pP->module_id]->UE_list.UE_sched_ctrl[UE_id].ue_reestablishment_reject_timer > 0) && - (RC.mac[ctxt_pP->module_id]->UE_list.UE_sched_ctrl[UE_id].ue_reestablishment_reject_timer_thres > 20)) { + if((RC.mac[ctxt_pP->module_id]->UE_info.UE_sched_ctrl[UE_id].ue_reestablishment_reject_timer > 0) && + (RC.mac[ctxt_pP->module_id]->UE_info.UE_sched_ctrl[UE_id].ue_reestablishment_reject_timer_thres > 20)) { LOG_E(RRC, PROTOCOL_RRC_CTXT_UE_FMT" RCConnectionReestablishmentComplete(Previous) don't receive, delete the c-rnti UE\n", PROTOCOL_RRC_CTXT_UE_ARGS(ctxt_pP)); - RC.mac[ctxt_pP->module_id]->UE_list.UE_sched_ctrl[UE_id].ue_reestablishment_reject_timer = 1000; + RC.mac[ctxt_pP->module_id]->UE_info.UE_sched_ctrl[UE_id].ue_reestablishment_reject_timer = 1000; rrc_eNB_previous_SRB2(ue_context_p); ue_context_p->ue_context.ue_reestablishment_timer = 0; } @@ -6862,12 +6862,12 @@ rrc_eNB_decode_ccch( break; } - if((RC.mac[ctxt_pP->module_id]->UE_list.UE_sched_ctrl[UE_id].ue_reestablishment_reject_timer > 0) && - (RC.mac[ctxt_pP->module_id]->UE_list.UE_sched_ctrl[UE_id].ue_reestablishment_reject_timer_thres > 20)) { + if((RC.mac[ctxt_pP->module_id]->UE_info.UE_sched_ctrl[UE_id].ue_reestablishment_reject_timer > 0) && + (RC.mac[ctxt_pP->module_id]->UE_info.UE_sched_ctrl[UE_id].ue_reestablishment_reject_timer_thres > 20)) { LOG_E(RRC, PROTOCOL_RRC_CTXT_UE_FMT" RCConnectionReestablishmentComplete(Previous) don't receive, delete the Previous UE\n", PROTOCOL_RRC_CTXT_UE_ARGS(ctxt_pP)); - RC.mac[ctxt_pP->module_id]->UE_list.UE_sched_ctrl[UE_id].ue_reestablishment_reject_timer = 1000; + RC.mac[ctxt_pP->module_id]->UE_info.UE_sched_ctrl[UE_id].ue_reestablishment_reject_timer = 1000; rrc_eNB_previous_SRB2(ue_context_p); ue_context_p->ue_context.ue_reestablishment_timer = 0; } @@ -7439,12 +7439,12 @@ rrc_eNB_decode_dcch( AssertFatal(!NODE_IS_CU(RC.rrc[ctxt_pP->module_id]->node_type), "CU cannot decode DCCH: no access to RC.mac[]\n"); - if(RC.mac[ctxt_pP->module_id]->UE_list.UE_sched_ctrl[UE_id].crnti_reconfigurationcomplete_flag == 1) { + if(RC.mac[ctxt_pP->module_id]->UE_info.UE_sched_ctrl[UE_id].crnti_reconfigurationcomplete_flag == 1) { LOG_I(RRC, PROTOCOL_RRC_CTXT_UE_FMT" UE State = RRC_RECONFIGURED (dedicated DRB, xid %ld) C-RNTI Complete\n", PROTOCOL_RRC_CTXT_UE_ARGS(ctxt_pP),ul_dcch_msg->message.choice.c1.choice.rrcConnectionReconfigurationComplete.rrc_TransactionIdentifier); dedicated_DRB = 2; - RC.mac[ctxt_pP->module_id]->UE_list.UE_sched_ctrl[UE_id].crnti_reconfigurationcomplete_flag = 0; + RC.mac[ctxt_pP->module_id]->UE_info.UE_sched_ctrl[UE_id].crnti_reconfigurationcomplete_flag = 0; } } else if (ue_context_p->ue_context.Status == RRC_HO_EXECUTION) { int16_t UE_id = find_UE_id(ctxt_pP->module_id, ctxt_pP->rnti); @@ -7459,7 +7459,7 @@ rrc_eNB_decode_dcch( flexran_agent_handover = 1; RC.rrc[ctxt_pP->module_id]->Nb_ue++; dedicated_DRB = 3; - RC.mac[ctxt_pP->module_id]->UE_list.UE_sched_ctrl[UE_id].crnti_reconfigurationcomplete_flag = 0; + RC.mac[ctxt_pP->module_id]->UE_info.UE_sched_ctrl[UE_id].crnti_reconfigurationcomplete_flag = 0; ue_context_p->ue_context.Status = RRC_RECONFIGURED; if(ue_context_p->ue_context.handover_info) { @@ -7637,7 +7637,7 @@ rrc_eNB_decode_dcch( break; } - RC.mac[ctxt_pP->module_id]->UE_list.UE_sched_ctrl[UE_id].ue_reestablishment_reject_timer = 0; + RC.mac[ctxt_pP->module_id]->UE_info.UE_sched_ctrl[UE_id].ue_reestablishment_reject_timer = 0; ue_context_p->ue_context.reestablishment_xid = -1; if (ul_dcch_msg->message.choice.c1.choice.rrcConnectionReestablishmentComplete.criticalExtensions.present == diff --git a/openair2/RRC/LTE/utils.c b/openair2/RRC/LTE/utils.c index 08637e0e6767e48eb94f298ad2a0fe9cb8e795c4..c84a2be476f3fd77e2d8eef1c83e9118a6ad917a 100644 --- a/openair2/RRC/LTE/utils.c +++ b/openair2/RRC/LTE/utils.c @@ -60,11 +60,11 @@ uint8_t rrc_find_free_ue_index(uint8_t Mod_id) { uint16_t i; for(i=1; i<=NB_CNX_CH; i++) - if ( (CH_rrc_inst[Mod_id].Info.UE_list[i][0] == 0) && - (CH_rrc_inst[Mod_id].Info.UE_list[i][1] == 0) && - (CH_rrc_inst[Mod_id].Info.UE_list[i][2] == 0) && - (CH_rrc_inst[Mod_id].Info.UE_list[i][3] == 0) && - (CH_rrc_inst[Mod_id].Info.UE_list[i][4] == 0)) { + if ( (CH_rrc_inst[Mod_id].Info.UE_info[i][0] == 0) && + (CH_rrc_inst[Mod_id].Info.UE_info[i][1] == 0) && + (CH_rrc_inst[Mod_id].Info.UE_info[i][2] == 0) && + (CH_rrc_inst[Mod_id].Info.UE_info[i][3] == 0) && + (CH_rrc_inst[Mod_id].Info.UE_info[i][4] == 0)) { return i; } @@ -78,7 +78,7 @@ unsigned short rrc_find_ue_index(unsigned char Mod_id, L2_ID Mac_id) { unsigned char i; /* for(i=0;i<=NB_CNX_CH;i++) - if( bcmp(Mac_id.L2_id,CH_rrc_inst[Mod_id].Info.UE_list[i].L2_id,sizeof(L2_ID))==0) + if( bcmp(Mac_id.L2_id,CH_rrc_inst[Mod_id].Info.UE_info[i].L2_id,sizeof(L2_ID))==0) return i; return i; */ @@ -167,7 +167,7 @@ unsigned char rrc_is_mobile_already_associated(uint8_t Mod_id, L2_ID Mac_id) { /* unsigned char i; for(i=0;i<NB_CNX_CH;i++) - if( bcmp(Mac_id.L2_id,CH_rrc_inst[Mod_id].Info.UE_list[i].L2_id,sizeof(L2_ID))==0) + if( bcmp(Mac_id.L2_id,CH_rrc_inst[Mod_id].Info.UE_info[i].L2_id,sizeof(L2_ID))==0) return 1; return 0; */ diff --git a/openair2/RRC/NR/MESSAGES/asn1_msg.c b/openair2/RRC/NR/MESSAGES/asn1_msg.c index a4092c11fa492ec5d3ba09e3a9215d63b13f00bf..c00b57d7aaf8fea1bb5683c4bbdde455877f66cf 100644 --- a/openair2/RRC/NR/MESSAGES/asn1_msg.c +++ b/openair2/RRC/NR/MESSAGES/asn1_msg.c @@ -570,8 +570,8 @@ void do_PHYSICALCELLGROUP(uint8_t Mod_id, void do_SpCellConfig(gNB_RRC_INST *rrc, struct NR_SpCellConfig *spconfig){ - gNB_RrcConfigurationReq *common_configuration; - common_configuration = CALLOC(1,sizeof(gNB_RrcConfigurationReq)); + //gNB_RrcConfigurationReq *common_configuration; + //common_configuration = CALLOC(1,sizeof(gNB_RrcConfigurationReq)); //Fill servingcellconfigcommon config value //Fill common config to structure // rrc->configuration = common_configuration; diff --git a/openair2/X2AP/x2ap_eNB_generate_messages.c b/openair2/X2AP/x2ap_eNB_generate_messages.c index 47a3475063fb5b25d3b3e91638f7ba1985dc0a52..0aeabce0d2cfcaa3bc545fc2ef2321cf46632b22 100644 --- a/openair2/X2AP/x2ap_eNB_generate_messages.c +++ b/openair2/X2AP/x2ap_eNB_generate_messages.c @@ -1691,11 +1691,11 @@ int x2ap_gNB_generate_ENDC_x2_SgNB_addition_request_ACK( x2ap_eNB_instance_t *in // Currently hardcoded (dummy) values filling the fields of SgNB_addition_request message. To be substituted // with values coming from RRC. - uint16_t nRencryptionAlgorithms = 0; - uint16_t nRintegrityProtectionAlgorithms = 0; - uint8_t SgNBSecurityKey[32] = { 0 }; - int uEaggregateMaximumBitRateDownlink = 100000000; - int uEaggregateMaximumBitRateUplink = 100000000; + //uint16_t nRencryptionAlgorithms = 0; + //uint16_t nRintegrityProtectionAlgorithms = 0; + //uint8_t SgNBSecurityKey[32] = { 0 }; + //int uEaggregateMaximumBitRateDownlink = 100000000; + //int uEaggregateMaximumBitRateUplink = 100000000; int e_rabs_admitted_tobeadded = 1; int e_RAB_ID = 1; long int pDCPatSgNB = X2AP_EN_DC_ResourceConfiguration__pDCPatSgNB_present; diff --git a/openair2/X2AP/x2ap_eNB_handler.c b/openair2/X2AP/x2ap_eNB_handler.c index df68746201014a0f59585a1a79b43df87f452237..b60bf5e869cbc44cd10c9568b583a238c226ee95 100644 --- a/openair2/X2AP/x2ap_eNB_handler.c +++ b/openair2/X2AP/x2ap_eNB_handler.c @@ -1773,7 +1773,7 @@ int x2ap_gNB_handle_ENDC_sGNB_addition_request (instance_t instance, //X2AP_MeNBtoSgNBContainer_t *container = &ie->value.choice.MeNBtoSgNBContainer; - if (ie->value.choice.MeNBtoSgNBContainer.size > 8192 ) // TODO: this is the size of rrc_buffer in struct x2ap_handover_req_s + if (container->size > 8192 ) // TODO: this is the size of rrc_buffer in struct x2ap_handover_req_s { printf("%s:%d: fatal: buffer too big\n", __FILE__, __LINE__); abort(); } memcpy(X2AP_ENDC_SGNB_ADDITION_REQ(msg).rrc_buffer, ie->value.choice.MeNBtoSgNBContainer.buf, ie->value.choice.MeNBtoSgNBContainer.size); diff --git a/targets/ARCH/USRP/USERSPACE/LIB/usrp_lib.cpp b/targets/ARCH/USRP/USERSPACE/LIB/usrp_lib.cpp index f37c8cf5cf586abf04c78372d658453d794fa35f..90b0a2e554d9c9199f04f5556b8e9d901867d464 100644 --- a/targets/ARCH/USRP/USERSPACE/LIB/usrp_lib.cpp +++ b/targets/ARCH/USRP/USERSPACE/LIB/usrp_lib.cpp @@ -835,22 +835,16 @@ extern "C" { if (args.find("clock_source")==std::string::npos) { if (openair0_cfg[0].clock_source == internal) { - //in UHD 3.14 we could use - //s->usrp->set_sync_source("clock_source=internal","time_source=internal"); - s->usrp->set_time_source("internal"); s->usrp->set_clock_source("internal"); - LOG_D(HW,"Setting time and clock source to internal\n"); + LOG_D(HW,"Setting clock source to internal\n"); } else if (openair0_cfg[0].clock_source == external ) { - //s->usrp->set_sync_source("clock_source=external","time_source=external"); - s->usrp->set_time_source("external"); s->usrp->set_clock_source("external"); - LOG_D(HW,"Setting time and clock source to external\n"); + LOG_D(HW,"Setting clock source to external\n"); } else if (openair0_cfg[0].clock_source==gpsdo) { s->usrp->set_clock_source("gpsdo"); - s->usrp->set_time_source("gpsdo"); - LOG_D(HW,"Setting time and clock source to gpsdo\n"); + LOG_D(HW,"Setting clock source to gpsdo\n"); } else { LOG_W(HW,"Clock source set neither in usrp_args nor on command line, using default!\n"); @@ -861,7 +855,31 @@ extern "C" { LOG_W(HW,"Clock source set in both usrp_args and in clock_source, ingnoring the latter!\n"); } } - + + if (args.find("time_source")==std::string::npos) { + if (openair0_cfg[0].time_source == internal) { + s->usrp->set_time_source("internal"); + LOG_D(HW,"Setting time source to internal\n"); + } + else if (openair0_cfg[0].time_source == external ) { + s->usrp->set_time_source("external"); + LOG_D(HW,"Setting time source to external\n"); + } + else if (openair0_cfg[0].time_source==gpsdo) { + s->usrp->set_time_source("gpsdo"); + LOG_D(HW,"Setting time source to gpsdo\n"); + } + else { + LOG_W(HW,"Time source set neither in usrp_args nor on command line, using default!\n"); + } + } + else { + if (openair0_cfg[0].clock_source != unset) { + LOG_W(HW,"Time source set in both usrp_args and in time_source, ingnoring the latter!\n"); + } + } + + if (s->usrp->get_clock_source(0) == "gpsdo") { s->use_gps = 1; @@ -1061,7 +1079,9 @@ extern "C" { //s->usrp->set_time_source("external"); // display USRP settings LOG_I(HW,"Actual master clock: %fMHz...\n",s->usrp->get_master_clock_rate()/1e6); - sleep(1); + LOG_I(HW,"Actual clock source %s...\n",s->usrp->get_clock_source(0).c_str()); + LOG_I(HW,"Actual time source %s...\n",s->usrp->get_time_source(0).c_str()); + sleep(1); // create tx & rx streamer uhd::stream_args_t stream_args_rx("sc16", "sc16"); int samples=openair0_cfg[0].sample_rate; diff --git a/targets/RT/USER/lte-enb.c b/targets/RT/USER/lte-enb.c index a61b56a08877c540fc902c8be8626c58bfaca3f4..cb04480d3321c1080299ecd7aaaaa4069ced9151 100644 --- a/targets/RT/USER/lte-enb.c +++ b/targets/RT/USER/lte-enb.c @@ -235,10 +235,10 @@ static inline int rxtx(PHY_VARS_eNB *eNB, new_dlsch_ue_select_tbl_in_use = dlsch_ue_select_tbl_in_use; dlsch_ue_select_tbl_in_use = !dlsch_ue_select_tbl_in_use; // L2-emulator can work only one eNB. - // memcpy(&pre_scd_eNB_UE_stats,&RC.mac[ru->eNB_list[0]->Mod_id]->UE_list.eNB_UE_stats, sizeof(eNB_UE_STATS)*MAX_NUM_CCs*NUMBER_OF_UE_MAX); - // memcpy(&pre_scd_activeUE, &RC.mac[ru->eNB_list[0]->Mod_id]->UE_list.active, sizeof(boolean_t)*NUMBER_OF_UE_MAX); - memcpy(&pre_scd_eNB_UE_stats,&RC.mac[0]->UE_list.eNB_UE_stats, sizeof(eNB_UE_STATS)*MAX_NUM_CCs*NUMBER_OF_UE_MAX); - memcpy(&pre_scd_activeUE, &RC.mac[0]->UE_list.active, sizeof(boolean_t)*NUMBER_OF_UE_MAX); + // memcpy(&pre_scd_eNB_UE_stats,&RC.mac[ru->eNB_list[0]->Mod_id]->UE_info.eNB_UE_stats, sizeof(eNB_UE_STATS)*MAX_NUM_CCs*NUMBER_OF_UE_MAX); + // memcpy(&pre_scd_activeUE, &RC.mac[ru->eNB_list[0]->Mod_id]->UE_info.active, sizeof(boolean_t)*NUMBER_OF_UE_MAX); + memcpy(&pre_scd_eNB_UE_stats,&RC.mac[0]->UE_info.eNB_UE_stats, sizeof(eNB_UE_STATS)*MAX_NUM_CCs*NUMBER_OF_UE_MAX); + memcpy(&pre_scd_activeUE, &RC.mac[0]->UE_info.active, sizeof(boolean_t)*NUMBER_OF_UE_MAX); AssertFatal((ret= pthread_mutex_lock(&ru->proc.mutex_pre_scd))==0,"[eNB] error locking proc mutex for eNB pre scd, return %d\n",ret); ru->proc.instance_pre_scd++; diff --git a/targets/RT/USER/lte-ru.c b/targets/RT/USER/lte-ru.c index e6364cad237799bbb81d0c0b781e3a965beb851c..8c9b143100ef19c0e9a58c9104659a2ff9ca5d43 100644 --- a/targets/RT/USER/lte-ru.c +++ b/targets/RT/USER/lte-ru.c @@ -1405,7 +1405,6 @@ void fill_rf_config(RU_t *ru, cfg->num_rb_dl=fp->N_RB_DL; cfg->tx_num_channels=ru->nb_tx; cfg->rx_num_channels=ru->nb_rx; - cfg->clock_source=get_softmodem_params()->clock_source; for (int i=0; i<ru->nb_tx; i++) { cfg->tx_freq[i] = (double)fp->dl_CarrierFreq; @@ -1866,8 +1865,8 @@ static void *ru_thread( void *param ) { #if defined(PRE_SCD_THREAD) new_dlsch_ue_select_tbl_in_use = dlsch_ue_select_tbl_in_use; dlsch_ue_select_tbl_in_use = !dlsch_ue_select_tbl_in_use; - memcpy(&pre_scd_eNB_UE_stats,&RC.mac[ru->eNB_list[0]->Mod_id]->UE_list.eNB_UE_stats, sizeof(eNB_UE_STATS)*MAX_NUM_CCs*NUMBER_OF_UE_MAX); - memcpy(&pre_scd_activeUE, &RC.mac[ru->eNB_list[0]->Mod_id]->UE_list.active, sizeof(boolean_t)*NUMBER_OF_UE_MAX); + memcpy(&pre_scd_eNB_UE_stats,&RC.mac[ru->eNB_list[0]->Mod_id]->UE_info.eNB_UE_stats, sizeof(eNB_UE_STATS)*MAX_NUM_CCs*NUMBER_OF_UE_MAX); + memcpy(&pre_scd_activeUE, &RC.mac[ru->eNB_list[0]->Mod_id]->UE_info.active, sizeof(boolean_t)*NUMBER_OF_UE_MAX); AssertFatal((ret=pthread_mutex_lock(&ru->proc.mutex_pre_scd))==0,"[eNB] error locking proc mutex for eNB pre scd\n"); ru->proc.instance_pre_scd++; @@ -2683,7 +2682,7 @@ void set_function_spec_param(RU_t *ru) { //extern void RCconfig_RU(void); -void init_RU(char *rf_config_file, clock_source_t clock_source, clock_source_t time_source, int send_dmrssync) { +void init_RU(char *rf_config_file, int send_dmrssync) { int ru_id, i, CC_id; RU_t *ru; PHY_VARS_eNB *eNB0 = (PHY_VARS_eNB *)NULL; @@ -2718,8 +2717,6 @@ void init_RU(char *rf_config_file, clock_source_t clock_source, clock_source_t t ru->south_out_cnt = 0; // use eNB_list[0] as a reference for RU frame parameters // NOTE: multiple CC_id are not handled here yet! - ru->openair0_cfg.clock_source = clock_source; - ru->openair0_cfg.time_source = time_source; //ru->generate_dmrs_sync = (ru->is_slave == 0) ? 1 : 0; if ((ru->is_slave == 0) && (ru->ota_sync_enable == 1)) @@ -2956,6 +2953,27 @@ void RCconfig_RU(void) { LOG_E(PHY, "Erroneous RU clock source in the provided configuration file: '%s'\n", *(RUParamList.paramarray[j][RU_SDR_CLK_SRC].strptr)); } } + else { + RC.ru[j]->openair0_cfg.clock_source = unset; + } + + if (config_isparamset(RUParamList.paramarray[j], RU_SDR_TME_SRC)) { + if (strcmp(*(RUParamList.paramarray[j][RU_SDR_TME_SRC].strptr), "internal") == 0) { + RC.ru[j]->openair0_cfg.time_source = internal; + LOG_D(PHY, "RU time source set as internal\n"); + } else if (strcmp(*(RUParamList.paramarray[j][RU_SDR_TME_SRC].strptr), "external") == 0) { + RC.ru[j]->openair0_cfg.time_source = external; + LOG_D(PHY, "RU time source set as external\n"); + } else if (strcmp(*(RUParamList.paramarray[j][RU_SDR_TME_SRC].strptr), "gpsdo") == 0) { + RC.ru[j]->openair0_cfg.time_source = gpsdo; + LOG_D(PHY, "RU time source set as gpsdo\n"); + } else { + LOG_E(PHY, "Erroneous RU time source in the provided configuration file: '%s'\n", *(RUParamList.paramarray[j][RU_SDR_CLK_SRC].strptr)); + } + } + else { + RC.ru[j]->openair0_cfg.time_source = unset; + } if (strcmp(*(RUParamList.paramarray[j][RU_LOCAL_RF_IDX].strptr), "yes") == 0) { if ( !(config_isparamset(RUParamList.paramarray[j],RU_LOCAL_IF_NAME_IDX)) ) { diff --git a/targets/RT/USER/lte-softmodem.c b/targets/RT/USER/lte-softmodem.c index 91303bcdc8b0903ee3702be0d6ae40ebc7739949..0b41a0471e0981b7584d2a663e81d5dccf4b835a 100644 --- a/targets/RT/USER/lte-softmodem.c +++ b/targets/RT/USER/lte-softmodem.c @@ -443,7 +443,7 @@ int restart_L1L2(module_id_t enb_id) { set_function_spec_param(RC.ru[enb_id]); /* reset the list of connected UEs in the MAC, since in this process with * loose all UEs (have to reconnect) */ - init_UE_list(&RC.mac[enb_id]->UE_list); + init_UE_info(&RC.mac[enb_id]->UE_info); LOG_I(ENB_APP, "attempting to create ITTI tasks\n"); // No more rrc thread, as many race conditions are hidden behind @@ -665,16 +665,16 @@ int main ( int argc, char **argv ) wait_eNBs(); printf("About to Init RU threads RC.nb_RU:%d\n", RC.nb_RU); - // RU thread and some L1 procedure aren't necessary in VNF or L2 FAPI simulator. - // but RU thread deals with pre_scd and this is necessary in VNF and simulator. - // some initialization is necessary and init_ru_vnf do this. - if (RC.nb_RU >0 && NFAPI_MODE!=NFAPI_MODE_VNF) { - printf("Initializing RU threads\n"); - init_RU(get_softmodem_params()->rf_config_file,get_softmodem_params()->clock_source,get_softmodem_params()->timing_source,get_softmodem_params()->send_dmrs_sync); - - for (ru_id=0; ru_id<RC.nb_RU; ru_id++) { - RC.ru[ru_id]->rf_map.card=0; - RC.ru[ru_id]->rf_map.chain=CC_id+(get_softmodem_params()->chain_offset); + // RU thread and some L1 procedure aren't necessary in VNF or L2 FAPI simulator. + // but RU thread deals with pre_scd and this is necessary in VNF and simulator. + // some initialization is necessary and init_ru_vnf do this. + if (RC.nb_RU >0 && NFAPI_MODE!=NFAPI_MODE_VNF) { + printf("Initializing RU threads\n"); + init_RU(get_softmodem_params()->rf_config_file,get_softmodem_params()->send_dmrs_sync); + + for (ru_id=0; ru_id<RC.nb_RU; ru_id++) { + RC.ru[ru_id]->rf_map.card=0; + RC.ru[ru_id]->rf_map.chain=CC_id+(get_softmodem_params()->chain_offset); } config_sync_var=0; diff --git a/targets/RT/USER/lte-softmodem.h b/targets/RT/USER/lte-softmodem.h index 5e1bf3616052630c081ba5c9bd0b8d4c78b4b815..c5fdb5f5468cbebb2d8474f9dcbaf4d41047abb5 100644 --- a/targets/RT/USER/lte-softmodem.h +++ b/targets/RT/USER/lte-softmodem.h @@ -81,7 +81,6 @@ #define CONFIG_HLP_DLSHIFT "dynamic shift for LLR compuation for TM3/4 (default 0)\n" #define CONFIG_HLP_USRP_ARGS "set the arguments to identify USRP (same syntax as in UHD)\n" #define CONFIG_HLP_DMAMAP "sets flag for improved EXMIMO UE performance\n" -#define CONFIG_HLP_CLK "tells hardware to use a clock reference (0:internal, 1:external, 2:gpsdo)\n" #define CONFIG_HLP_TDD "Set hardware to TDD mode (default: FDD). Used only with -U (otherwise set in config file).\n" #define CONFIG_HLP_TADV "Set timing_advance\n" @@ -115,7 +114,6 @@ {"dlsch-demod-shift", CONFIG_HLP_DLSHIFT, 0, iptr:(int32_t *)&dlsch_demod_shift, defintval:0, TYPE_INT, 0}, \ {"usrp-args", CONFIG_HLP_USRP_ARGS, 0, strptr:(char **)&usrp_args, defstrval:"type=b200",TYPE_STRING, 0}, \ {"mmapped-dma", CONFIG_HLP_DMAMAP, PARAMFLAG_BOOL, uptr:&mmapped_dma, defintval:0, TYPE_INT, 0}, \ - {"clock-source", CONFIG_HLP_CLK, 0, iptr:&clock_source, defintval:0, TYPE_INT, 0}, \ {"T" , CONFIG_HLP_TDD, PARAMFLAG_BOOL, iptr:&tddflag, defintval:0, TYPE_INT, 0}, \ {"A", CONFIG_HLP_TADV, 0, iptr:&(timingadv), defintval:0, TYPE_INT, 0} \ } @@ -169,7 +167,7 @@ extern void init_RU_proc(RU_t *ru); extern void stop_RU(int nb_ru); extern void kill_RU_proc(RU_t *ru); extern void set_function_spec_param(RU_t *ru); -extern void init_RU(char *, clock_source_t clock_source, clock_source_t time_source, int send_dmrssync); +extern void init_RU(char *, int send_dmrssync); // In lte-ue.c extern int setup_ue_buffers(PHY_VARS_UE **phy_vars_ue, openair0_config_t *openair0_cfg); diff --git a/targets/RT/USER/lte-ue.c b/targets/RT/USER/lte-ue.c index ea4da800a24980554352971587f16e1897cbd8b0..d9465db425fae6653f86dae884ac628bb96f5ad1 100644 --- a/targets/RT/USER/lte-ue.c +++ b/targets/RT/USER/lte-ue.c @@ -1108,6 +1108,45 @@ static void *UE_phy_stub_single_thread_rxn_txnp4(void *arg) } } + if (dl_config_req && tx_request_pdu_list) { + nfapi_dl_config_request_body_t* dl_config_req_body = &dl_config_req->dl_config_request_body; + for (int i = 0; i < dl_config_req_body->number_pdu; ++i) { + nfapi_dl_config_request_pdu_t* pdu = &dl_config_req_body->dl_config_pdu_list[i]; + if (pdu->pdu_type == NFAPI_DL_CONFIG_DCI_DL_PDU_TYPE) { + i += 1; + AssertFatal(i < dl_config_req->dl_config_request_body.number_pdu, + "Need PDU following DCI at index %d, but not found\n", + i); + nfapi_dl_config_request_pdu_t *dlsch = &dl_config_req_body->dl_config_pdu_list[i]; + if (dlsch->pdu_type != NFAPI_DL_CONFIG_DLSCH_PDU_TYPE) { + LOG_E(MAC, "expected DLSCH PDU at index %d\n", i); + continue; + } + dl_config_req_UE_MAC_dci(NFAPI_SFNSF2SFN(dl_config_req->sfn_sf), + NFAPI_SFNSF2SF(dl_config_req->sfn_sf), + pdu, + dlsch, + ue_num); + } else if (pdu->pdu_type == NFAPI_DL_CONFIG_BCH_PDU_TYPE) { + dl_config_req_UE_MAC_bch(NFAPI_SFNSF2SFN(dl_config_req->sfn_sf), + NFAPI_SFNSF2SF(dl_config_req->sfn_sf), + pdu, + ue_num); + } + } + } + + if (hi_dci0_req) { + nfapi_hi_dci0_request_body_t *hi_dci0_body = &hi_dci0_req->hi_dci0_request_body; + for (int i = 0; i < hi_dci0_body->number_of_dci + hi_dci0_body->number_of_hi; i++) { + nfapi_hi_dci0_request_pdu_t* pdu = &hi_dci0_body->hi_dci0_pdu_list[i]; + hi_dci0_req_UE_MAC(NFAPI_SFNSF2SFN(hi_dci0_req->sfn_sf), + NFAPI_SFNSF2SF(hi_dci0_req->sfn_sf), + pdu, + ue_num); + } + } + //for (Mod_id=0; Mod_id<NB_UE_INST; Mod_id++) { for (ue_index=0; ue_index < ue_num; ue_index++) { ue_Mod_id = ue_thread_id + NB_THREAD_INST*ue_index; @@ -1136,15 +1175,6 @@ static void *UE_phy_stub_single_thread_rxn_txnp4(void *arg) phy_procedures_UE_SL_RX(UE,proc); - if (dl_config_req!=NULL && tx_request_pdu_list!=NULL) { - //if(dl_config_req!= NULL) { - dl_config_req_UE_MAC(dl_config_req, ue_Mod_id); - } - - if (hi_dci0_req!=NULL && hi_dci0_req->hi_dci0_request_body.hi_dci0_pdu_list!=NULL) { - hi_dci0_req_UE_MAC(hi_dci0_req, ue_Mod_id); - } - if(NFAPI_MODE!=NFAPI_UE_STUB_PNF) phy_procedures_UE_SL_TX(UE,proc); } @@ -1183,7 +1213,7 @@ static void *UE_phy_stub_single_thread_rxn_txnp4(void *arg) if (UE_mac_inst[ue_Mod_id].UE_mode[0] == PRACH && ue_Mod_id == next_Mod_id) { next_ra_frame++; - if(next_ra_frame > 200) { + if(next_ra_frame > 500) { // check if we have PRACH opportunity if (is_prach_subframe(&UE->frame_parms,proc->frame_tx, proc->subframe_tx) && UE_mac_inst[ue_Mod_id].SI_Decoded == 1) { // The one working strangely... @@ -1413,12 +1443,14 @@ static void *UE_phy_stub_thread_rxn_txnp4(void *arg) oai_subframe_ind(timer_frame, timer_subframe); if(dl_config_req!= NULL) { - dl_config_req_UE_MAC(dl_config_req, Mod_id); + AssertFatal(0, "dl_config_req_UE_MAC() not handled\n"); + //dl_config_req_UE_MAC(dl_config_req, Mod_id); } //if(UE_mac_inst[Mod_id].hi_dci0_req!= NULL){ if (hi_dci0_req!=NULL && hi_dci0_req->hi_dci0_request_body.hi_dci0_pdu_list!=NULL) { - hi_dci0_req_UE_MAC(hi_dci0_req, Mod_id); + AssertFatal(0, "hi_dci0_req_UE_MAC() not handled\n"); + //hi_dci0_req_UE_MAC(hi_dci0_req, Mod_id); //if(UE_mac_inst[Mod_id].hi_dci0_req->hi_dci0_request_body.hi_dci0_pdu_list!=NULL){ free(hi_dci0_req->hi_dci0_request_body.hi_dci0_pdu_list); hi_dci0_req->hi_dci0_request_body.hi_dci0_pdu_list = NULL; diff --git a/targets/RT/USER/lte-uesoftmodem.c b/targets/RT/USER/lte-uesoftmodem.c index 67988c03c383240716e547e8c13aa648f780c993..8afbbe535837b702741184d8ef9779a2e6399e59 100644 --- a/targets/RT/USER/lte-uesoftmodem.c +++ b/targets/RT/USER/lte-uesoftmodem.c @@ -113,10 +113,6 @@ uint16_t runtime_phy_tx[29][6]; // SISO [MCS 0-28][RBs 0-5 : 6, 15, 25, 50, 75, volatile int oai_exit = 0; - -clock_source_t clock_source = internal,time_source=internal; - - unsigned int mmapped_dma=0; @@ -467,7 +463,8 @@ void init_openair0(LTE_DL_FRAME_PARMS *frame_parms,int rxgain) { openair0_cfg[card].Mod_id = 0; openair0_cfg[card].num_rb_dl=frame_parms->N_RB_DL; - openair0_cfg[card].clock_source = clock_source; + openair0_cfg[card].clock_source = get_softmodem_params()->clock_source; + openair0_cfg[card].time_source = get_softmodem_params()->timing_source; openair0_cfg[card].tx_num_channels=min(2,frame_parms->nb_antennas_tx); openair0_cfg[card].rx_num_channels=min(2,frame_parms->nb_antennas_rx); diff --git a/targets/RT/USER/rfsim.c b/targets/RT/USER/rfsim.c index bd8305682c6529b6a099d49c81a901bfc63a80c2..a9a091243334e1690cb402eab15a8bba469de8e0 100644 --- a/targets/RT/USER/rfsim.c +++ b/targets/RT/USER/rfsim.c @@ -64,7 +64,7 @@ sim_t sim; void init_ru_devices(void); -void init_RU(char *,clock_source_t clock_source,clock_source_t time_source,int send_dmrssync); +void init_RU(char *,int send_dmrssync); void *rfsim_top(void *n_frames); @@ -101,7 +101,7 @@ void RCConfig_sim(void) { RC.nb_RU = RUParamList.numelt; AssertFatal(RC.nb_RU>0,"we need at least 1 RU for simulation\n"); printf("returned with %d rus\n",RC.nb_RU); - init_RU(NULL,internal,internal,0); + init_RU(NULL,0); printf("Waiting for RUs to get set up\n"); wait_RUs(); init_ru_devices();