diff --git a/openair2/LAYER2/NR_MAC_gNB/gNB_scheduler.c b/openair2/LAYER2/NR_MAC_gNB/gNB_scheduler.c index 2c8b0aabd2..def6a7f304 100644 --- a/openair2/LAYER2/NR_MAC_gNB/gNB_scheduler.c +++ b/openair2/LAYER2/NR_MAC_gNB/gNB_scheduler.c @@ -318,9 +318,8 @@ void nr_schedule_pucch(int Mod_idP, frame_t frameP, sub_frame_t slotP) { - uint16_t O_uci; - uint16_t O_ack; - uint8_t SR_flag = 0; // no SR in PUCCH implemented for now + uint16_t O_csi, O_ack, O_uci; + uint8_t O_sr = 0; // no SR in PUCCH implemented for now NR_ServingCellConfigCommon_t *scc = RC.nrmac[Mod_idP]->common_channels->ServingCellConfigCommon; NR_UE_list_t *UE_list = &RC.nrmac[Mod_idP]->UE_list; AssertFatal(UE_list->active[UE_id] >=0,"Cannot find UE_id %d is not active\n",UE_id); @@ -336,8 +335,9 @@ void nr_schedule_pucch(int Mod_idP, for (int l=0; l<2; l++) { curr_pucch = &UE_list->UE_sched_ctrl[UE_id].sched_pucch[k][l]; O_ack = curr_pucch->dai_c; - O_uci = O_ack + curr_pucch->csi_bits; // for now we are just sending acknacks in pucch - if ((O_uci>0 || SR_flag==1) && (frameP == curr_pucch->frame) && (slotP == curr_pucch->ul_slot)) { + O_csi = curr_pucch->csi_bits; + O_uci = O_ack + O_csi + O_sr; + if ((O_uci>0) && (frameP == curr_pucch->frame) && (slotP == curr_pucch->ul_slot)) { UL_tti_req->SFN = curr_pucch->frame; UL_tti_req->Slot = curr_pucch->ul_slot; UL_tti_req->pdus_list[UL_tti_req->n_pdus].pdu_type = NFAPI_NR_UL_CONFIG_PUCCH_PDU_TYPE; @@ -346,17 +346,17 @@ void nr_schedule_pucch(int Mod_idP, memset(pucch_pdu,0,sizeof(nfapi_nr_pucch_pdu_t)); UL_tti_req->n_pdus+=1; - LOG_I(MAC,"Scheduling pucch reception for frame %d slot %d with SR flag %d and (%d, %d) (ACK, CSI) bits\n", - frameP,slotP,SR_flag,O_ack,curr_pucch->csi_bits); + LOG_I(MAC,"Scheduling pucch reception for frame %d slot %d with %d SR bits and (%d, %d) (ACK, CSI) bits\n", + frameP,slotP,O_sr,O_ack,curr_pucch->csi_bits); nr_configure_pucch(pucch_pdu, scc, ubwp, UE_list->rnti[UE_id], curr_pucch->resource_indicator, - O_uci, + O_csi, O_ack, - SR_flag); + O_sr); memset((void *) &UE_list->UE_sched_ctrl[UE_id].sched_pucch[k][l], 0, diff --git a/openair2/LAYER2/NR_MAC_gNB/gNB_scheduler_primitives.c b/openair2/LAYER2/NR_MAC_gNB/gNB_scheduler_primitives.c index 76f77ed806..c647b46618 100644 --- a/openair2/LAYER2/NR_MAC_gNB/gNB_scheduler_primitives.c +++ b/openair2/LAYER2/NR_MAC_gNB/gNB_scheduler_primitives.c @@ -545,9 +545,9 @@ void nr_configure_pucch(nfapi_nr_pucch_pdu_t* pucch_pdu, NR_BWP_Uplink_t *bwp, uint16_t rnti, uint8_t pucch_resource, - uint16_t O_uci, + uint16_t O_csi, uint16_t O_ack, - uint8_t SR_flag) { + uint8_t O_sr) { NR_PUCCH_Config_t *pucch_Config; NR_PUCCH_Resource_t *pucchres; @@ -562,6 +562,8 @@ void nr_configure_pucch(nfapi_nr_pucch_pdu_t* pucch_pdu, pucch_pdu->bit_len_harq = O_ack; + uint16_t O_uci = O_csi + O_ack; + if (bwp) { // This is not the InitialBWP NR_PUSCH_Config_t *pusch_Config = bwp->bwp_Dedicated->pusch_Config->choice.setup; @@ -661,7 +663,7 @@ void nr_configure_pucch(nfapi_nr_pucch_pdu_t* pucch_pdu, pucch_pdu->initial_cyclic_shift = pucchres->format.choice.format0->initialCyclicShift; pucch_pdu->nr_of_symbols = pucchres->format.choice.format0->nrofSymbols; pucch_pdu->start_symbol_index = pucchres->format.choice.format0->startingSymbolIndex; - pucch_pdu->sr_flag = SR_flag; + pucch_pdu->sr_flag = O_sr; break; case NR_PUCCH_Resource__format_PR_format1 : pucch_pdu->format_type = 1; @@ -669,22 +671,23 @@ void nr_configure_pucch(nfapi_nr_pucch_pdu_t* pucch_pdu, pucch_pdu->nr_of_symbols = pucchres->format.choice.format1->nrofSymbols; pucch_pdu->start_symbol_index = pucchres->format.choice.format1->startingSymbolIndex; pucch_pdu->time_domain_occ_idx = pucchres->format.choice.format1->timeDomainOCC; - pucch_pdu->sr_flag = SR_flag; + pucch_pdu->sr_flag = O_sr; break; case NR_PUCCH_Resource__format_PR_format2 : pucch_pdu->format_type = 2; pucch_pdu->nr_of_symbols = pucchres->format.choice.format2->nrofSymbols; pucch_pdu->start_symbol_index = pucchres->format.choice.format2->startingSymbolIndex; - pucch_pdu->prb_size = pucchres->format.choice.format2->nrofPRBs; pucch_pdu->data_scrambling_id = pusch_id!= NULL ? *pusch_id : *scc->physCellId; pucch_pdu->dmrs_scrambling_id = id0!= NULL ? *id0 : *scc->physCellId; - pucch_pdu->bit_len_csi_part1 = O_uci-O_ack; + pucch_pdu->prb_size = compute_pucch_prb_size(2,pucchres->format.choice.format2->nrofPRBs, + O_uci+O_sr,O_csi,pucch_Config->format2->choice.setup->maxCodeRate, + 2,pucchres->format.choice.format2->nrofSymbols,8); + pucch_pdu->bit_len_csi_part1 = O_csi; break; case NR_PUCCH_Resource__format_PR_format3 : pucch_pdu->format_type = 3; pucch_pdu->nr_of_symbols = pucchres->format.choice.format3->nrofSymbols; pucch_pdu->start_symbol_index = pucchres->format.choice.format3->startingSymbolIndex; - pucch_pdu->prb_size = pucchres->format.choice.format3->nrofPRBs; pucch_pdu->data_scrambling_id = pusch_id!= NULL ? *pusch_id : *scc->physCellId; if (pucch_Config->format3 == NULL) { pucch_pdu->pi_2bpsk = 0; @@ -695,7 +698,19 @@ void nr_configure_pucch(nfapi_nr_pucch_pdu_t* pucch_pdu, pucch_pdu->pi_2bpsk = pucchfmt->pi2BPSK!= NULL ? 1 : 0; pucch_pdu->add_dmrs_flag = pucchfmt->additionalDMRS!= NULL ? 1 : 0; } - pucch_pdu->bit_len_csi_part1 = O_uci-O_ack; + int f3_dmrs_symbols; + if (pucchres->format.choice.format3->nrofSymbols==4) + f3_dmrs_symbols = 1<freq_hop_flag; + else { + if(pucchres->format.choice.format3->nrofSymbols<10) + f3_dmrs_symbols = 2; + else + f3_dmrs_symbols = 2<add_dmrs_flag; + } + pucch_pdu->prb_size = compute_pucch_prb_size(3,pucchres->format.choice.format3->nrofPRBs, + O_uci+O_sr,O_csi,pucch_Config->format3->choice.setup->maxCodeRate, + 2-pucch_pdu->pi_2bpsk,pucchres->format.choice.format3->nrofSymbols-f3_dmrs_symbols,12); + pucch_pdu->bit_len_csi_part1 = O_csi; break; case NR_PUCCH_Resource__format_PR_format4 : pucch_pdu->format_type = 4; @@ -713,7 +728,7 @@ void nr_configure_pucch(nfapi_nr_pucch_pdu_t* pucch_pdu, pucch_pdu->pi_2bpsk = pucchfmt->pi2BPSK!= NULL ? 1 : 0; pucch_pdu->add_dmrs_flag = pucchfmt->additionalDMRS!= NULL ? 1 : 0; } - pucch_pdu->bit_len_csi_part1 = O_uci-O_ack; + pucch_pdu->bit_len_csi_part1 = O_csi; break; default : AssertFatal(1==0,"Undefined PUCCH format \n"); @@ -729,6 +744,84 @@ void nr_configure_pucch(nfapi_nr_pucch_pdu_t* pucch_pdu, } +uint16_t compute_pucch_prb_size(uint8_t format, + uint8_t nr_prbs, + uint16_t O_tot, + uint16_t O_csi, + NR_PUCCH_MaxCodeRate_t *maxCodeRate, + uint8_t Qm, + uint8_t n_symb, + uint8_t n_re_ctrl) { + + uint16_t O_crc; + + if (O_tot<12) + O_crc = 0; + else{ + if (O_tot<20) + O_crc = 6; + else { + if (O_tot<360) + O_crc = 11; + else + AssertFatal(1==0,"Case for segmented PUCCH not yet implemented"); + } + } + + int rtimes100; + switch(*maxCodeRate){ + case NR_PUCCH_MaxCodeRate_zeroDot08 : + rtimes100 = 8; + break; + case NR_PUCCH_MaxCodeRate_zeroDot15 : + rtimes100 = 15; + break; + case NR_PUCCH_MaxCodeRate_zeroDot25 : + rtimes100 = 25; + break; + case NR_PUCCH_MaxCodeRate_zeroDot35 : + rtimes100 = 35; + break; + case NR_PUCCH_MaxCodeRate_zeroDot45 : + rtimes100 = 45; + break; + case NR_PUCCH_MaxCodeRate_zeroDot60 : + rtimes100 = 60; + break; + case NR_PUCCH_MaxCodeRate_zeroDot80 : + rtimes100 = 80; + break; + default : + AssertFatal(1==0,"Invalid MaxCodeRate"); + } + + float r = (float)rtimes100/100; + + if (O_csi == O_tot) { + if ((O_tot+O_csi)>(nr_prbs*n_re_ctrl*n_symb*Qm*r)) + AssertFatal(1==0,"MaxCodeRate %.2f can't support %d UCI bits and %d CRC bits with %d PRBs", + r,O_tot,O_crc,nr_prbs); + else + return nr_prbs; + } + + if (format==2){ + // TODO fix this for multiple CSI reports + for (int i=1; i<=nr_prbs; i++){ + if((O_tot+O_crc)<=(i*n_symb*Qm*n_re_ctrl*r) && + (O_tot+O_crc)>((i-1)*n_symb*Qm*n_re_ctrl*r)) + return i; + } + AssertFatal(1==0,"MaxCodeRate %.2f can't support %d UCI bits and %d CRC bits with at most %d PRBs", + r,O_tot,O_crc,nr_prbs); + } + else{ + AssertFatal(1==0,"Not yet implemented"); + } + +} + + void prepare_dci(NR_CellGroupConfig_t *secondaryCellGroup, dci_pdu_rel15_t *dci_pdu_rel15, nr_dci_format_t format, diff --git a/openair2/LAYER2/NR_MAC_gNB/mac_proto.h b/openair2/LAYER2/NR_MAC_gNB/mac_proto.h index 2ff5145943..64164c02f9 100644 --- a/openair2/LAYER2/NR_MAC_gNB/mac_proto.h +++ b/openair2/LAYER2/NR_MAC_gNB/mac_proto.h @@ -215,9 +215,9 @@ void nr_configure_pucch(nfapi_nr_pucch_pdu_t* pucch_pdu, NR_BWP_Uplink_t *bwp, uint16_t rnti, uint8_t pucch_resource, - uint16_t O_uci, + uint16_t O_csi, uint16_t O_ack, - uint8_t SR_flag); + uint8_t O_sr); void find_search_space(int ss_type, NR_BWP_Downlink_t *bwp, @@ -286,6 +286,15 @@ int allocate_nr_CCEs(gNB_MAC_INST *nr_mac, int m ); +uint16_t compute_pucch_prb_size(uint8_t format, + uint8_t nr_prbs, + uint16_t O_tot, + uint16_t O_csi, + NR_PUCCH_MaxCodeRate_t *maxCodeRate, + uint8_t Qm, + uint8_t n_symb, + uint8_t n_re_ctrl); + void update_csi_bitlen (NR_CSI_MeasConfig_t *csi_MeasConfig, NR_UE_list_t *UE_list, int UE_id); int get_dlscs(nfapi_nr_config_request_t *cfg); diff --git a/openair2/RRC/NR/rrc_gNB_reconfig.c b/openair2/RRC/NR/rrc_gNB_reconfig.c index decb99b173..3bc851ad03 100644 --- a/openair2/RRC/NR/rrc_gNB_reconfig.c +++ b/openair2/RRC/NR/rrc_gNB_reconfig.c @@ -911,7 +911,7 @@ void fill_default_secondaryCellGroup(NR_ServingCellConfigCommon_t *servingcellco pucchres2->secondHopPRB=NULL; pucchres2->format.present= NR_PUCCH_Resource__format_PR_format2; pucchres2->format.choice.format2=calloc(1,sizeof(*pucchres2->format.choice.format2)); - pucchres2->format.choice.format2->nrofPRBs=16; + pucchres2->format.choice.format2->nrofPRBs=4; pucchres2->format.choice.format2->nrofSymbols=1; pucchres2->format.choice.format2->startingSymbolIndex=13; ASN_SEQUENCE_ADD(&pucch_Config->resourceToAddModList->list,pucchres2); @@ -922,7 +922,7 @@ void fill_default_secondaryCellGroup(NR_ServingCellConfigCommon_t *servingcellco pucchres3->secondHopPRB=NULL; pucchres3->format.present= NR_PUCCH_Resource__format_PR_format2; pucchres3->format.choice.format2=calloc(1,sizeof(*pucchres3->format.choice.format2)); - pucchres3->format.choice.format2->nrofPRBs=16; + pucchres3->format.choice.format2->nrofPRBs=4; pucchres3->format.choice.format2->nrofSymbols=1; pucchres3->format.choice.format2->startingSymbolIndex=12; ASN_SEQUENCE_ADD(&pucch_Config->resourceToAddModList->list,pucchres3); @@ -934,7 +934,7 @@ void fill_default_secondaryCellGroup(NR_ServingCellConfigCommon_t *servingcellco pucchfmt2->interslotFrequencyHopping=NULL; pucchfmt2->additionalDMRS=NULL; pucchfmt2->maxCodeRate=calloc(1,sizeof(*pucchfmt2->maxCodeRate)); - *pucchfmt2->maxCodeRate=NR_PUCCH_MaxCodeRate_zeroDot15; + *pucchfmt2->maxCodeRate=NR_PUCCH_MaxCodeRate_zeroDot25; pucchfmt2->nrofSlots=NULL; pucchfmt2->pi2BPSK=NULL; pucchfmt2->simultaneousHARQ_ACK_CSI=NULL;