MAC: use seq_arr to group LC configuration
Use a common structure nr_lc_config_t to group LC configuration for one logical channel. Use seq_arr for simple lookup, adding, removing of elements without manual indexing logic. This commit retains the previous logic of adding/releasing LCs through the process_CellGroupConfig(), although we know while building the CellGroupConfig if we add/release LCs. The next commit fixes this.
This commit is contained in:
@@ -1458,6 +1458,7 @@ add_library(L2_NR
|
||||
${MAC_NR_SRC}
|
||||
${GNB_APP_SRC}
|
||||
)
|
||||
target_link_libraries(L2_NR PRIVATE ds alg)
|
||||
|
||||
add_library(e1_if
|
||||
${NR_RRC_DIR}/cucp_cuup_direct.c
|
||||
|
||||
@@ -284,9 +284,9 @@ static arr_ue_id_t filter_ues_by_s_nssai_in_du_or_monolithic(const test_info_lst
|
||||
UE_iterator (RC.nrmac[0]->UE_info.list, ue) {
|
||||
NR_UE_sched_ctrl_t *sched_ctrl = &ue->UE_sched_ctrl;
|
||||
// UE matches if any of its DRBs matches
|
||||
for (int l = 0; l < sched_ctrl->dl_lc_num; ++l) {
|
||||
long lcid = sched_ctrl->dl_lc_ids[l];
|
||||
if (nssai_matches(sched_ctrl->dl_lc_nssai[lcid], sst, sd)) {
|
||||
for (size_t l = 0; l < seq_arr_size(&sched_ctrl->lc_config); ++l) {
|
||||
const nr_lc_config_t *c = seq_arr_at(&sched_ctrl->lc_config, l);
|
||||
if (nssai_matches(c->nssai, sst, sd)) {
|
||||
if (node_type == ngran_gNB_DU) {
|
||||
f1_ue_data_t rrc_ue_id = du_get_f1_ue_data(ue->rnti); // gNB CU UE ID = rrc_ue_id
|
||||
arr_ue_id.ue_id[arr_ue_id.sz] = fill_ue_id_data[ngran_gNB_DU](NULL, rrc_ue_id.secondary_ue, 0);
|
||||
|
||||
@@ -52,6 +52,8 @@
|
||||
#include "executables/softmodem-common.h"
|
||||
#include <complex.h>
|
||||
|
||||
#include "common/utils/alg/find.h"
|
||||
|
||||
extern RAN_CONTEXT_t RC;
|
||||
//extern int l2_init_gNB(void);
|
||||
extern uint8_t nfapi_mode;
|
||||
@@ -272,41 +274,30 @@ static void process_rlcBearerConfig(struct NR_CellGroupConfig__rlc_BearerToAddMo
|
||||
{
|
||||
if (rlc_bearer2release_list) {
|
||||
for (int i = 0; i < rlc_bearer2release_list->list.count; i++) {
|
||||
for (int idx = 0; idx < sched_ctrl->dl_lc_num; idx++) {
|
||||
if (sched_ctrl->dl_lc_ids[idx] == *rlc_bearer2release_list->list.array[i]) {
|
||||
const int remaining_lcs = sched_ctrl->dl_lc_num - idx - 1;
|
||||
memmove(&sched_ctrl->dl_lc_ids[idx], &sched_ctrl->dl_lc_ids[idx + 1], sizeof(sched_ctrl->dl_lc_ids[idx]) * remaining_lcs);
|
||||
sched_ctrl->dl_lc_num--;
|
||||
break;
|
||||
}
|
||||
}
|
||||
nr_lc_config_t c = {.lcid = *rlc_bearer2release_list->list.array[i]};
|
||||
elm_arr_t elm = find_if(&sched_ctrl->lc_config, &c, eq_lcid_config);
|
||||
if (elm.found)
|
||||
seq_arr_erase(&sched_ctrl->lc_config, elm.it);
|
||||
else
|
||||
LOG_E(NR_MAC, "could not remove rlc bearer: could not find bearer with ID %d\n", c.lcid);
|
||||
}
|
||||
}
|
||||
|
||||
if (rlc_bearer2add_list) {
|
||||
// keep lcids
|
||||
for (int i = 0; i < rlc_bearer2add_list->list.count; i++) {
|
||||
const int lcid = rlc_bearer2add_list->list.array[i]->logicalChannelIdentity;
|
||||
bool found = false;
|
||||
for (int idx = 0; idx < sched_ctrl->dl_lc_num; idx++) {
|
||||
if (sched_ctrl->dl_lc_ids[idx] == lcid) {
|
||||
found = true;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if (!found) {
|
||||
sched_ctrl->dl_lc_num++;
|
||||
sched_ctrl->dl_lc_ids[sched_ctrl->dl_lc_num - 1] = lcid;
|
||||
LOG_D(NR_MAC, "Adding LCID %d (%s %d)\n", lcid, lcid < 4 ? "SRB" : "DRB", lcid);
|
||||
nr_lc_config_t c = {.lcid = rlc_bearer2add_list->list.array[i]->logicalChannelIdentity};
|
||||
elm_arr_t elm = find_if(&sched_ctrl->lc_config, &c, eq_lcid_config);
|
||||
if (!elm.found) {
|
||||
LOG_D(NR_MAC, "Adding LCID %d (%s %d)\n", c.lcid, c.lcid < 4 ? "SRB" : "DRB", c.lcid);
|
||||
seq_arr_push_back(&sched_ctrl->lc_config, &c, sizeof(c));
|
||||
} else {
|
||||
LOG_W(NR_MAC, "cannot add LCID %d: already present\n", c.lcid);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
LOG_D(NR_MAC, "In %s: total num of active bearers %d) \n",
|
||||
__FUNCTION__,
|
||||
sched_ctrl->dl_lc_num);
|
||||
|
||||
LOG_D(NR_MAC, "total num of active bearers %ld\n", seq_arr_size(&sched_ctrl->lc_config));
|
||||
}
|
||||
|
||||
void process_CellGroup(NR_CellGroupConfig_t *CellGroup, NR_UE_info_t *UE)
|
||||
|
||||
@@ -329,8 +329,9 @@ static void nr_store_dlsch_buffer(module_id_t module_id, frame_t frame, sub_fram
|
||||
|
||||
/* loop over all activated logical channels */
|
||||
// Note: DL_SCH_LCID_DCCH, DL_SCH_LCID_DCCH1, DL_SCH_LCID_DTCH
|
||||
for (int i = 0; i < sched_ctrl->dl_lc_num; ++i) {
|
||||
const int lcid = sched_ctrl->dl_lc_ids[i];
|
||||
for (int i = 0; i < seq_arr_size(&sched_ctrl->lc_config); ++i) {
|
||||
const nr_lc_config_t *c = seq_arr_at(&sched_ctrl->lc_config, i);
|
||||
const int lcid = c->lcid;
|
||||
const uint16_t rnti = UE->rnti;
|
||||
LOG_D(NR_MAC, "In %s: UE %x: LCID %d\n", __FUNCTION__, rnti, lcid);
|
||||
if (lcid == DL_SCH_LCID_DTCH && sched_ctrl->rrc_processing_timer > 0) {
|
||||
@@ -1275,8 +1276,9 @@ void nr_schedule_ue_spec(module_id_t module_id,
|
||||
|
||||
if (sched_ctrl->num_total_bytes > 0) {
|
||||
/* loop over all activated logical channels */
|
||||
for (int i = 0; i < sched_ctrl->dl_lc_num; ++i) {
|
||||
const int lcid = sched_ctrl->dl_lc_ids[i];
|
||||
for (int i = 0; i < seq_arr_size(&sched_ctrl->lc_config); ++i) {
|
||||
const nr_lc_config_t *c = seq_arr_at(&sched_ctrl->lc_config, i);
|
||||
const int lcid = c->lcid;
|
||||
|
||||
if (sched_ctrl->rlc_status[lcid].bytes_in_buffer == 0)
|
||||
continue; // no data for this LC tbs_size_t len = 0;
|
||||
|
||||
@@ -104,9 +104,9 @@ void nr_preprocessor_phytest(module_id_t module_id,
|
||||
}
|
||||
|
||||
sched_ctrl->num_total_bytes = 0;
|
||||
sched_ctrl->dl_lc_num = 1;
|
||||
const int lcid = DL_SCH_LCID_DTCH;
|
||||
sched_ctrl->dl_lc_ids[sched_ctrl->dl_lc_num - 1] = lcid;
|
||||
DevAssert(seq_arr_size(&sched_ctrl->lc_config) == 1);
|
||||
const nr_lc_config_t *c = seq_arr_at(&sched_ctrl->lc_config, 0);
|
||||
const int lcid = c->lcid;
|
||||
const uint16_t rnti = UE->rnti;
|
||||
/* update sched_ctrl->num_total_bytes so that postprocessor schedules data,
|
||||
* if available */
|
||||
|
||||
@@ -2097,6 +2097,7 @@ void delete_nr_ue_data(NR_UE_info_t *UE, NR_COMMON_channels_t *ccPtr, uid_alloca
|
||||
ASN_STRUCT_FREE(asn_DEF_NR_CellGroupConfig, UE->reconfigCellGroup);
|
||||
ASN_STRUCT_FREE(asn_DEF_NR_UE_NR_Capability, UE->capability);
|
||||
NR_UE_sched_ctrl_t *sched_ctrl = &UE->UE_sched_ctrl;
|
||||
seq_arr_free(&sched_ctrl->lc_config, NULL);
|
||||
destroy_nr_list(&sched_ctrl->available_dl_harq);
|
||||
destroy_nr_list(&sched_ctrl->feedback_dl_harq);
|
||||
destroy_nr_list(&sched_ctrl->retrans_dl_harq);
|
||||
@@ -2490,6 +2491,9 @@ NR_UE_info_t *add_new_nr_ue(gNB_MAC_INST *nr_mac, rnti_t rntiP, NR_CellGroupConf
|
||||
sched_ctrl->sched_srs.frame = -1;
|
||||
sched_ctrl->sched_srs.slot = -1;
|
||||
|
||||
// initialize LCID structure
|
||||
seq_arr_init(&sched_ctrl->lc_config, sizeof(nr_lc_config_t));
|
||||
|
||||
// initialize UE BWP information
|
||||
NR_UE_DL_BWP_t *dl_bwp = &UE->current_DL_BWP;
|
||||
memset(dl_bwp, 0, sizeof(*dl_bwp));
|
||||
@@ -3220,3 +3224,10 @@ long get_lcid_from_srbid(int srb_id)
|
||||
{
|
||||
return srb_id;
|
||||
}
|
||||
|
||||
bool eq_lcid_config(const void *vval, const void *vit)
|
||||
{
|
||||
const nr_lc_config_t *val = (const nr_lc_config_t *)vval;
|
||||
const nr_lc_config_t *it = (const nr_lc_config_t *)vit;
|
||||
return it->lcid == val->lcid;
|
||||
}
|
||||
|
||||
@@ -443,4 +443,6 @@ void nr_mac_check_ul_failure(const gNB_MAC_INST *nrmac, int rnti, NR_UE_sched_ct
|
||||
|
||||
void nr_mac_trigger_reconfiguration(const gNB_MAC_INST *nrmac, const NR_UE_info_t *UE);
|
||||
|
||||
bool eq_lcid_config(const void *vval, const void *vit);
|
||||
|
||||
#endif /*__LAYER2_NR_MAC_PROTO_H__*/
|
||||
|
||||
@@ -28,6 +28,7 @@
|
||||
#include "F1AP_CauseRadioNetwork.h"
|
||||
#include "openair3/ocp-gtpu/gtp_itf.h"
|
||||
#include "openair2/LAYER2/nr_pdcp/nr_pdcp_oai_api.h"
|
||||
#include "common/utils/alg/find.h"
|
||||
|
||||
#include "uper_decoder.h"
|
||||
#include "uper_encoder.h"
|
||||
@@ -318,9 +319,13 @@ static void set_nssaiConfig(const int drb_len, const f1ap_drb_to_be_setup_t *req
|
||||
for (int i = 0; i < drb_len; i++) {
|
||||
const f1ap_drb_to_be_setup_t *drb = &req_drbs[i];
|
||||
|
||||
long lcid = get_lcid_from_drbid(drb->drb_id);
|
||||
sched_ctrl->dl_lc_nssai[lcid] = drb->nssai;
|
||||
LOG_I(NR_MAC, "Setting NSSAI sst: %d, sd: %d for DRB: %ld\n", drb->nssai.sst, drb->nssai.sd, drb->drb_id);
|
||||
nr_lc_config_t c = {.lcid = get_lcid_from_drbid(drb->drb_id)};
|
||||
elm_arr_t elm = find_if(&sched_ctrl->lc_config, &c, eq_lcid_config);
|
||||
if (elm.found) {
|
||||
nr_lc_config_t *c = (nr_lc_config_t *)elm.it;
|
||||
c->nssai = drb->nssai;
|
||||
LOG_I(NR_MAC, "Setting NSSAI sst: %d, sd: %d for DRB: %ld\n", drb->nssai.sst, drb->nssai.sd, drb->drb_id);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -335,8 +340,11 @@ static void set_QoSConfig(const f1ap_ue_context_modif_req_t *req, NR_UE_sched_ct
|
||||
for (int i = 0; i < drb_count; i++) {
|
||||
f1ap_drb_to_be_setup_t *drb_p = &req->drbs_to_be_setup[i];
|
||||
uint8_t nb_qos_flows = drb_p->drb_info.flows_to_be_setup_length;
|
||||
long drb_id = drb_p->drb_id;
|
||||
LOG_I(NR_MAC, "number of QOS flows mapped to DRB_id %ld: %d\n", drb_id, nb_qos_flows);
|
||||
nr_lc_config_t c = {.lcid = get_lcid_from_drbid(drb_p->drb_id)};
|
||||
elm_arr_t elm = find_if(&sched_ctrl->lc_config, &c, eq_lcid_config);
|
||||
DevAssert(elm.found);
|
||||
nr_lc_config_t *lc_config = (nr_lc_config_t *) elm.it;
|
||||
LOG_I(NR_MAC, "number of QOS flows mapped to LCID %d: %d\n", c.lcid, nb_qos_flows);
|
||||
|
||||
for (int q = 0; q < nb_qos_flows; q++) {
|
||||
f1ap_flows_mapped_to_drb_t *qos_flow = &drb_p->drb_info.flows_mapped_to_drb[q];
|
||||
@@ -355,14 +363,9 @@ static void set_QoSConfig(const f1ap_ue_context_modif_req_t *req, NR_UE_sched_ct
|
||||
priority = qos_priority[id];
|
||||
}
|
||||
}
|
||||
sched_ctrl->qos_config[drb_id - 1][q].fiveQI = fiveqi;
|
||||
sched_ctrl->qos_config[drb_id - 1][q].priority = priority;
|
||||
LOG_D(NR_MAC,
|
||||
"In %s: drb_id %ld: 5QI %lu priority %lu\n",
|
||||
__func__,
|
||||
drb_id,
|
||||
sched_ctrl->qos_config[drb_id - 1][q].fiveQI,
|
||||
sched_ctrl->qos_config[drb_id - 1][q].priority);
|
||||
lc_config->qos_config[q].fiveQI = fiveqi;
|
||||
lc_config->qos_config[q].priority = priority;
|
||||
LOG_D(NR_MAC, "LC ID %d: 5QI %lu priority %lu\n", c.lcid, fiveqi, priority);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -684,8 +687,10 @@ void dl_rrc_message_transfer(const f1ap_dl_rrc_message_t *dl_rrc)
|
||||
UE->expect_reconfiguration = false;
|
||||
/* Re-establish RLC for all remaining bearers */
|
||||
if (UE->reestablish_rlc) {
|
||||
for (int i = 1; i < UE->UE_sched_ctrl.dl_lc_num; ++i)
|
||||
nr_rlc_reestablish_entity(dl_rrc->gNB_DU_ue_id, UE->UE_sched_ctrl.dl_lc_ids[i]);
|
||||
for (int i = 1; i < seq_arr_size(&UE->UE_sched_ctrl.lc_config); ++i) {
|
||||
nr_lc_config_t *lc_config = seq_arr_at(&UE->UE_sched_ctrl.lc_config, i);
|
||||
nr_rlc_reestablish_entity(dl_rrc->gNB_DU_ue_id, lc_config->lcid);
|
||||
}
|
||||
UE->reestablish_rlc = false;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -170,15 +170,15 @@ size_t dump_mac_stats(gNB_MAC_INST *gNB, char *output, size_t strlen, bool reset
|
||||
"UE %04x: MAC: TX %14"PRIu64" RX %14"PRIu64" bytes\n",
|
||||
UE->rnti, stats->dl.total_bytes, stats->ul.total_bytes);
|
||||
|
||||
for (int i = 0; i < sched_ctrl->dl_lc_num; i++) {
|
||||
int lc_id = sched_ctrl->dl_lc_ids[i];
|
||||
for (int i = 0; i < seq_arr_size(&sched_ctrl->lc_config); i++) {
|
||||
const nr_lc_config_t *c = seq_arr_at(&sched_ctrl->lc_config, i);
|
||||
output += snprintf(output,
|
||||
end - output,
|
||||
"UE %04x: LCID %d: TX %14"PRIu64" RX %14"PRIu64" bytes\n",
|
||||
UE->rnti,
|
||||
lc_id,
|
||||
stats->dl.lc_bytes[lc_id],
|
||||
stats->ul.lc_bytes[lc_id]);
|
||||
c->lcid,
|
||||
stats->dl.lc_bytes[c->lcid],
|
||||
stats->ul.lc_bytes[c->lcid]);
|
||||
}
|
||||
}
|
||||
NR_SCHED_UNLOCK(&gNB->UE_info.mutex);
|
||||
|
||||
@@ -42,6 +42,7 @@
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
#include <pthread.h>
|
||||
#include "common/utils/ds/seq_arr.h"
|
||||
|
||||
#define NR_SCHED_LOCK(lock) \
|
||||
do { \
|
||||
@@ -519,6 +520,14 @@ typedef struct NR_QoS_config_s {
|
||||
uint64_t priority;
|
||||
} NR_QoS_config_t;
|
||||
|
||||
typedef struct nr_lc_config {
|
||||
uint8_t lcid;
|
||||
/// associated NSSAI for DRB
|
||||
nssai_t nssai;
|
||||
/// QoS config for DRB
|
||||
NR_QoS_config_t qos_config[NR_MAX_NUM_QFI];
|
||||
} nr_lc_config_t;
|
||||
|
||||
/*! \brief scheduling control information set through an API */
|
||||
#define MAX_CSI_REPORTS 48
|
||||
typedef struct {
|
||||
@@ -607,20 +616,15 @@ typedef struct {
|
||||
/// UL HARQ processes that await retransmission
|
||||
NR_list_t retrans_ul_harq;
|
||||
NR_UE_mac_ce_ctrl_t UE_mac_ce_ctrl; // MAC CE related information
|
||||
/// number of active DL LCs
|
||||
uint8_t dl_lc_num;
|
||||
/// order in which DLSCH scheduler should allocate LCs
|
||||
uint8_t dl_lc_ids[NR_MAX_NUM_LCID];
|
||||
|
||||
/// Timer for RRC processing procedures
|
||||
uint32_t rrc_processing_timer;
|
||||
|
||||
/// sri, ul_ri and tpmi based on SRS
|
||||
nr_srs_feedback_t srs_feedback;
|
||||
nssai_t dl_lc_nssai[NR_MAX_NUM_LCID];
|
||||
|
||||
// Information about the QoS configuration for each LCID/DRB
|
||||
NR_QoS_config_t qos_config[NR_MAX_NUM_LCID - 4][NR_MAX_NUM_QFI]; // 0 -CCCH and 1- 3 SRBs(0,1,2)
|
||||
/// per-LC configuration
|
||||
seq_arr_t lc_config;
|
||||
} NR_UE_sched_ctrl_t;
|
||||
|
||||
typedef struct {
|
||||
|
||||
Reference in New Issue
Block a user