diff --git a/openair2/E2AP/RAN_FUNCTION/CUSTOMIZED/ran_func_mac.c b/openair2/E2AP/RAN_FUNCTION/CUSTOMIZED/ran_func_mac.c index 5a451cff01..13b6306a1c 100644 --- a/openair2/E2AP/RAN_FUNCTION/CUSTOMIZED/ran_func_mac.c +++ b/openair2/E2AP/RAN_FUNCTION/CUSTOMIZED/ran_func_mac.c @@ -66,7 +66,7 @@ bool read_mac_sm(void* data) } if (is_ul_slot(rd->slot, &RC.nrmac[mod_id]->frame_structure)) { rd->ul_curr_tbs = UE->mac_stats.ul.current_bytes; - rd->ul_sched_rb = sched_ctrl->sched_pusch.rbSize; + rd->ul_sched_rb = UE->mac_stats.ul.current_rbs; } rd->rnti = UE->rnti; diff --git a/openair2/LAYER2/NR_MAC_gNB/gNB_scheduler_phytest.c b/openair2/LAYER2/NR_MAC_gNB/gNB_scheduler_phytest.c index deaae2affb..6323ab4c6a 100644 --- a/openair2/LAYER2/NR_MAC_gNB/gNB_scheduler_phytest.c +++ b/openair2/LAYER2/NR_MAC_gNB/gNB_scheduler_phytest.c @@ -208,9 +208,11 @@ uint32_t target_ul_mcs = 9; uint32_t target_ul_bw = 50; uint32_t target_ul_Nl = 1; uint64_t ulsch_slot_bitmap = (1 << 8); -bool nr_ul_preprocessor_phytest(module_id_t module_id, frame_t frame, slot_t slot) +void nr_ul_preprocessor_phytest(gNB_MAC_INST *nr_mac, post_process_pusch_t *pp_pusch) { - gNB_MAC_INST *nr_mac = RC.nrmac[module_id]; + int frame = pp_pusch->frame; + int slot = pp_pusch->slot; + /* already mutex protected: held in gNB_dlsch_ulsch_scheduler() */ NR_COMMON_channels_t *cc = nr_mac->common_channels; NR_ServingCellConfigCommon_t *scc = cc->ServingCellConfigCommon; @@ -219,7 +221,7 @@ bool nr_ul_preprocessor_phytest(module_id_t module_id, frame_t frame, slot_t slo AssertFatal(nr_mac->UE_info.connected_ue_list[1] == NULL, "cannot handle more than one UE\n"); if (UE == NULL) - return false; + return; const int CC_id = 0; @@ -229,7 +231,7 @@ bool nr_ul_preprocessor_phytest(module_id_t module_id, frame_t frame, slot_t slo /* return if all UL HARQ processes wait for feedback */ if (sched_ctrl->retrans_ul_harq.head == -1 && sched_ctrl->available_ul_harq.head == -1) { LOG_D(NR_MAC, "[UE %04x][%4d.%2d] UE has no free UL HARQ process, skipping\n", UE->rnti, frame, slot); - return false; + return; } const int bw = ul_bwp->BWPSize; @@ -243,7 +245,7 @@ bool nr_ul_preprocessor_phytest(module_id_t module_id, frame_t frame, slot_t slo TYPE_C_RNTI_); const int temp_tda = get_ul_tda(nr_mac, frame, slot); if (temp_tda < 0) - return false; + return; AssertFatal(temp_tda < tdaList->list.count, "time domain assignment %d >= %d\n", temp_tda, tdaList->list.count); const int mu = ul_bwp->scs; int K2 = get_K2(tdaList, temp_tda, mu, scc); @@ -252,17 +254,18 @@ bool nr_ul_preprocessor_phytest(module_id_t module_id, frame_t frame, slot_t slo const int sched_slot = (slot + K2) % slots_frame; const int tda = get_ul_tda(nr_mac, sched_frame, sched_slot); if (tda < 0) - return false; + return; AssertFatal(tda < tdaList->list.count, "time domain assignment %d >= %d\n", tda, tdaList->list.count); + /* check if slot is UL, and that slot is 8 (assuming K2=6 because of UE * limitations). Note that if K2 or the TDD configuration is changed, below * conditions might exclude each other and never be true */ int slot_period = sched_slot % nr_mac->frame_structure.numb_slots_period; if (!is_xlsch_in_slot(ulsch_slot_bitmap, slot_period)) - return false; + return; NR_tda_info_t tda_info = get_ul_tda_info(ul_bwp, sched_ctrl->coreset->controlResourceSetId, @@ -270,7 +273,7 @@ bool nr_ul_preprocessor_phytest(module_id_t module_id, frame_t frame, slot_t slo TYPE_C_RNTI_, tda); if (!tda_info.valid_tda) - return false; + return; // TODO implement beam procedures for phy-test mode int beam = 0; @@ -280,7 +283,7 @@ bool nr_ul_preprocessor_phytest(module_id_t module_id, frame_t frame, slot_t slo for (int i = rbStart; i < rbStart + rbSize; ++i) { if ((vrb_map_UL[i+BWPStart] & SL_to_bitmap(tda_info.startSymbolIndex, tda_info.nrOfSymbols)) != 0) { LOG_E(MAC, "%4d.%2d RB %d is already reserved, cannot schedule UE\n", frame, slot, i); - return false; + return; } } @@ -295,7 +298,7 @@ bool nr_ul_preprocessor_phytest(module_id_t module_id, frame_t frame, slot_t slo 0); if (CCEIndex < 0) { LOG_E(MAC, "%s(): CCE list not empty, couldn't schedule PUSCH\n", __func__); - return false; + return; } sched_ctrl->cce_index = CCEIndex; @@ -337,7 +340,8 @@ bool nr_ul_preprocessor_phytest(module_id_t module_id, frame_t frame, slot_t slo sched.nrOfLayers /* NrOfLayers */) >> 3; - sched_ctrl->sched_pusch = sched; + /* save allocation to FAPI structures */ + post_process_ulsch(nr_mac, pp_pusch, UE, &sched); /* mark the corresponding RBs as used */ fill_pdcch_vrb_map(nr_mac, @@ -349,5 +353,4 @@ bool nr_ul_preprocessor_phytest(module_id_t module_id, frame_t frame, slot_t slo for (int rb = rbStart; rb < rbStart + rbSize; rb++) vrb_map_UL[rb+BWPStart] |= SL_to_bitmap(tda_info.startSymbolIndex, tda_info.nrOfSymbols); - return true; } diff --git a/openair2/LAYER2/NR_MAC_gNB/gNB_scheduler_primitives.c b/openair2/LAYER2/NR_MAC_gNB/gNB_scheduler_primitives.c index f8c842706c..a6de5b987d 100644 --- a/openair2/LAYER2/NR_MAC_gNB/gNB_scheduler_primitives.c +++ b/openair2/LAYER2/NR_MAC_gNB/gNB_scheduler_primitives.c @@ -2692,7 +2692,6 @@ NR_UE_info_t *get_new_nr_ue_inst(uid_allocator_t *uia, rnti_t rnti, NR_CellGroup /* set illegal time domain allocation to force recomputation of all fields */ sched_ctrl->sched_pdsch.time_domain_allocation = -1; - sched_ctrl->sched_pusch.time_domain_allocation = -1; /* Set default BWPs */ AssertFatal(UE->sc_info.n_ul_bwp <= NR_MAX_NUM_BWP, "uplinkBWP_ToAddModList has %d BWP!\n", UE->sc_info.n_ul_bwp); diff --git a/openair2/LAYER2/NR_MAC_gNB/gNB_scheduler_ulsch.c b/openair2/LAYER2/NR_MAC_gNB/gNB_scheduler_ulsch.c index 493c2a37e0..4e8bce0392 100644 --- a/openair2/LAYER2/NR_MAC_gNB/gNB_scheduler_ulsch.c +++ b/openair2/LAYER2/NR_MAC_gNB/gNB_scheduler_ulsch.c @@ -1700,17 +1700,18 @@ static void nr_ue_max_mcs_min_rb(int mu, } static bool allocate_ul_retransmission(gNB_MAC_INST *nrmac, - frame_t frame, - slot_t slot, - uint16_t *rballoc_mask, - int *n_rb_sched, - int dci_beam_idx, - NR_UE_info_t* UE, - int harq_pid, - const NR_ServingCellConfigCommon_t *scc, - const int tda) + post_process_pusch_t *pp_pusch, + uint16_t *rballoc_mask, + int *n_rb_sched, + int dci_beam_idx, + NR_UE_info_t *UE, + int harq_pid, + const NR_ServingCellConfigCommon_t *scc, + const int tda) { const int CC_id = 0; + int frame = pp_pusch->frame; + int slot = pp_pusch->slot; NR_UE_sched_ctrl_t *sched_ctrl = &UE->UE_sched_ctrl; /* Get previous PUSCH field info */ const NR_sched_pusch_t *retInfo = &sched_ctrl->ul_harq_processes[harq_pid].sched_pusch; @@ -1820,7 +1821,7 @@ static bool allocate_ul_retransmission(gNB_MAC_INST *nrmac, fill_pdcch_vrb_map(nrmac, CC_id, &sched_ctrl->sched_pdcch, CCEIndex, sched_ctrl->aggregation_level, dci_beam_idx); // signal new allocation - sched_ctrl->sched_pusch = new_sched; + post_process_ulsch(nrmac, pp_pusch, UE, &new_sched); LOG_D(NR_MAC, "%4d.%2d Allocate UL retransmission RNTI %04x sched %4d.%2d (%d RBs)\n", frame, @@ -1848,9 +1849,8 @@ static int comparator(const void *p, const void *q) { return ((UEsched_t*)p)->coef < ((UEsched_t*)q)->coef; } -static void pf_ul(module_id_t module_id, - frame_t frame, - int slot, +static void pf_ul(gNB_MAC_INST *nrmac, + post_process_pusch_t *pp_pusch, frame_t sched_frame, int sched_slot, NR_UE_info_t *UE_list[], @@ -1859,7 +1859,8 @@ static void pf_ul(module_id_t module_id, int n_rb_sched[num_beams]) { const int CC_id = 0; - gNB_MAC_INST *nrmac = RC.nrmac[module_id]; + int frame = pp_pusch->frame; + int slot = pp_pusch->slot; NR_ServingCellConfigCommon_t *scc = nrmac->common_channels[CC_id].ServingCellConfigCommon; int slots_per_frame = nrmac->frame_structure.numb_slots_frame; const int min_rb = nrmac->min_grant_prb; @@ -1880,13 +1881,16 @@ static void pf_ul(module_id_t module_id, LOG_D(NR_MAC,"pf_ul: preparing UL scheduling for UE %04x\n",UE->rnti); NR_UE_UL_BWP_t *current_BWP = &UE->current_UL_BWP; - const NR_mac_dir_stats_t *stats = &UE->mac_stats.ul; + NR_mac_dir_stats_t *stats = &UE->mac_stats.ul; /* Calculate throughput */ const float a = 0.01f; const uint32_t b = stats->current_bytes; UE->ul_thr_ue = (1 - a) * UE->ul_thr_ue + a * b; + stats->current_bytes = 0; + stats->current_rbs = 0; + int total_rem_ues = 0; for (int i = 0; i < num_beams; i++) total_rem_ues += remainUEs[i]; @@ -1915,8 +1919,7 @@ static void pf_ul(module_id_t module_id, /* Allocate retransmission*/ const int tda = get_ul_tda(nrmac, sched_frame, sched_slot); bool r = allocate_ul_retransmission(nrmac, - frame, - slot, + pp_pusch, rballoc_mask, &n_rb_sched[beam.idx], dci_beam.idx, @@ -2063,7 +2066,8 @@ static void pf_ul(module_id_t module_id, sched.dmrs_info.N_PRB_DMRS * sched.dmrs_info.num_dmrs_symb, deltaMCS, false); - sched_ctrl->sched_pusch = sched; + /* save allocation to FAPI structures */ + post_process_ulsch(nrmac, pp_pusch, UE, &sched); LOG_D(NR_MAC, "pf_ul %d.%d UE %x Scheduling PUSCH (no data) nrb %d mcs %d tbs %d bits phr_txpower %d\n", frame, @@ -2263,7 +2267,9 @@ static void pf_ul(module_id_t module_id, sched_ctrl->cce_index = CCEIndex; fill_pdcch_vrb_map(nrmac, CC_id, &sched_ctrl->sched_pdcch, CCEIndex, sched_ctrl->aggregation_level, dci_beam.idx); - sched_ctrl->sched_pusch = sched; + /* save allocation to FAPI structures */ + post_process_ulsch(nrmac, pp_pusch, iterator->UE, &sched); + n_rb_sched[beam.idx] -= sched.rbSize; for (int rb = bi.bwpStart; rb < sched.rbSize; rb++) rballoc_mask[rb + sched.rbStart] |= slbitmap; @@ -2374,7 +2380,7 @@ nfapi_nr_pusch_pdu_t *prepare_pusch_pdu(nfapi_nr_ul_tti_request_t *future_ul_tti return pusch_pdu; } -static void post_process_ulsch(gNB_MAC_INST *nr_mac, post_process_pusch_t *pusch, NR_UE_info_t *UE, NR_sched_pusch_t *sched_pusch) +void post_process_ulsch(gNB_MAC_INST *nr_mac, post_process_pusch_t *pusch, NR_UE_info_t *UE, NR_sched_pusch_t *sched_pusch) { frame_t frame = pusch->frame; slot_t slot = pusch->slot; @@ -2585,12 +2591,14 @@ static void post_process_ulsch(gNB_MAC_INST *nr_mac, post_process_pusch_t *pusch nr_mac->cset0_bwp_size); } -static bool nr_ulsch_preprocessor(module_id_t module_id, frame_t frame, slot_t slot) +static void nr_ulsch_preprocessor(gNB_MAC_INST *nr_mac, post_process_pusch_t *pp_pusch) { - gNB_MAC_INST *nr_mac = RC.nrmac[module_id]; + int frame = pp_pusch->frame; + int slot = pp_pusch->slot; + // no UEs if (nr_mac->UE_info.connected_ue_list[0] == NULL) - return false; + return; NR_COMMON_channels_t *cc = nr_mac->common_channels; NR_ServingCellConfigCommon_t *scc = cc->ServingCellConfigCommon; @@ -2603,7 +2611,7 @@ static bool nr_ulsch_preprocessor(module_id_t module_id, frame_t frame, slot_t s const int sched_frame = (frame + (slot + K2) / slots_frame) % MAX_FRAME_NUMBER; const int sched_slot = (slot + K2) % slots_frame; if (!is_ul_slot(sched_slot, &nr_mac->frame_structure)) - return false; + return; int num_beams = nr_mac->beam_info.beam_allocation ? nr_mac->beam_info.beams_per_period : 1; int bw = scc->uplinkConfigCommon->frequencyInfoUL->scs_SpecificCarrierList.list.array[0]->carrierBandwidth; @@ -2618,8 +2626,7 @@ static bool nr_ulsch_preprocessor(module_id_t module_id, frame_t frame, slot_t s max_sched_ues = min(max_sched_ues, MAX_DCI_CORESET); /* proportional fair scheduling algorithm */ - pf_ul(module_id, frame, slot, sched_frame, sched_slot, nr_mac->UE_info.connected_ue_list, max_sched_ues, num_beams, len); - return true; + pf_ul(nr_mac, pp_pusch, sched_frame, sched_slot, nr_mac->UE_info.connected_ue_list, max_sched_ues, num_beams, len); } nr_pp_impl_ul nr_init_ulsch_preprocessor(int CC_id) @@ -2659,38 +2666,15 @@ void nr_schedule_ulsch(module_id_t module_id, frame_t frame, slot_t slot, nfapi_ /* already mutex protected: held in gNB_dlsch_ulsch_scheduler() */ NR_SCHED_ENSURE_LOCKED(&nr_mac->sched_lock); + ul_dci_req->SFN = frame; + ul_dci_req->Slot = slot; + post_process_pusch_t pusch = { .frame = frame, .slot = slot, .ul_dci_req = ul_dci_req, .pdcch_pdu_coreset = {NULL}, }; + /* Uplink data ONLY can be scheduled when the current slot is downlink slot, * because we have to schedule the DCI0 first before schedule uplink data */ if (!is_dl_slot(slot, &nr_mac->frame_structure)) { LOG_D(NR_MAC, "Current slot %d is NOT DL slot, cannot schedule DCI0 for UL data\n", slot); return; } - bool do_sched = nr_mac->pre_processor_ul(module_id, frame, slot); - if (!do_sched) - return; - - ul_dci_req->SFN = frame; - ul_dci_req->Slot = slot; - post_process_pusch_t pusch = { frame, slot, ul_dci_req }; - - NR_UEs_t *UE_info = &nr_mac->UE_info; - UE_iterator(UE_info->connected_ue_list, UE) { - NR_UE_sched_ctrl_t *sched_ctrl = &UE->UE_sched_ctrl; - if (sched_ctrl->ul_failure && !get_softmodem_params()->phy_test) - continue; - - UE->mac_stats.ul.current_bytes = 0; - UE->mac_stats.ul.current_rbs = 0; - - /* dynamic PUSCH values (RB alloc, MCS, hence R, Qm, TBS) that change in - * every TTI are pre-populated by the preprocessor and used below */ - NR_sched_pusch_t *sched_pusch = &sched_ctrl->sched_pusch; - LOG_D(NR_MAC,"UE %04x : sched_pusch->rbSize %d\n",UE->rnti,sched_pusch->rbSize); - if (sched_pusch->rbSize <= 0) - continue; - - post_process_ulsch(nr_mac, &pusch, UE, sched_pusch); - - memset(sched_pusch, 0, sizeof(*sched_pusch)); - } + nr_mac->pre_processor_ul(nr_mac, &pusch); } diff --git a/openair2/LAYER2/NR_MAC_gNB/mac_proto.h b/openair2/LAYER2/NR_MAC_gNB/mac_proto.h index 66a9262f22..2c9e1a2a43 100644 --- a/openair2/LAYER2/NR_MAC_gNB/mac_proto.h +++ b/openair2/LAYER2/NR_MAC_gNB/mac_proto.h @@ -149,7 +149,7 @@ uint16_t nr_mac_compute_RIV(uint16_t N_RB_DL, uint16_t RBstart, uint16_t Lcrbs); void nr_preprocessor_phytest(module_id_t module_id, frame_t frame, slot_t slot); /* \brief UL preprocessor for phytest: schedules UE_id 0 with fixed MCS on a * fixed set of resources */ -bool nr_ul_preprocessor_phytest(module_id_t module_id, frame_t frame, slot_t slot); +void nr_ul_preprocessor_phytest(gNB_MAC_INST *nr_mac, post_process_pusch_t *pp_pusch); void handle_nr_uci_pucch_0_1(module_id_t mod_id, frame_t frame, @@ -498,4 +498,6 @@ void prepare_du_configuration_update(gNB_MAC_INST *mac, const NR_BCCH_DL_SCH_Message_t *sib1); void nr_mac_clean_cellgroup(NR_CellGroupConfig_t *cell_group); + +void post_process_ulsch(gNB_MAC_INST *nr_mac, post_process_pusch_t *pusch, NR_UE_info_t *UE, NR_sched_pusch_t *sched_pusch); #endif /*__LAYER2_NR_MAC_PROTO_H__*/ diff --git a/openair2/LAYER2/NR_MAC_gNB/nr_mac_gNB.h b/openair2/LAYER2/NR_MAC_gNB/nr_mac_gNB.h index ea7d80a214..1778d0507f 100644 --- a/openair2/LAYER2/NR_MAC_gNB/nr_mac_gNB.h +++ b/openair2/LAYER2/NR_MAC_gNB/nr_mac_gNB.h @@ -598,9 +598,6 @@ typedef struct { NR_sched_pucch_t *sched_pucch; int sched_pucch_size; - /// Sched PUSCH: scheduling decisions, copied into HARQ and cleared every TTI - NR_sched_pusch_t sched_pusch; - /// Sched SRS: scheduling decisions NR_sched_srs_t sched_srs; @@ -807,8 +804,12 @@ typedef struct { nfapi_nr_dl_tti_pdcch_pdu_rel15_t *pdcch_pdu_coreset[MAX_NUM_CORESET]; } post_process_pusch_t; +/* forward declaration to use in nr_pp_impl_dl */ +struct gNB_MAC_INST_s; +typedef struct gNB_MAC_INST_s gNB_MAC_INST; + typedef void (*nr_pp_impl_dl)(module_id_t mod_id, frame_t frame, slot_t slot); -typedef bool (*nr_pp_impl_ul)(module_id_t mod_id, frame_t frame, slot_t slot); +typedef void (*nr_pp_impl_ul)(gNB_MAC_INST *nr_mac, post_process_pusch_t *pp_pusch); typedef struct f1_config_t { f1ap_setup_req_t *setup_req;