Commit daefb90c authored by Sriharsha Korada's avatar Sriharsha Korada

Extension to PF algorithm based on qos flow priorities

parent c37974ca
...@@ -29,6 +29,7 @@ ...@@ -29,6 +29,7 @@
* @ingroup _mac * @ingroup _mac
*/ */
#define _GNU_SOURCE
#include "common/platform_types.h" #include "common/platform_types.h"
#include "common/platform_constants.h" #include "common/platform_constants.h"
...@@ -55,6 +56,65 @@ extern RAN_CONTEXT_t RC; ...@@ -55,6 +56,65 @@ extern RAN_CONTEXT_t RC;
//extern int l2_init_gNB(void); //extern int l2_init_gNB(void);
extern uint8_t nfapi_mode; extern uint8_t nfapi_mode;
/**
* This is a QoS comparator function for qsort.
*
* @lcid1 pointer to the first array element
* @lcid1 pointer to the second array element
* @return negative return value means that *p1 goes before *p2
* zero return value means that that *p1 is equivalent to *p2
* positive return value means that *p1 goes after *p2
**/
static int QoS_Comp(const void *lcid1, const void *lcid2, void *sctrl)
{
NR_UE_sched_ctrl_t *sched_ctrl = (NR_UE_sched_ctrl_t *)sctrl;
uint8_t lcid_1 = *(uint8_t *)lcid1;
uint8_t lcid_2 = *(uint8_t *)lcid2;
uint8_t *lc_priority = sched_ctrl->dl_lc_ids_priorities;
int32_t priority_1 = lc_priority[lcid_1];
int32_t priority_2 = lc_priority[lcid_2];
return (priority_1 - priority_2);
}
void process_lcOrder(NR_UE_sched_ctrl_t *sched_ctrl)
{
// Reset the priority of the UE
sched_ctrl->priority_ue = 0;
for (int i = 0; i < sched_ctrl->dl_lc_num; i++) {
uint8_t lcid = sched_ctrl->dl_lc_ids[i];
if (lcid < 4) {
/* each SRB is considered a priority of 1 */
sched_ctrl->dl_lc_ids_priorities[lcid] = 1;
} else {
/* sum of priorities of qos flows mapped to a DRB/LC */
uint8_t drb_id = lcid - 3; /* DRBID is LCID - 3 */
for (int q = 0; q < NR_MAX_NUM_QFI; q++)
sched_ctrl->dl_lc_ids_priorities[lcid] += sched_ctrl->qos_config[drb_id - 1][q].priority;
}
sched_ctrl->priority_ue += sched_ctrl->dl_lc_ids_priorities[lcid];
LOG_D(NR_MAC,
"The priority of the UE with lcid %d of priority %d is %d\n",
lcid,
sched_ctrl->dl_lc_ids_priorities[lcid],
sched_ctrl->priority_ue);
}
/* lc with in each UE are sorted so that lower in value(high priority) lcs are scheduled first*/
qsort_r(sched_ctrl->dl_lc_ids, sched_ctrl->dl_lc_num, sizeof(uint8_t), QoS_Comp, sched_ctrl->dl_lc_ids_priorities);
LOG_I(NR_MAC, "Printing logical channel ids sorted by Priority Level:\n");
for (int j = 0; j < sched_ctrl->dl_lc_num; j++) {
uint8_t lcid = sched_ctrl->dl_lc_ids[j];
LOG_I(NR_MAC,
"LCID %d (%s %d)\n",
lcid,
lcid < 4 ? "SRB" : "DRB",
lcid < 4 ? lcid : lcid - 3); // lcid 0 - SRB0, 1- SRB1, 2 - SRB2, 3 - 31 DRBs,
}
}
static void process_rlcBearerConfig(struct NR_CellGroupConfig__rlc_BearerToAddModList *rlc_bearer2add_list, static void process_rlcBearerConfig(struct NR_CellGroupConfig__rlc_BearerToAddModList *rlc_bearer2add_list,
struct NR_CellGroupConfig__rlc_BearerToReleaseList *rlc_bearer2release_list, struct NR_CellGroupConfig__rlc_BearerToReleaseList *rlc_bearer2release_list,
NR_UE_sched_ctrl_t *sched_ctrl) NR_UE_sched_ctrl_t *sched_ctrl)
...@@ -120,6 +180,7 @@ void process_CellGroup(NR_CellGroupConfig_t *CellGroup, NR_UE_info_t *UE) ...@@ -120,6 +180,7 @@ void process_CellGroup(NR_CellGroupConfig_t *CellGroup, NR_UE_info_t *UE)
nr_mac_prepare_ra_ue(RC.nrmac[0], UE->rnti, CellGroup); nr_mac_prepare_ra_ue(RC.nrmac[0], UE->rnti, CellGroup);
} }
process_rlcBearerConfig(CellGroup->rlc_BearerToAddModList, CellGroup->rlc_BearerToReleaseList, &UE->UE_sched_ctrl); process_rlcBearerConfig(CellGroup->rlc_BearerToAddModList, CellGroup->rlc_BearerToReleaseList, &UE->UE_sched_ctrl);
process_lcOrder(&UE->UE_sched_ctrl);
} }
static void config_common(gNB_MAC_INST *nrmac, int pdsch_AntennaPorts, int pusch_AntennaPorts, NR_ServingCellConfigCommon_t *scc) static void config_common(gNB_MAC_INST *nrmac, int pdsch_AntennaPorts, int pusch_AntennaPorts, NR_ServingCellConfigCommon_t *scc)
......
...@@ -653,6 +653,9 @@ static void pf_dl(module_id_t module_id, ...@@ -653,6 +653,9 @@ static void pf_dl(module_id_t module_id,
if (sched_ctrl->num_total_bytes == 0 && frame != (sched_ctrl->ta_frame + 10) % 1024) if (sched_ctrl->num_total_bytes == 0 && frame != (sched_ctrl->ta_frame + 10) % 1024)
continue; continue;
/* QoS processing*/
uint8_t aggregated_priority = sched_ctrl->priority_ue;
/* Calculate coeff */ /* Calculate coeff */
const NR_bler_options_t *bo = &mac->dl_bler; const NR_bler_options_t *bo = &mac->dl_bler;
const int max_mcs_table = current_BWP->mcsTableIdx == 1 ? 27 : 28; const int max_mcs_table = current_BWP->mcsTableIdx == 1 ? 27 : 28;
...@@ -674,14 +677,16 @@ static void pf_dl(module_id_t module_id, ...@@ -674,14 +677,16 @@ static void pf_dl(module_id_t module_id,
0 /* N_PRB_oh, 0 for initialBWP */, 0 /* N_PRB_oh, 0 for initialBWP */,
0 /* tb_scaling */, 0 /* tb_scaling */,
sched_pdsch->nrOfLayers) >> 3; sched_pdsch->nrOfLayers) >> 3;
float coeff_ue = (float) tbs / UE->dl_thr_ue; float coeff_ue = (float)tbs / (UE->dl_thr_ue * aggregated_priority);
LOG_D(NR_MAC, "[UE %04x][%4d.%2d] b %d, thr_ue %f, tbs %d, coeff_ue %f\n", LOG_D(NR_MAC,
"[UE %04x][%4d.%2d] b %d, thr_ue %f, tbs %d, ue_priority %d, coeff_ue %f\n",
UE->rnti, UE->rnti,
frame, frame,
slot, slot,
b, b,
UE->dl_thr_ue, UE->dl_thr_ue,
tbs, tbs,
aggregated_priority,
coeff_ue); coeff_ue);
/* Create UE_sched list for UEs eligible for new transmission*/ /* Create UE_sched list for UEs eligible for new transmission*/
UE_sched[curUE].coef=coeff_ue; UE_sched[curUE].coef=coeff_ue;
......
...@@ -252,7 +252,7 @@ static void set_QoSConfig(const f1ap_ue_context_modif_req_t *req, NR_UE_sched_ct ...@@ -252,7 +252,7 @@ static void set_QoSConfig(const f1ap_ue_context_modif_req_t *req, NR_UE_sched_ct
AssertFatal(req != NULL, "f1ap_ue_context_modif_req is NULL\n"); AssertFatal(req != NULL, "f1ap_ue_context_modif_req is NULL\n");
uint8_t drb_count = req->drbs_to_be_setup_length; uint8_t drb_count = req->drbs_to_be_setup_length;
uint8_t srb_count = req->srbs_to_be_setup_length; uint8_t srb_count = req->srbs_to_be_setup_length;
LOG_I(NR_MAC, "Number of DRBs = %d and SRBs = %d\n", drb_count, srb_count); LOG_D(NR_MAC, "Number of DRBs = %d and SRBs = %d\n", drb_count, srb_count);
/* DRBs*/ /* DRBs*/
for (int i = 0; i < drb_count; i++) { for (int i = 0; i < drb_count; i++) {
...@@ -272,7 +272,7 @@ static void set_QoSConfig(const f1ap_ue_context_modif_req_t *req, NR_UE_sched_ct ...@@ -272,7 +272,7 @@ static void set_QoSConfig(const f1ap_ue_context_modif_req_t *req, NR_UE_sched_ct
fiveqi = qos_char->dynamic.fiveqi > 0 ? qos_char->dynamic.fiveqi : 0; fiveqi = qos_char->dynamic.fiveqi > 0 ? qos_char->dynamic.fiveqi : 0;
} }
if (qos_char->qos_type == non_dynamic) { if (qos_char->qos_type == non_dynamic) {
LOG_D(NR_MAC, "Qos Priority level is considered from the standarsdized 5QI to QoS mapping table\n"); LOG_I(NR_MAC, "Qos Priority level is considered from the standarsdized 5QI to QoS mapping table\n");
for (int id = 0; id < 26; id++) { for (int id = 0; id < 26; id++) {
if (qos_fiveqi[id] == fiveqi) if (qos_fiveqi[id] == fiveqi)
priority = qos_priority[id]; priority = qos_priority[id];
...@@ -280,7 +280,7 @@ static void set_QoSConfig(const f1ap_ue_context_modif_req_t *req, NR_UE_sched_ct ...@@ -280,7 +280,7 @@ static void set_QoSConfig(const f1ap_ue_context_modif_req_t *req, NR_UE_sched_ct
} }
sched_ctrl->qos_config[drb_id - 1][q].fiveQI = fiveqi; sched_ctrl->qos_config[drb_id - 1][q].fiveQI = fiveqi;
sched_ctrl->qos_config[drb_id - 1][q].priority = priority; sched_ctrl->qos_config[drb_id - 1][q].priority = priority;
LOG_D(NR_MAC, LOG_I(NR_MAC,
"In %s: drb_id %ld: 5QI %lu priority %lu\n", "In %s: drb_id %ld: 5QI %lu priority %lu\n",
__func__, __func__,
drb_id, drb_id,
...@@ -353,12 +353,12 @@ void ue_context_setup_request(const f1ap_ue_context_setup_t *req) ...@@ -353,12 +353,12 @@ void ue_context_setup_request(const f1ap_ue_context_setup_t *req)
AssertFatal(enc_rval.encoded > 0, "Could not encode CellGroup, failed element %s\n", enc_rval.failed_type->name); AssertFatal(enc_rval.encoded > 0, "Could not encode CellGroup, failed element %s\n", enc_rval.failed_type->name);
resp.du_to_cu_rrc_information->cellGroupConfig_length = (enc_rval.encoded + 7) >> 3; resp.du_to_cu_rrc_information->cellGroupConfig_length = (enc_rval.encoded + 7) >> 3;
/* TODO: need to apply after UE context reconfiguration confirmed? */
nr_mac_prepare_cellgroup_update(mac, UE, new_CellGroup);
/* Fill the QoS config in MAC for each active DRB */ /* Fill the QoS config in MAC for each active DRB */
set_QoSConfig(req, &UE->UE_sched_ctrl); set_QoSConfig(req, &UE->UE_sched_ctrl);
/* TODO: need to apply after UE context reconfiguration confirmed? */
nr_mac_prepare_cellgroup_update(mac, UE, new_CellGroup);
/* Set NSSAI config in MAC for each active DRB */ /* Set NSSAI config in MAC for each active DRB */
set_nssaiConfig(req->drbs_to_be_setup_length, req->drbs_to_be_setup, &UE->UE_sched_ctrl); set_nssaiConfig(req->drbs_to_be_setup_length, req->drbs_to_be_setup, &UE->UE_sched_ctrl);
...@@ -457,11 +457,11 @@ void ue_context_modification_request(const f1ap_ue_context_modif_req_t *req) ...@@ -457,11 +457,11 @@ void ue_context_modification_request(const f1ap_ue_context_modif_req_t *req)
AssertFatal(enc_rval.encoded > 0, "Could not encode CellGroup, failed element %s\n", enc_rval.failed_type->name); AssertFatal(enc_rval.encoded > 0, "Could not encode CellGroup, failed element %s\n", enc_rval.failed_type->name);
resp.du_to_cu_rrc_information->cellGroupConfig_length = (enc_rval.encoded + 7) >> 3; resp.du_to_cu_rrc_information->cellGroupConfig_length = (enc_rval.encoded + 7) >> 3;
nr_mac_prepare_cellgroup_update(mac, UE, new_CellGroup);
/* Fill the QoS config in MAC for each active DRB */ /* Fill the QoS config in MAC for each active DRB */
set_QoSConfig(req, &UE->UE_sched_ctrl); set_QoSConfig(req, &UE->UE_sched_ctrl);
nr_mac_prepare_cellgroup_update(mac, UE, new_CellGroup);
/* Set NSSAI config in MAC for each active DRB */ /* Set NSSAI config in MAC for each active DRB */
set_nssaiConfig(req->drbs_to_be_setup_length, req->drbs_to_be_setup, &UE->UE_sched_ctrl); set_nssaiConfig(req->drbs_to_be_setup_length, req->drbs_to_be_setup, &UE->UE_sched_ctrl);
} else { } else {
......
...@@ -634,6 +634,8 @@ typedef struct { ...@@ -634,6 +634,8 @@ typedef struct {
uint8_t dl_lc_num; uint8_t dl_lc_num;
/// order in which DLSCH scheduler should allocate LCs /// order in which DLSCH scheduler should allocate LCs
uint8_t dl_lc_ids[NR_MAX_NUM_LCID]; uint8_t dl_lc_ids[NR_MAX_NUM_LCID];
// priorities of lcids
uint8_t dl_lc_ids_priorities[NR_MAX_NUM_LCID];
/// Timer for RRC processing procedures /// Timer for RRC processing procedures
uint32_t rrc_processing_timer; uint32_t rrc_processing_timer;
...@@ -642,8 +644,15 @@ typedef struct { ...@@ -642,8 +644,15 @@ typedef struct {
nr_srs_feedback_t srs_feedback; nr_srs_feedback_t srs_feedback;
nssai_t dl_lc_nssai[NR_MAX_NUM_LCID]; 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) Information about the QoS configuration for each LCID/DRB
(0 -CCCH and 1- 3 SRBs(0,1,2), 4-32 DRBs(0, 1, 28))
DRB Identity can be any value [1-32]
*/
NR_QoS_config_t qos_config[NR_MAX_NUM_LCID][NR_MAX_NUM_QFI];
// priority assigned to ue
uint8_t priority_ue;
} NR_UE_sched_ctrl_t; } NR_UE_sched_ctrl_t;
typedef struct { typedef struct {
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment