From 9726a47fbb91960cdded1467012ddbc8d3947f79 Mon Sep 17 00:00:00 2001 From: Raghavendra Dinavahi Date: Thu, 1 Aug 2024 17:52:05 +0200 Subject: [PATCH] enable HARQ32, Changes in gNB - Enabled configuration for number of dl, ul harq processes in conf file - set "num_dlharq = 32; num_ulharq = 32;" under "gNBs" section in the conf file - default values when not configured is 16 for DL, UL harq processes - IEs in the RRC messages set according to the number of DL, UL harq processes configured. - If value 32 is configured , then IEs related to num harq processes and dci bits also configured in Bandwidth parts. --- doc/RUNMODEM.md | 8 + openair2/GNB_APP/gnb_config.c | 15 +- openair2/GNB_APP/gnb_paramdef.h | 13 ++ openair2/LAYER2/NR_MAC_gNB/gNB_scheduler_RA.c | 2 +- .../LAYER2/NR_MAC_gNB/gNB_scheduler_bch.c | 2 +- .../LAYER2/NR_MAC_gNB/gNB_scheduler_dlsch.c | 2 +- .../NR_MAC_gNB/gNB_scheduler_primitives.c | 114 +++++++------- openair2/LAYER2/NR_MAC_gNB/mac_proto.h | 4 +- openair2/LAYER2/NR_MAC_gNB/nr_mac_gNB.h | 2 + openair2/RRC/NR/nr_rrc_config.c | 147 +++++++++++++++--- 10 files changed, 230 insertions(+), 79 deletions(-) diff --git a/doc/RUNMODEM.md b/doc/RUNMODEM.md index 4d181158a9..dcd6154187 100644 --- a/doc/RUNMODEM.md +++ b/doc/RUNMODEM.md @@ -205,6 +205,14 @@ cd cmake_targets sudo ./ran_build/build/nr-softmodem -O ../targets/PROJECTS/GENERIC-NR-5GC/CONF/gnb.sa.band66.fr1.25PRB.usrpx300.conf --sa --rfsim --rfsimulator.prop_delay 238.74 ``` +To configure NTN gNB with 32 HARQ processes in downlink and uplink, add these settings in conf files under section `gNBs.[0]` +``` +... + num_dlharq = 32; + num_ulharq = 32; +... +``` + ### NR UE At UE side, there are two main parameters to cope with the large NTN propagation delay, cellSpecificKoffset and ta-Common. diff --git a/openair2/GNB_APP/gnb_config.c b/openair2/GNB_APP/gnb_config.c index 9d9de98f8b..c571b253e1 100644 --- a/openair2/GNB_APP/gnb_config.c +++ b/openair2/GNB_APP/gnb_config.c @@ -675,6 +675,9 @@ void RCconfig_verify(configmodule_interface_t *cfg, ngran_node_t node_type) verify_gnb_param_notset(gnbp, GNB_DO_SRS_IDX, GNB_CONFIG_STRING_DOSRS); verify_gnb_param_notset(gnbp, GNB_FORCE256QAMOFF_IDX, GNB_CONFIG_STRING_FORCE256QAMOFF); verify_gnb_param_notset(gnbp, GNB_MAXMIMOLAYERS_IDX, GNB_CONFIG_STRING_MAXMIMOLAYERS); + verify_gnb_param_notset(gnbp, GNB_DISABLE_HARQ_IDX, GNB_CONFIG_STRING_DISABLE_HARQ); + verify_gnb_param_notset(gnbp, GNB_NUM_DL_HARQ_IDX, GNB_CONFIG_STRING_NUM_DL_HARQPROCESSES); + verify_gnb_param_notset(gnbp, GNB_NUM_UL_HARQ_IDX, GNB_CONFIG_STRING_NUM_UL_HARQPROCESSES); // check for some general sections verify_section_notset(cfg, NULL, CONFIG_STRING_L1_LIST); @@ -1213,6 +1216,10 @@ void RCconfig_nr_macrlc(configmodule_interface_t *cfg) GNB_CONFIG_STRING_ACTIVE_GNBS, num_gnbs); paramdef_t GNBParams[] = GNBPARAMS_DESC; + /* map parameter checking array instances to parameter definition array instances */ + checkedparam_t config_check_GNBParams[] = GNBPARAMS_CHECK; + for (int i = 0; i < sizeofArray(GNBParams); ++i) + GNBParams[i].chkPptr = &(config_check_GNBParams[i]); config_getlist(cfg, &GNBParamList, GNBParams, sizeofArray(GNBParams), NULL); if (NFAPI_MODE != NFAPI_MODE_PNF) { @@ -1261,16 +1268,20 @@ void RCconfig_nr_macrlc(configmodule_interface_t *cfg) config.use_deltaMCS = *GNBParamList.paramarray[0][GNB_USE_DELTA_MCS_IDX].iptr != 0; config.maxMIMO_layers = *GNBParamList.paramarray[0][GNB_MAXMIMOLAYERS_IDX].iptr; config.disable_harq = *GNBParamList.paramarray[0][GNB_DISABLE_HARQ_IDX].iptr; + config.num_dlharq = *GNBParamList.paramarray[0][GNB_NUM_DL_HARQ_IDX].iptr; + config.num_ulharq = *GNBParamList.paramarray[0][GNB_NUM_UL_HARQ_IDX].iptr; if (config.disable_harq) LOG_W(GNB_APP, "\"disable_harq\" is a REL17 feature and is incompatible with REL15 and REL16 UEs!\n"); LOG_I(GNB_APP, - "CSI-RS %d, SRS %d, 256 QAM %s, delta_MCS %s, maxMIMO_Layers %d, HARQ feedback %s\n", + "CSI-RS %d, SRS %d, 256 QAM %s, delta_MCS %s, maxMIMO_Layers %d, HARQ feedback %s, num DLHARQ:%d, num ULHARQ:%d\n", config.do_CSIRS, config.do_SRS, config.force_256qam_off ? "force off" : "may be on", config.use_deltaMCS ? "on" : "off", config.maxMIMO_layers, - config.disable_harq ? "disabled" : "enabled"); + config.disable_harq ? "disabled" : "enabled", + config.num_dlharq, + config.num_ulharq); int tot_ant = config.pdsch_AntennaPorts.N1 * config.pdsch_AntennaPorts.N2 * config.pdsch_AntennaPorts.XP; AssertFatal(config.maxMIMO_layers != 0 && config.maxMIMO_layers <= tot_ant, "Invalid maxMIMO_layers %d\n", config.maxMIMO_layers); diff --git a/openair2/GNB_APP/gnb_paramdef.h b/openair2/GNB_APP/gnb_paramdef.h index 339ea75714..c632bf1b3e 100644 --- a/openair2/GNB_APP/gnb_paramdef.h +++ b/openair2/GNB_APP/gnb_paramdef.h @@ -135,6 +135,8 @@ typedef enum { #define GNB_CONFIG_STRING_FORCEUL256QAMOFF "force_UL256qam_off" #define GNB_CONFIG_STRING_GNB_DU_ID "gNB_DU_ID" #define GNB_CONFIG_STRING_GNB_CU_UP_ID "gNB_CU_UP_ID" +#define GNB_CONFIG_STRING_NUM_DL_HARQPROCESSES "num_dlharq" +#define GNB_CONFIG_STRING_NUM_UL_HARQPROCESSES "num_ulharq" #define GNB_CONFIG_HLP_STRING_ENABLE_SDAP "enable the SDAP layer\n" #define GNB_CONFIG_HLP_FORCE256QAMOFF "suppress activation of 256 QAM despite UE support" @@ -143,6 +145,8 @@ typedef enum { #define GNB_CONFIG_HLP_STRING_DRBS "Number of total DRBs to establish, including the mandatory for PDU SEssion (default=1)\n" #define GNB_CONFIG_HLP_GNB_DU_ID "defines the gNB-DU ID (only applicable for DU)" #define GNB_CONFIG_HLP_GNB_CU_UP_ID "defines the gNB-CU-UP ID (only applicable for CU-UP)" +#define GNB_CONFIG_HLP_NUM_DL_HARQ "Set Num DL harq processes. Valid values 2,4,6,8,10,12,16,32. Default 16" +#define GNB_CONFIG_HLP_NUM_UL_HARQ "Set Num UL harq processes. Valid values 16,32. Default 16" /*-----------------------------------------------------------------------------------------------------------------------------------------*/ /* cell configuration parameters */ @@ -183,6 +187,8 @@ typedef enum { {GNB_CONFIG_STRING_FORCEUL256QAMOFF, GNB_CONFIG_HLP_FORCEUL256QAMOFF, 0,.iptr=NULL, .defintval=0, TYPE_INT, 0}, \ {GNB_CONFIG_STRING_MAXMIMOLAYERS, GNB_CONFIG_HLP_MAXMIMOLAYERS, 0, .iptr=NULL, .defintval=-1, TYPE_INT, 0}, \ {GNB_CONFIG_STRING_DISABLE_HARQ, GNB_CONFIG_HLP_DISABLE_HARQ, PARAMFLAG_BOOL, .iptr=NULL, .defintval=0, TYPE_INT, 0}, \ +{GNB_CONFIG_STRING_NUM_DL_HARQPROCESSES, GNB_CONFIG_HLP_NUM_DL_HARQ, 0, .iptr=NULL, .defintval=16, TYPE_INT, 0}, \ +{GNB_CONFIG_STRING_NUM_UL_HARQPROCESSES, GNB_CONFIG_HLP_NUM_UL_HARQ, 0, .iptr=NULL, .defintval=16, TYPE_INT, 0}, \ } // clang-format on @@ -220,8 +226,13 @@ typedef enum { #define GNB_FORCEUL256QAMOFF_IDX 30 #define GNB_MAXMIMOLAYERS_IDX 31 #define GNB_DISABLE_HARQ_IDX 32 +#define GNB_NUM_DL_HARQ_IDX 33 +#define GNB_NUM_UL_HARQ_IDX 34 #define TRACKING_AREA_CODE_OKRANGE {0x0001,0xFFFD} +#define NUM_DL_HARQ_OKVALUES {2,4,6,8,10,12,16,32} +#define NUM_UL_HARQ_OKVALUES {16,32} + #define GNBPARAMS_CHECK { \ { .s5 = { NULL } }, \ { .s5 = { NULL } }, \ @@ -256,6 +267,8 @@ typedef enum { { .s5 = { NULL } }, \ { .s5 = { NULL } }, \ { .s5 = { NULL } }, \ + { .s1 = { config_check_intval, NUM_DL_HARQ_OKVALUES,8 } }, \ + { .s1 = { config_check_intval, NUM_UL_HARQ_OKVALUES,2 } }, \ } /*-------------------------------------------------------------------------------------------------------------------------------------------------*/ diff --git a/openair2/LAYER2/NR_MAC_gNB/gNB_scheduler_RA.c b/openair2/LAYER2/NR_MAC_gNB/gNB_scheduler_RA.c index 495eb30eef..d1a0bae0dc 100644 --- a/openair2/LAYER2/NR_MAC_gNB/gNB_scheduler_RA.c +++ b/openair2/LAYER2/NR_MAC_gNB/gNB_scheduler_RA.c @@ -1651,7 +1651,7 @@ static void prepare_dl_pdus(gNB_MAC_INST *nr_mac, dci_payload.mcs = pdsch_pdu_rel15->mcsIndex[0]; dci_payload.tb_scaling = tb_scaling; dci_payload.rv = pdsch_pdu_rel15->rvIndex[0]; - dci_payload.harq_pid = current_harq_pid; + dci_payload.harq_pid.val = current_harq_pid; dci_payload.ndi = ndi; dci_payload.dai[0].val = pucch ? (pucch->dai_c-1) & 3 : 0; dci_payload.tpc = tpc; // TPC for PUCCH: table 7.2.1-1 in 38.213 diff --git a/openair2/LAYER2/NR_MAC_gNB/gNB_scheduler_bch.c b/openair2/LAYER2/NR_MAC_gNB/gNB_scheduler_bch.c index 3d531315ea..970118a643 100644 --- a/openair2/LAYER2/NR_MAC_gNB/gNB_scheduler_bch.c +++ b/openair2/LAYER2/NR_MAC_gNB/gNB_scheduler_bch.c @@ -500,7 +500,7 @@ static void nr_fill_nfapi_dl_sib1_pdu(int Mod_idP, dci_payload.time_domain_assignment.val = gNB_mac->sched_ctrlCommon->sched_pdsch.time_domain_allocation; dci_payload.mcs = pdsch->mcs; dci_payload.rv = pdsch_pdu_rel15->rvIndex[0]; - dci_payload.harq_pid = 0; + dci_payload.harq_pid.val = 0; dci_payload.ndi = 0; dci_payload.dai[0].val = 0; dci_payload.tpc = 0; // table 7.2.1-1 in 38.213 diff --git a/openair2/LAYER2/NR_MAC_gNB/gNB_scheduler_dlsch.c b/openair2/LAYER2/NR_MAC_gNB/gNB_scheduler_dlsch.c index cd4fc9b197..dc412cdf78 100644 --- a/openair2/LAYER2/NR_MAC_gNB/gNB_scheduler_dlsch.c +++ b/openair2/LAYER2/NR_MAC_gNB/gNB_scheduler_dlsch.c @@ -1211,7 +1211,7 @@ void nr_schedule_ue_spec(module_id_t module_id, dci_payload.time_domain_assignment.val = sched_pdsch->time_domain_allocation; dci_payload.mcs = sched_pdsch->mcs; dci_payload.rv = pdsch_pdu->rvIndex[0]; - dci_payload.harq_pid = current_harq_pid; + dci_payload.harq_pid.val = current_harq_pid; dci_payload.ndi = harq->ndi; dci_payload.dai[0].val = pucch ? (pucch->dai_c-1)&3 : 0; dci_payload.tpc = sched_ctrl->tpc1; // TPC for PUCCH: table 7.2.1-1 in 38.213 diff --git a/openair2/LAYER2/NR_MAC_gNB/gNB_scheduler_primitives.c b/openair2/LAYER2/NR_MAC_gNB/gNB_scheduler_primitives.c index 5728f6bb3f..5769efe4f2 100644 --- a/openair2/LAYER2/NR_MAC_gNB/gNB_scheduler_primitives.c +++ b/openair2/LAYER2/NR_MAC_gNB/gNB_scheduler_primitives.c @@ -791,7 +791,7 @@ void config_uldci(const NR_UE_ServingCell_Info_t *sc_info, dci_pdu_rel15->mcs = pusch_pdu->mcs_index; dci_pdu_rel15->ndi = ndi; dci_pdu_rel15->rv = pusch_pdu->pusch_data.rv_index; - dci_pdu_rel15->harq_pid = pusch_pdu->pusch_data.harq_process_id; + dci_pdu_rel15->harq_pid.val = pusch_pdu->pusch_data.harq_process_id; dci_pdu_rel15->tpc = tpc; NR_PUSCH_Config_t *pusch_Config = ul_bwp->pusch_Config; @@ -1432,10 +1432,11 @@ void fill_dci_pdu_rel15(const NR_UE_ServingCell_Info_t *servingCellInfo, pos += 2; *dci_pdu |= (dci_pdu_rel15->rv & 0x3) << (dci_size - pos); LOG_D(NR_MAC, "RV %d (%d bits)=> %d (0x%lx)\n", dci_pdu_rel15->rv, 2, dci_size - pos, *dci_pdu); - // HARQ process number 4bit - pos += 4; - *dci_pdu |= ((dci_pdu_rel15->harq_pid & 0xf) << (dci_size - pos)); - LOG_D(NR_MAC, "HARQ_PID %d (%d bits)=> %d (0x%lx)\n", dci_pdu_rel15->harq_pid, 4, dci_size - pos, *dci_pdu); + // HARQ process number 4bit/5bit + fsize = dci_pdu_rel15->harq_pid.nbits; + pos += fsize; + *dci_pdu |= ((dci_pdu_rel15->harq_pid.val & ((1 << fsize) - 1)) << (dci_size - pos)); + LOG_D(NR_MAC, "HARQ_PID %d (%d bits)=> %d (0x%lx)\n", dci_pdu_rel15->harq_pid.val, fsize, dci_size - pos, *dci_pdu); // Downlink assignment index 2bit pos += 2; *dci_pdu |= ((dci_pdu_rel15->dai[0].val & 3) << (dci_size - pos)); @@ -1538,9 +1539,10 @@ void fill_dci_pdu_rel15(const NR_UE_ServingCell_Info_t *servingCellInfo, // Redundancy version 2bit for (int i = 0; i < 2; i++) *dci_pdu |= (((uint64_t)dci_pdu_rel15->rv >> (1 - i)) & 1) << (dci_size - pos++); - // HARQ process number 4bit - for (int i = 0; i < 4; i++) - *dci_pdu |= (((uint64_t)dci_pdu_rel15->harq_pid >> (3 - i)) & 1) << (dci_size - pos++); + // HARQ process number 4bit/5bit + fsize = dci_pdu_rel15->harq_pid.nbits; + for (int i = 0; i < fsize; i++) + *dci_pdu |= (((uint64_t)dci_pdu_rel15->harq_pid.val >> (fsize - i - 1)) & 1) << (dci_size - pos++); // Downlink assignment index – 2 bits for (int i = 0; i < 2; i++) *dci_pdu |= (((uint64_t)dci_pdu_rel15->dai[0].val >> (1 - i)) & 1) << (dci_size - pos++); @@ -1563,7 +1565,7 @@ void fill_dci_pdu_rel15(const NR_UE_ServingCell_Info_t *servingCellInfo, LOG_D(NR_MAC, "dci_pdu_rel15->vrb_to_prb_mapping.val = %i\n", dci_pdu_rel15->vrb_to_prb_mapping.val); LOG_D(NR_MAC, "dci_pdu_rel15->mcs = %i\n", dci_pdu_rel15->mcs); LOG_D(NR_MAC, "dci_pdu_rel15->rv = %i\n", dci_pdu_rel15->rv); - LOG_D(NR_MAC, "dci_pdu_rel15->harq_pid = %i\n", dci_pdu_rel15->harq_pid); + LOG_D(NR_MAC, "dci_pdu_rel15->harq_pid = %i\n", dci_pdu_rel15->harq_pid.val); LOG_D(NR_MAC, "dci_pdu_rel15->dai[0].val = %i\n", dci_pdu_rel15->dai[0].val); LOG_D(NR_MAC, "dci_pdu_rel15->tpc = %i\n", dci_pdu_rel15->tpc); LOG_D(NR_MAC, @@ -1603,9 +1605,10 @@ void fill_dci_pdu_rel15(const NR_UE_ServingCell_Info_t *servingCellInfo, // Redundancy version 2bit pos += 2; *dci_pdu |= ((uint64_t)dci_pdu_rel15->rv & 0x3) << (dci_size - pos); - // HARQ process number 4bit - pos += 4; - *dci_pdu |= ((uint64_t)dci_pdu_rel15->harq_pid & 0xf) << (dci_size - pos); + // HARQ process number 4bit/5bit + fsize = dci_pdu_rel15->harq_pid.nbits; + pos += fsize; + *dci_pdu |= ((uint64_t)dci_pdu_rel15->harq_pid.val & ((1 << fsize) - 1)) << (dci_size - pos); // TPC command for scheduled PUSCH – 2 bits pos += 2; *dci_pdu |= ((uint64_t)dci_pdu_rel15->tpc & 0x3) << (dci_size - pos); @@ -1628,7 +1631,7 @@ void fill_dci_pdu_rel15(const NR_UE_ServingCell_Info_t *servingCellInfo, LOG_D(NR_MAC, "dci_pdu_rel15->mcs = %i\n", dci_pdu_rel15->mcs); LOG_D(NR_MAC, "dci_pdu_rel15->ndi = %i\n", dci_pdu_rel15->ndi); LOG_D(NR_MAC, "dci_pdu_rel15->rv = %i\n", dci_pdu_rel15->rv); - LOG_D(NR_MAC, "dci_pdu_rel15->harq_pid = %i\n", dci_pdu_rel15->harq_pid); + LOG_D(NR_MAC, "dci_pdu_rel15->harq_pid = %i\n", dci_pdu_rel15->harq_pid.val); LOG_D(NR_MAC, "dci_pdu_rel15->tpc = %i\n", dci_pdu_rel15->tpc); LOG_D(NR_MAC, "dci_pdu_rel15->padding = %i\n", dci_pdu_rel15->padding); break; @@ -1656,9 +1659,10 @@ void fill_dci_pdu_rel15(const NR_UE_ServingCell_Info_t *servingCellInfo, // Redundancy version 2bit pos += 2; *dci_pdu |= ((uint64_t)dci_pdu_rel15->rv & 0x3) << (dci_size - pos); - // HARQ process number 4bit - pos += 4; - *dci_pdu |= ((uint64_t)dci_pdu_rel15->harq_pid & 0xf) << (dci_size - pos); + // HARQ process number 4bit/5bit + fsize = dci_pdu_rel15->harq_pid.nbits; + pos += fsize; + *dci_pdu |= ((uint64_t)dci_pdu_rel15->harq_pid.val & ((1 << fsize) - 1)) << (dci_size - pos); // Padding bits for (int a = pos; a < dci_size; a++) *dci_pdu |= ((uint64_t)dci_pdu_rel15->padding & 1) << (dci_size - pos++); @@ -1677,7 +1681,7 @@ void fill_dci_pdu_rel15(const NR_UE_ServingCell_Info_t *servingCellInfo, LOG_D(NR_MAC, "dci_pdu_rel15->mcs = %i\n", dci_pdu_rel15->mcs); LOG_D(NR_MAC, "dci_pdu_rel15->ndi = %i\n", dci_pdu_rel15->ndi); LOG_D(NR_MAC, "dci_pdu_rel15->rv = %i\n", dci_pdu_rel15->rv); - LOG_D(NR_MAC, "dci_pdu_rel15->harq_pid = %i\n", dci_pdu_rel15->harq_pid); + LOG_D(NR_MAC, "dci_pdu_rel15->harq_pid = %i\n", dci_pdu_rel15->harq_pid.val); LOG_D(NR_MAC, "dci_pdu_rel15->tpc = %i\n", dci_pdu_rel15->tpc); LOG_D(NR_MAC, "dci_pdu_rel15->padding = %i\n", dci_pdu_rel15->padding); @@ -1726,9 +1730,10 @@ void fill_dci_pdu_rel15(const NR_UE_ServingCell_Info_t *servingCellInfo, // Redundancy version 2bit pos += 2; *dci_pdu |= ((uint64_t)dci_pdu_rel15->rv & 0x3) << (dci_size - pos); - // HARQ process number 4bit - pos += 4; - *dci_pdu |= ((uint64_t)dci_pdu_rel15->harq_pid & 0xf) << (dci_size - pos); + // HARQ process number 4bit/5bit + fsize = dci_pdu_rel15->harq_pid.nbits; + pos += fsize; + *dci_pdu |= ((uint64_t)dci_pdu_rel15->harq_pid.val & ((1 << fsize) - 1)) << (dci_size - pos); // 1st Downlink assignment index pos += dci_pdu_rel15->dai[0].nbits; *dci_pdu |= ((uint64_t)dci_pdu_rel15->dai[0].val & ((1 << dci_pdu_rel15->dai[0].nbits) - 1)) << (dci_size - pos); @@ -1858,9 +1863,10 @@ void fill_dci_pdu_rel15(const NR_UE_ServingCell_Info_t *servingCellInfo, // Redundancy version 2bit pos += dci_pdu_rel15->rv2.nbits; *dci_pdu |= ((uint64_t)dci_pdu_rel15->rv2.val & ((1 << dci_pdu_rel15->rv2.nbits) - 1)) << (dci_size - pos); - // HARQ process number 4bit - pos += 4; - *dci_pdu |= ((uint64_t)dci_pdu_rel15->harq_pid & 0xf) << (dci_size - pos); + // HARQ process number 4bit/5bit + fsize = dci_pdu_rel15->harq_pid.nbits; + pos += fsize; + *dci_pdu |= ((uint64_t)dci_pdu_rel15->harq_pid.val & ((1 << fsize) - 1)) << (dci_size - pos); // Downlink assignment index pos += dci_pdu_rel15->dai[0].nbits; *dci_pdu |= ((uint64_t)dci_pdu_rel15->dai[0].val & ((1 << dci_pdu_rel15->dai[0].nbits) - 1)) << (dci_size - pos); @@ -2073,26 +2079,6 @@ NR_UE_info_t *find_nr_UE(NR_UEs_t *UEs, rnti_t rntiP) return NULL; } -int get_nrofHARQ_ProcessesForPDSCH(e_NR_PDSCH_ServingCellConfig__nrofHARQ_ProcessesForPDSCH n) -{ - switch (n) { - case NR_PDSCH_ServingCellConfig__nrofHARQ_ProcessesForPDSCH_n2: - return 2; - case NR_PDSCH_ServingCellConfig__nrofHARQ_ProcessesForPDSCH_n4: - return 4; - case NR_PDSCH_ServingCellConfig__nrofHARQ_ProcessesForPDSCH_n6: - return 6; - case NR_PDSCH_ServingCellConfig__nrofHARQ_ProcessesForPDSCH_n10: - return 10; - case NR_PDSCH_ServingCellConfig__nrofHARQ_ProcessesForPDSCH_n12: - return 12; - case NR_PDSCH_ServingCellConfig__nrofHARQ_ProcessesForPDSCH_n16: - return 16; - default: - return 8; - } -} - void delete_nr_ue_data(NR_UE_info_t *UE, NR_COMMON_channels_t *ccPtr, uid_allocator_t *uia) { ASN_STRUCT_FREE(asn_DEF_NR_CellGroupConfig, UE->CellGroup); @@ -2351,6 +2337,8 @@ void configure_UE_BWP(gNB_MAC_INST *nr_mac, if (pdsch_servingcellconfig->codeBlockGroupTransmission && pdsch_servingcellconfig->codeBlockGroupTransmission->choice.setup) sc_info->pdsch_CGB_Transmission = pdsch_servingcellconfig->codeBlockGroupTransmission->choice.setup; + if (pdsch_servingcellconfig->ext3) + sc_info->nrofHARQ_ProcessesForPDSCH_v1700 = pdsch_servingcellconfig->ext3->nrofHARQ_ProcessesForPDSCH_v1700; } sc_info->crossCarrierSchedulingConfig = servingCellConfig->crossCarrierSchedulingConfig; sc_info->supplementaryUplink = servingCellConfig->supplementaryUplink; @@ -2367,6 +2355,8 @@ void configure_UE_BWP(gNB_MAC_INST *nr_mac, if (pusch_servingcellconfig->codeBlockGroupTransmission && pusch_servingcellconfig->codeBlockGroupTransmission->choice.setup) sc_info->pusch_CGB_Transmission = pusch_servingcellconfig->codeBlockGroupTransmission->choice.setup; + if (pusch_servingcellconfig->ext3) + sc_info->nrofHARQ_ProcessesForPUSCH_r17 = pusch_servingcellconfig->ext3->nrofHARQ_ProcessesForPUSCH_r17; } } } @@ -2516,13 +2506,7 @@ NR_UE_info_t *add_new_nr_ue(gNB_MAC_INST *nr_mac, rnti_t rntiP, NR_CellGroupConf /* get Number of HARQ processes for this UE */ // pdsch_servingcellconfig == NULL in SA -> will create default (8) number of HARQ processes create_dl_harq_list(sched_ctrl, &UE->sc_info); - // add all available UL HARQ processes for this UE - // nb of ul harq processes not configurable - create_nr_list(&sched_ctrl->available_ul_harq, 16); - for (int harq = 0; harq < 16; harq++) - add_tail_nr_list(&sched_ctrl->available_ul_harq, harq); - create_nr_list(&sched_ctrl->feedback_ul_harq, 16); - create_nr_list(&sched_ctrl->retrans_ul_harq, 16); + create_ul_harq_list(sched_ctrl, &UE->sc_info); reset_srs_stats(UE); @@ -2580,8 +2564,7 @@ void free_sched_pucch_list(NR_UE_sched_ctrl_t *sched_ctrl) void create_dl_harq_list(NR_UE_sched_ctrl_t *sched_ctrl, const NR_UE_ServingCell_Info_t *sc_info) { - const int nrofHARQ = - sc_info && sc_info->nrofHARQ_ProcessesForPDSCH ? get_nrofHARQ_ProcessesForPDSCH(*sc_info->nrofHARQ_ProcessesForPDSCH) : 8; + const int nrofHARQ = get_nrofHARQ_ProcessesForPDSCH(sc_info); // add all available DL HARQ processes for this UE AssertFatal(sched_ctrl->available_dl_harq.len == sched_ctrl->feedback_dl_harq.len && sched_ctrl->available_dl_harq.len == sched_ctrl->retrans_dl_harq.len, @@ -2610,6 +2593,30 @@ void create_dl_harq_list(NR_UE_sched_ctrl_t *sched_ctrl, const NR_UE_ServingCell } } +void create_ul_harq_list(NR_UE_sched_ctrl_t *sched_ctrl, const NR_UE_ServingCell_Info_t *sc_info) +{ + int nrofHARQ = get_nrofHARQ_ProcessesForPUSCH(sc_info); + if (sched_ctrl->available_ul_harq.len == 0) { + create_nr_list(&sched_ctrl->available_ul_harq, nrofHARQ); + for (int harq = 0; harq < nrofHARQ; harq++) + add_tail_nr_list(&sched_ctrl->available_ul_harq, harq); + create_nr_list(&sched_ctrl->feedback_ul_harq, nrofHARQ); + create_nr_list(&sched_ctrl->retrans_ul_harq, nrofHARQ); + } else if (sched_ctrl->available_ul_harq.len == nrofHARQ) { + LOG_D(NR_MAC, "nrofHARQ %d already configured\n", nrofHARQ); + } else { + const int old_nrofHARQ = sched_ctrl->available_ul_harq.len; + AssertFatal(nrofHARQ > old_nrofHARQ, + "cannot resize HARQ list to be smaller (nrofHARQ %d, old_nrofHARQ %d)\n", + nrofHARQ, old_nrofHARQ); + resize_nr_list(&sched_ctrl->available_ul_harq, nrofHARQ); + for (int harq = old_nrofHARQ; harq < nrofHARQ; harq++) + add_tail_nr_list(&sched_ctrl->available_ul_harq, harq); + resize_nr_list(&sched_ctrl->feedback_ul_harq, nrofHARQ); + resize_nr_list(&sched_ctrl->retrans_ul_harq, nrofHARQ); + } +} + void reset_dl_harq_list(NR_UE_sched_ctrl_t *sched_ctrl) { int harq; while ((harq = sched_ctrl->feedback_dl_harq.head) >= 0) { @@ -2980,8 +2987,9 @@ static void nr_mac_apply_cellgroup(gNB_MAC_INST *mac, NR_UE_info_t *UE, frame_t reset_srs_stats(UE); if (get_softmodem_params()->sa) { - // add all available DL HARQ processes for this UE in SA + // add all available DL,UL HARQ processes for this UE in SA create_dl_harq_list(sched_ctrl, &UE->sc_info); + create_ul_harq_list(sched_ctrl, &UE->sc_info); } } diff --git a/openair2/LAYER2/NR_MAC_gNB/mac_proto.h b/openair2/LAYER2/NR_MAC_gNB/mac_proto.h index 938d5cf27b..82fc2ceee1 100644 --- a/openair2/LAYER2/NR_MAC_gNB/mac_proto.h +++ b/openair2/LAYER2/NR_MAC_gNB/mac_proto.h @@ -281,8 +281,6 @@ int get_spf(nfapi_nr_config_request_scf_t *cfg); int to_absslot(nfapi_nr_config_request_scf_t *cfg,int frame,int slot); -int get_nrofHARQ_ProcessesForPDSCH(e_NR_PDSCH_ServingCellConfig__nrofHARQ_ProcessesForPDSCH n); - void nr_get_tbs_dl(nfapi_nr_dl_tti_pdsch_pdu *pdsch_pdu, int x_overhead, uint8_t numdmrscdmgroupnodata, @@ -351,6 +349,8 @@ void nr_rx_sdu(const module_id_t gnb_mod_idP, void create_dl_harq_list(NR_UE_sched_ctrl_t *sched_ctrl, const NR_UE_ServingCell_Info_t *sc_info); +void create_ul_harq_list(NR_UE_sched_ctrl_t *sched_ctrl, const NR_UE_ServingCell_Info_t *sc_info); + void reset_dl_harq_list(NR_UE_sched_ctrl_t *sched_ctrl); void reset_ul_harq_list(NR_UE_sched_ctrl_t *sched_ctrl); diff --git a/openair2/LAYER2/NR_MAC_gNB/nr_mac_gNB.h b/openair2/LAYER2/NR_MAC_gNB/nr_mac_gNB.h index 8362a61205..7792b70f6d 100644 --- a/openair2/LAYER2/NR_MAC_gNB/nr_mac_gNB.h +++ b/openair2/LAYER2/NR_MAC_gNB/nr_mac_gNB.h @@ -156,6 +156,8 @@ typedef struct nr_mac_config_t { //int pusch_TargetSNRx10; //int pucch_TargetSNRx10; nr_mac_timers_t timer_config; + int num_dlharq; + int num_ulharq; } nr_mac_config_t; typedef struct NR_preamble_ue { diff --git a/openair2/RRC/NR/nr_rrc_config.c b/openair2/RRC/NR/nr_rrc_config.c index dd3b3db216..e5f0c295b5 100644 --- a/openair2/RRC/NR/nr_rrc_config.c +++ b/openair2/RRC/NR/nr_rrc_config.c @@ -2599,6 +2599,107 @@ static NR_MAC_CellGroupConfig_t *configure_mac_cellgroup(const nr_mac_timers_t * return mac_CellGroupConfig; } +// Set HARQ related IEs according to the number of DL, UL harqprocesses configured +static void fill_harq_IEs(NR_ServingCellConfig_t *scc, int num_dlharq, int num_ulharq) +{ + + AssertFatal(scc && scc->pdsch_ServingCellConfig && + scc->pdsch_ServingCellConfig->present == NR_SetupRelease_PDSCH_ServingCellConfig_PR_setup, + "PDSCH_Servingcellconfig IEs NOT present\n"); + + NR_PDSCH_ServingCellConfig_t *pdsch_scc = scc->pdsch_ServingCellConfig->choice.setup; + + switch (num_dlharq) { + case 2: + *pdsch_scc->nrofHARQ_ProcessesForPDSCH = NR_PDSCH_ServingCellConfig__nrofHARQ_ProcessesForPDSCH_n2; + break; + case 4: + *pdsch_scc->nrofHARQ_ProcessesForPDSCH = NR_PDSCH_ServingCellConfig__nrofHARQ_ProcessesForPDSCH_n4; + break; + case 6: + *pdsch_scc->nrofHARQ_ProcessesForPDSCH = NR_PDSCH_ServingCellConfig__nrofHARQ_ProcessesForPDSCH_n6; + break; + case 8: + // 8 if IEs nrofHARQ_ProcessesForPDSCH and nrofHARQ_ProcessesForPDSCH_v1700 are not present + free_and_zero(pdsch_scc->nrofHARQ_ProcessesForPDSCH); + break; + case 10: + *pdsch_scc->nrofHARQ_ProcessesForPDSCH = NR_PDSCH_ServingCellConfig__nrofHARQ_ProcessesForPDSCH_n10; + break; + case 12: + *pdsch_scc->nrofHARQ_ProcessesForPDSCH = NR_PDSCH_ServingCellConfig__nrofHARQ_ProcessesForPDSCH_n12; + break; + case 16: + *pdsch_scc->nrofHARQ_ProcessesForPDSCH = NR_PDSCH_ServingCellConfig__nrofHARQ_ProcessesForPDSCH_n16; + break; + case 32: + if (!pdsch_scc->ext3) + pdsch_scc->ext3 = calloc(1, sizeof(*pdsch_scc->ext3)); + asn1cCallocOne(pdsch_scc->ext3->nrofHARQ_ProcessesForPDSCH_v1700, + NR_PDSCH_ServingCellConfig__ext3__nrofHARQ_ProcessesForPDSCH_v1700_n32); + NR_BWP_DownlinkDedicated_t *dlbwp = scc->initialDownlinkBWP; + if (dlbwp && dlbwp->pdsch_Config && + dlbwp->pdsch_Config->present == NR_SetupRelease_PDSCH_Config_PR_setup) { + NR_PDSCH_Config_t *dlcfg = scc->initialDownlinkBWP->pdsch_Config->choice.setup; + if (!dlcfg->ext3) + dlcfg->ext3 = calloc(1, sizeof(*dlcfg->ext3)); + asn1cCallocOne(dlcfg->ext3->harq_ProcessNumberSizeDCI_1_1_r17, 5); + } + int num_dl_bwp = 0; + if (scc->downlinkBWP_ToAddModList) + num_dl_bwp = scc->downlinkBWP_ToAddModList->list.count; + for (int i = 0;i < num_dl_bwp; i++) { + dlbwp = scc->downlinkBWP_ToAddModList->list.array[i]->bwp_Dedicated; + if (dlbwp && dlbwp->pdsch_Config && + dlbwp->pdsch_Config->present == NR_SetupRelease_PDSCH_Config_PR_setup) { + NR_PDSCH_Config_t *dlcfg = dlbwp->pdsch_Config->choice.setup; + if (!dlcfg->ext3) + dlcfg->ext3 = calloc(1, sizeof(*dlcfg->ext3)); + asn1cCallocOne(dlcfg->ext3->harq_ProcessNumberSizeDCI_1_1_r17, 5); + } + } + break; + default: // Already IE should have been set to 16 harq processes + break; + } + + + AssertFatal(scc->uplinkConfig,"uplinkConfig IE NOT present\n"); + + if (num_ulharq == 32) { + if (!scc->uplinkConfig->pusch_ServingCellConfig) + scc->uplinkConfig->pusch_ServingCellConfig = calloc(1, sizeof(*scc->uplinkConfig->pusch_ServingCellConfig)); + scc->uplinkConfig->pusch_ServingCellConfig->present = NR_SetupRelease_PUSCH_ServingCellConfig_PR_setup; + if (!scc->uplinkConfig->pusch_ServingCellConfig->choice.setup) + scc->uplinkConfig->pusch_ServingCellConfig->choice.setup = calloc(1, sizeof(NR_PUSCH_ServingCellConfig_t)); + NR_PUSCH_ServingCellConfig_t *pusch_scc = scc->uplinkConfig->pusch_ServingCellConfig->choice.setup; + if (!pusch_scc->ext3) + pusch_scc->ext3 = calloc(1, sizeof(*pusch_scc->ext3)); + asn1cCallocOne(pusch_scc->ext3->nrofHARQ_ProcessesForPUSCH_r17, + NR_PUSCH_ServingCellConfig__ext3__nrofHARQ_ProcessesForPUSCH_r17_n32); + NR_BWP_UplinkDedicated_t *ulbwp = scc->uplinkConfig->initialUplinkBWP; + if (ulbwp && ulbwp->pusch_Config && + ulbwp->pusch_Config->present == NR_SetupRelease_PUSCH_Config_PR_setup) { + NR_PUSCH_Config_t *ulcfg = ulbwp->pusch_Config->choice.setup; + if (!ulcfg->ext2) + ulcfg->ext2 = calloc(1, sizeof(*ulcfg->ext2)); + asn1cCallocOne(ulcfg->ext2->harq_ProcessNumberSizeDCI_0_1_r17, 5); + } + int num_ul_bwp = 0; + if (scc->uplinkConfig->uplinkBWP_ToAddModList) + num_ul_bwp = scc->uplinkConfig->uplinkBWP_ToAddModList->list.count; + for (int i = 0;i < num_ul_bwp; i++) { + ulbwp = scc->uplinkConfig->uplinkBWP_ToAddModList->list.array[i]->bwp_Dedicated; + if (ulbwp && ulbwp->pusch_Config && + ulbwp->pusch_Config->present == NR_SetupRelease_PUSCH_Config_PR_setup) { + NR_PUSCH_Config_t *ulcfg = ulbwp->pusch_Config->choice.setup; + if (!ulcfg->ext2) + ulcfg->ext2 = calloc(1, sizeof(*ulcfg->ext2)); + asn1cCallocOne(ulcfg->ext2->harq_ProcessNumberSizeDCI_0_1_r17, 5); + } + } + } +} static NR_SpCellConfig_t *get_initial_SpCellConfig(int uid, const NR_ServingCellConfigCommon_t *scc, @@ -2681,12 +2782,12 @@ static NR_SpCellConfig_t *get_initial_SpCellConfig(int uid, pdsch_servingcellconfig->codeBlockGroupTransmission = NULL; pdsch_servingcellconfig->xOverhead = NULL; - pdsch_servingcellconfig->nrofHARQ_ProcessesForPDSCH = calloc(1, sizeof(*pdsch_servingcellconfig->nrofHARQ_ProcessesForPDSCH)); - *pdsch_servingcellconfig->nrofHARQ_ProcessesForPDSCH = NR_PDSCH_ServingCellConfig__nrofHARQ_ProcessesForPDSCH_n16; + asn1cCallocOne(pdsch_servingcellconfig->nrofHARQ_ProcessesForPDSCH, NR_PDSCH_ServingCellConfig__nrofHARQ_ProcessesForPDSCH_n16); pdsch_servingcellconfig->pucch_Cell = NULL; set_dl_maxmimolayers(pdsch_servingcellconfig, scc, NULL, configuration->maxMIMO_layers); if (configuration->disable_harq) { - pdsch_servingcellconfig->ext3 = calloc(1, sizeof(*pdsch_servingcellconfig->ext3)); + if (!pdsch_servingcellconfig->ext3) + pdsch_servingcellconfig->ext3 = calloc(1, sizeof(*pdsch_servingcellconfig->ext3)); pdsch_servingcellconfig->ext3->downlinkHARQ_FeedbackDisabled_r17 = calloc(1, sizeof(*pdsch_servingcellconfig->ext3->downlinkHARQ_FeedbackDisabled_r17)); pdsch_servingcellconfig->ext3->downlinkHARQ_FeedbackDisabled_r17->present = NR_SetupRelease_DownlinkHARQ_FeedbackDisabled_r17_PR_setup; pdsch_servingcellconfig->ext3->downlinkHARQ_FeedbackDisabled_r17->choice.setup.buf = calloc(4, sizeof(uint8_t)); @@ -2848,6 +2949,8 @@ static NR_SpCellConfig_t *get_initial_SpCellConfig(int uid, config_rsrp_meas_report(csi_MeasConfig, scc, pucchrsrp, configuration->do_CSIRS, bwp_id + 10, uid, pdsch_AntennaPorts); } + fill_harq_IEs(SpCellConfig->spCellConfigDedicated, configuration->num_dlharq, configuration->num_ulharq); + if (LOG_DEBUGFLAG(DEBUG_ASN1)) { xer_fprint(stdout, &asn_DEF_NR_SpCellConfig, SpCellConfig); } @@ -2936,16 +3039,15 @@ void update_cellGroupConfig(NR_CellGroupConfig_t *cellGroupConfig, } *pusch_Config->maxRank = ul_max_layers; } - if (uplinkConfig->pusch_ServingCellConfig == NULL) { + if (!uplinkConfig->pusch_ServingCellConfig) uplinkConfig->pusch_ServingCellConfig = calloc(1, sizeof(*uplinkConfig->pusch_ServingCellConfig)); - uplinkConfig->pusch_ServingCellConfig->present = NR_SetupRelease_PUSCH_ServingCellConfig_PR_setup; + uplinkConfig->pusch_ServingCellConfig->present = NR_SetupRelease_PUSCH_ServingCellConfig_PR_setup; + if (!uplinkConfig->pusch_ServingCellConfig->choice.setup) uplinkConfig->pusch_ServingCellConfig->choice.setup = calloc(1, sizeof(*uplinkConfig->pusch_ServingCellConfig->choice.setup)); + if (!uplinkConfig->pusch_ServingCellConfig->choice.setup->ext1) uplinkConfig->pusch_ServingCellConfig->choice.setup->ext1 = calloc(1, sizeof(*uplinkConfig->pusch_ServingCellConfig->choice.setup->ext1)); - uplinkConfig->pusch_ServingCellConfig->choice.setup->ext1->maxMIMO_Layers = - calloc(1, sizeof(*uplinkConfig->pusch_ServingCellConfig->choice.setup->ext1->maxMIMO_Layers)); - } - *uplinkConfig->pusch_ServingCellConfig->choice.setup->ext1->maxMIMO_Layers = ul_max_layers; + asn1cCallocOne(uplinkConfig->pusch_ServingCellConfig->choice.setup->ext1->maxMIMO_Layers, ul_max_layers); } long maxMIMO_Layers = uplinkConfig && uplinkConfig->pusch_ServingCellConfig @@ -3249,18 +3351,23 @@ NR_CellGroupConfig_t *get_default_secondaryCellGroup(const NR_ServingCellConfigC secondaryCellGroup->spCellConfig->spCellConfigDedicated->downlinkBWP_ToReleaseList = NULL; secondaryCellGroup->spCellConfig->spCellConfigDedicated->uplinkConfig->uplinkBWP_ToReleaseList = NULL; - secondaryCellGroup->spCellConfig->spCellConfigDedicated->uplinkConfig->pusch_ServingCellConfig = - calloc(1, sizeof(*secondaryCellGroup->spCellConfig->spCellConfigDedicated->uplinkConfig->pusch_ServingCellConfig)); - NR_PUSCH_ServingCellConfig_t *pusch_scc = calloc(1, sizeof(*pusch_scc)); + if (!secondaryCellGroup->spCellConfig->spCellConfigDedicated->uplinkConfig->pusch_ServingCellConfig) + secondaryCellGroup->spCellConfig->spCellConfigDedicated->uplinkConfig->pusch_ServingCellConfig = + calloc(1, sizeof(*secondaryCellGroup->spCellConfig->spCellConfigDedicated->uplinkConfig->pusch_ServingCellConfig)); secondaryCellGroup->spCellConfig->spCellConfigDedicated->uplinkConfig->pusch_ServingCellConfig->present = NR_SetupRelease_PUSCH_ServingCellConfig_PR_setup; - secondaryCellGroup->spCellConfig->spCellConfigDedicated->uplinkConfig->pusch_ServingCellConfig->choice.setup = pusch_scc; + if (!secondaryCellGroup->spCellConfig->spCellConfigDedicated->uplinkConfig->pusch_ServingCellConfig->choice.setup) + secondaryCellGroup->spCellConfig->spCellConfigDedicated->uplinkConfig->pusch_ServingCellConfig->choice.setup = calloc( + 1, + sizeof(*secondaryCellGroup->spCellConfig->spCellConfigDedicated->uplinkConfig->pusch_ServingCellConfig->choice.setup)); + NR_PUSCH_ServingCellConfig_t *pusch_scc = + secondaryCellGroup->spCellConfig->spCellConfigDedicated->uplinkConfig->pusch_ServingCellConfig->choice.setup; pusch_scc->codeBlockGroupTransmission = NULL; pusch_scc->rateMatching = NULL; pusch_scc->xOverhead = NULL; - pusch_scc->ext1 = calloc(1, sizeof(*pusch_scc->ext1)); - pusch_scc->ext1->maxMIMO_Layers = calloc(1, sizeof(*pusch_scc->ext1->maxMIMO_Layers)); - *pusch_scc->ext1->maxMIMO_Layers = 1; + if (!pusch_scc->ext1) + pusch_scc->ext1 = calloc(1, sizeof(*pusch_scc->ext1)); + asn1cCallocOne(pusch_scc->ext1->maxMIMO_Layers, 1); pusch_scc->ext1->processingType2Enabled = NULL; secondaryCellGroup->spCellConfig->spCellConfigDedicated->uplinkConfig->carrierSwitching = NULL; @@ -3275,13 +3382,13 @@ NR_CellGroupConfig_t *get_default_secondaryCellGroup(const NR_ServingCellConfigC secondaryCellGroup->spCellConfig->spCellConfigDedicated->pdsch_ServingCellConfig->choice.setup = pdsch_servingcellconfig; pdsch_servingcellconfig->codeBlockGroupTransmission = NULL; pdsch_servingcellconfig->xOverhead = NULL; - pdsch_servingcellconfig->nrofHARQ_ProcessesForPDSCH = calloc(1, sizeof(*pdsch_servingcellconfig->nrofHARQ_ProcessesForPDSCH)); - *pdsch_servingcellconfig->nrofHARQ_ProcessesForPDSCH = NR_PDSCH_ServingCellConfig__nrofHARQ_ProcessesForPDSCH_n16; + asn1cCallocOne(pdsch_servingcellconfig->nrofHARQ_ProcessesForPDSCH, NR_PDSCH_ServingCellConfig__nrofHARQ_ProcessesForPDSCH_n16); pdsch_servingcellconfig->pucch_Cell = NULL; set_dl_maxmimolayers(pdsch_servingcellconfig, servingcellconfigcommon, uecap, configuration->maxMIMO_layers); pdsch_servingcellconfig->ext1->processingType2Enabled = NULL; if (configuration->disable_harq) { - pdsch_servingcellconfig->ext3 = calloc(1, sizeof(*pdsch_servingcellconfig->ext3)); + if (!pdsch_servingcellconfig->ext3) + pdsch_servingcellconfig->ext3 = calloc(1, sizeof(*pdsch_servingcellconfig->ext3)); pdsch_servingcellconfig->ext3->downlinkHARQ_FeedbackDisabled_r17 = calloc(1, sizeof(*pdsch_servingcellconfig->ext3->downlinkHARQ_FeedbackDisabled_r17)); pdsch_servingcellconfig->ext3->downlinkHARQ_FeedbackDisabled_r17->present = NR_SetupRelease_DownlinkHARQ_FeedbackDisabled_r17_PR_setup; pdsch_servingcellconfig->ext3->downlinkHARQ_FeedbackDisabled_r17->choice.setup.buf = calloc(4, sizeof(uint8_t)); @@ -3385,6 +3492,8 @@ NR_CellGroupConfig_t *get_default_secondaryCellGroup(const NR_ServingCellConfigC secondaryCellGroup->spCellConfig->spCellConfigDedicated->pathlossReferenceLinking = NULL; secondaryCellGroup->spCellConfig->spCellConfigDedicated->servingCellMO = NULL; + fill_harq_IEs(secondaryCellGroup->spCellConfig->spCellConfigDedicated, configuration->num_dlharq, configuration->num_ulharq); + if (LOG_DEBUGFLAG(DEBUG_ASN1)) { xer_fprint(stdout, &asn_DEF_NR_SpCellConfig, (void *)secondaryCellGroup->spCellConfig); }