Add PDCCH UESS aggregation level configuration option
Added uess_agg_levels configuration option which changes the number of PDCCH candidates per aggregation level.
This commit is contained in:
@@ -150,6 +150,15 @@ typedef enum ip_traffic_type_e {
|
|||||||
TRAFFIC_PC5S_SESSION_INIT = 10
|
TRAFFIC_PC5S_SESSION_INIT = 10
|
||||||
} ip_traffic_type_t;
|
} ip_traffic_type_t;
|
||||||
|
|
||||||
|
typedef enum {
|
||||||
|
PDCCH_AGG_LEVEL1 = 0,
|
||||||
|
PDCCH_AGG_LEVEL2,
|
||||||
|
PDCCH_AGG_LEVEL4,
|
||||||
|
PDCCH_AGG_LEVEL8,
|
||||||
|
PDCCH_AGG_LEVEL16,
|
||||||
|
NUM_PDCCH_AGG_LEVELS
|
||||||
|
} Pdcch_Aggregation_Level_t;
|
||||||
|
|
||||||
typedef struct net_ip_address_s {
|
typedef struct net_ip_address_s {
|
||||||
unsigned ipv4: 1;
|
unsigned ipv4: 1;
|
||||||
unsigned ipv6: 1;
|
unsigned ipv6: 1;
|
||||||
|
|||||||
@@ -551,6 +551,18 @@ void get_coreset_rballoc(uint8_t *FreqDomainResource,int *n_rb,int *rb_offset) {
|
|||||||
*n_rb = 6*count;
|
*n_rb = 6*count;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// According to 38.211 7.3.2.2
|
||||||
|
int get_coreset_num_cces(uint8_t *FreqDomainResource, int duration)
|
||||||
|
{
|
||||||
|
int num_rbs;
|
||||||
|
int rb_offset;
|
||||||
|
get_coreset_rballoc(FreqDomainResource, &num_rbs, &rb_offset);
|
||||||
|
int total_resource_element_groups = num_rbs * duration;
|
||||||
|
int reg_per_cce = 6;
|
||||||
|
int total_cces = total_resource_element_groups / reg_per_cce;
|
||||||
|
return total_cces;
|
||||||
|
}
|
||||||
|
|
||||||
int get_nb_periods_per_frame(uint8_t tdd_period)
|
int get_nb_periods_per_frame(uint8_t tdd_period)
|
||||||
{
|
{
|
||||||
|
|
||||||
|
|||||||
@@ -245,6 +245,7 @@ uint32_t to_nrarfcn(int nr_bandP, uint64_t dl_CarrierFreq, uint8_t scs_index, ui
|
|||||||
int cce_to_reg_interleaving(const int R, int k, int n_shift, const int C, int L, const int N_regs);
|
int cce_to_reg_interleaving(const int R, int k, int n_shift, const int C, int L, const int N_regs);
|
||||||
int get_SLIV(uint8_t S, uint8_t L);
|
int get_SLIV(uint8_t S, uint8_t L);
|
||||||
void get_coreset_rballoc(uint8_t *FreqDomainResource,int *n_rb,int *rb_offset);
|
void get_coreset_rballoc(uint8_t *FreqDomainResource,int *n_rb,int *rb_offset);
|
||||||
|
int get_coreset_num_cces(uint8_t *FreqDomainResource, int duration);
|
||||||
int get_nr_table_idx(int nr_bandP, uint8_t scs_index);
|
int get_nr_table_idx(int nr_bandP, uint8_t scs_index);
|
||||||
int32_t get_delta_duplex(int nr_bandP, uint8_t scs_index);
|
int32_t get_delta_duplex(int nr_bandP, uint8_t scs_index);
|
||||||
frame_type_t get_frame_type(uint16_t nr_bandP, uint8_t scs_index);
|
frame_type_t get_frame_type(uint16_t nr_bandP, uint8_t scs_index);
|
||||||
|
|||||||
@@ -43,10 +43,15 @@ The actual scheduler implementation can be found in functions `pf_dl()` and
|
|||||||
PDCCH aggregation level is selected using closed loop controller, where DL HARQ
|
PDCCH aggregation level is selected using closed loop controller, where DL HARQ
|
||||||
feedback is the controller feedback signal. It is used to increment `pdcch_cl_adjust`
|
feedback is the controller feedback signal. It is used to increment `pdcch_cl_adjust`
|
||||||
variable if no feedback is detected and decrement the variable when feedback is detected.
|
variable if no feedback is detected and decrement the variable when feedback is detected.
|
||||||
`pdcch_cl_adjust` is later mapped PDCCH aggregation level range.
|
`pdcch_cl_adjust` is later mapped to the PDCCH aggregation level range.
|
||||||
|
|
||||||
The value of `pdcch_cl_adjust` is clamped to range <0,1>, the increment value is 0.05 while
|
The value of `pdcch_cl_adjust` is clamped to range <0,1>, the increment value is 0.05 while
|
||||||
the decrement value is 0.01.
|
the decrement value is 0.01. These values are selected to ensure PDCCH success rate is high.
|
||||||
|
See Examples below for futher explaination.
|
||||||
|
|
||||||
|
The possible values of aggregation level on UE SS can be configured via `uess_agg_levels` configuration
|
||||||
|
option. By default the gNB uses only aggregation level 2 which translates to `uess_agg_levels` set to
|
||||||
|
`[0, 1, 0, 0, 0]`. For example, to enable aggregation level 2 and 4 set `uess_agg_levels` to `[0, 1, 1, 0, 0]`.
|
||||||
|
|
||||||
### Examples:
|
### Examples:
|
||||||
#### Example 1:
|
#### Example 1:
|
||||||
|
|||||||
@@ -671,7 +671,8 @@ printf("%d\n", slot);
|
|||||||
.timer_config.n310 = 10,
|
.timer_config.n310 = 10,
|
||||||
.timer_config.t311 = 3000,
|
.timer_config.t311 = 3000,
|
||||||
.timer_config.n311 = 1,
|
.timer_config.n311 = 1,
|
||||||
.timer_config.t319 = 400};
|
.timer_config.t319 = 400,
|
||||||
|
.num_agg_level_candidates = {0, 0, 1, 1, 0}};
|
||||||
|
|
||||||
RC.nb_nr_macrlc_inst = 1;
|
RC.nb_nr_macrlc_inst = 1;
|
||||||
RC.nb_nr_mac_CC = (int*)malloc(RC.nb_nr_macrlc_inst*sizeof(int));
|
RC.nb_nr_mac_CC = (int*)malloc(RC.nb_nr_macrlc_inst*sizeof(int));
|
||||||
|
|||||||
@@ -1129,11 +1129,25 @@ static NR_ServingCellConfigCommon_t *get_scc_config(configmodule_interface_t *cf
|
|||||||
AssertFatal(pcc != NULL && pcc->commonSearchSpaceList == NULL, "memory leak\n");
|
AssertFatal(pcc != NULL && pcc->commonSearchSpaceList == NULL, "memory leak\n");
|
||||||
pcc->commonSearchSpaceList = calloc_or_fail(1, sizeof(*pcc->commonSearchSpaceList));
|
pcc->commonSearchSpaceList = calloc_or_fail(1, sizeof(*pcc->commonSearchSpaceList));
|
||||||
|
|
||||||
NR_SearchSpace_t *ss1 = rrc_searchspace_config(true, 1, 0);
|
// TODO: Make CSS aggregation levels configurable
|
||||||
|
int css_num_agg_level_candidates[NUM_PDCCH_AGG_LEVELS];
|
||||||
|
css_num_agg_level_candidates[PDCCH_AGG_LEVEL1] = NR_SearchSpace__nrofCandidates__aggregationLevel1_n0;
|
||||||
|
if (get_softmodem_params()->usim_test) {
|
||||||
|
css_num_agg_level_candidates[PDCCH_AGG_LEVEL2] = NR_SearchSpace__nrofCandidates__aggregationLevel2_n0;
|
||||||
|
css_num_agg_level_candidates[PDCCH_AGG_LEVEL4] = NR_SearchSpace__nrofCandidates__aggregationLevel4_n1;
|
||||||
|
css_num_agg_level_candidates[PDCCH_AGG_LEVEL8] = NR_SearchSpace__nrofCandidates__aggregationLevel8_n1;
|
||||||
|
} else {
|
||||||
|
css_num_agg_level_candidates[PDCCH_AGG_LEVEL2] = NR_SearchSpace__nrofCandidates__aggregationLevel2_n0;
|
||||||
|
css_num_agg_level_candidates[PDCCH_AGG_LEVEL4] = NR_SearchSpace__nrofCandidates__aggregationLevel4_n1;
|
||||||
|
css_num_agg_level_candidates[PDCCH_AGG_LEVEL8] = NR_SearchSpace__nrofCandidates__aggregationLevel8_n0;
|
||||||
|
}
|
||||||
|
css_num_agg_level_candidates[PDCCH_AGG_LEVEL16] = NR_SearchSpace__nrofCandidates__aggregationLevel16_n0;
|
||||||
|
|
||||||
|
NR_SearchSpace_t *ss1 = rrc_searchspace_config(true, 1, 0, css_num_agg_level_candidates);
|
||||||
asn1cSeqAdd(&pcc->commonSearchSpaceList->list, ss1);
|
asn1cSeqAdd(&pcc->commonSearchSpaceList->list, ss1);
|
||||||
NR_SearchSpace_t *ss2 = rrc_searchspace_config(true, 2, 0);
|
NR_SearchSpace_t *ss2 = rrc_searchspace_config(true, 2, 0, css_num_agg_level_candidates);
|
||||||
asn1cSeqAdd(&pcc->commonSearchSpaceList->list, ss2);
|
asn1cSeqAdd(&pcc->commonSearchSpaceList->list, ss2);
|
||||||
NR_SearchSpace_t *ss3 = rrc_searchspace_config(true, 3, 0);
|
NR_SearchSpace_t *ss3 = rrc_searchspace_config(true, 3, 0, css_num_agg_level_candidates);
|
||||||
asn1cSeqAdd(&pcc->commonSearchSpaceList->list, ss3);
|
asn1cSeqAdd(&pcc->commonSearchSpaceList->list, ss3);
|
||||||
|
|
||||||
asn1cCallocOne(pcc->searchSpaceSIB1, 0);
|
asn1cCallocOne(pcc->searchSpaceSIB1, 0);
|
||||||
@@ -1501,6 +1515,34 @@ void RCconfig_nr_macrlc(configmodule_interface_t *cfg)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Construct default aggragation level list or read from config
|
||||||
|
int uess_num_agg_level_candidates[NUM_PDCCH_AGG_LEVELS];
|
||||||
|
uess_num_agg_level_candidates[PDCCH_AGG_LEVEL1] = NR_SearchSpace__nrofCandidates__aggregationLevel1_n0;
|
||||||
|
if (get_softmodem_params()->usim_test) {
|
||||||
|
uess_num_agg_level_candidates[PDCCH_AGG_LEVEL2] = NR_SearchSpace__nrofCandidates__aggregationLevel2_n0;
|
||||||
|
uess_num_agg_level_candidates[PDCCH_AGG_LEVEL4] = NR_SearchSpace__nrofCandidates__aggregationLevel4_n1;
|
||||||
|
uess_num_agg_level_candidates[PDCCH_AGG_LEVEL8] = NR_SearchSpace__nrofCandidates__aggregationLevel8_n1;
|
||||||
|
} else {
|
||||||
|
uess_num_agg_level_candidates[PDCCH_AGG_LEVEL2] = NR_SearchSpace__nrofCandidates__aggregationLevel2_n2;
|
||||||
|
uess_num_agg_level_candidates[PDCCH_AGG_LEVEL4] = NR_SearchSpace__nrofCandidates__aggregationLevel4_n0;
|
||||||
|
uess_num_agg_level_candidates[PDCCH_AGG_LEVEL8] = NR_SearchSpace__nrofCandidates__aggregationLevel8_n0;
|
||||||
|
}
|
||||||
|
uess_num_agg_level_candidates[PDCCH_AGG_LEVEL16] = NR_SearchSpace__nrofCandidates__aggregationLevel16_n0;
|
||||||
|
int* agg_level_list = uess_num_agg_level_candidates;
|
||||||
|
int num_agg_levels = 5;
|
||||||
|
if (GNBParamList.paramarray[0][GNB_UESS_AGG_LEVEL_LIST_IDX].numelt > 0) {
|
||||||
|
agg_level_list = GNBParamList.paramarray[0][GNB_UESS_AGG_LEVEL_LIST_IDX].iptr;
|
||||||
|
num_agg_levels = GNBParamList.paramarray[0][GNB_UESS_AGG_LEVEL_LIST_IDX].numelt;
|
||||||
|
}
|
||||||
|
memcpy(config.num_agg_level_candidates, agg_level_list, sizeof(int) * num_agg_levels);
|
||||||
|
LOG_I(NR_MAC,
|
||||||
|
"Candidates per PDCCH aggregation level on UESS: L1: %d, L2: %d, L4: %d, L8: %d, L16: %d\n",
|
||||||
|
config.num_agg_level_candidates[PDCCH_AGG_LEVEL1],
|
||||||
|
config.num_agg_level_candidates[PDCCH_AGG_LEVEL2],
|
||||||
|
config.num_agg_level_candidates[PDCCH_AGG_LEVEL4],
|
||||||
|
config.num_agg_level_candidates[PDCCH_AGG_LEVEL8],
|
||||||
|
config.num_agg_level_candidates[PDCCH_AGG_LEVEL16]);
|
||||||
|
|
||||||
NR_ServingCellConfigCommon_t *scc = get_scc_config(cfg, config.minRXTXTIME);
|
NR_ServingCellConfigCommon_t *scc = get_scc_config(cfg, config.minRXTXTIME);
|
||||||
//xer_fprint(stdout, &asn_DEF_NR_ServingCellConfigCommon, scc);
|
//xer_fprint(stdout, &asn_DEF_NR_ServingCellConfigCommon, scc);
|
||||||
NR_ServingCellConfig_t *scd = get_scd_config(cfg);
|
NR_ServingCellConfig_t *scd = get_scd_config(cfg);
|
||||||
|
|||||||
@@ -138,6 +138,7 @@ typedef enum {
|
|||||||
#define GNB_CONFIG_STRING_NUM_DL_HARQPROCESSES "num_dlharq"
|
#define GNB_CONFIG_STRING_NUM_DL_HARQPROCESSES "num_dlharq"
|
||||||
#define GNB_CONFIG_STRING_NUM_UL_HARQPROCESSES "num_ulharq"
|
#define GNB_CONFIG_STRING_NUM_UL_HARQPROCESSES "num_ulharq"
|
||||||
#define GNB_CONFIG_STRING_BEAM_WEIGHTS_LIST "beam_weights"
|
#define GNB_CONFIG_STRING_BEAM_WEIGHTS_LIST "beam_weights"
|
||||||
|
#define GNB_CONFIG_STRING_UESS_AGG_LEVEL_LIST "uess_agg_levels"
|
||||||
|
|
||||||
#define GNB_CONFIG_HLP_STRING_ENABLE_SDAP "enable the SDAP layer\n"
|
#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"
|
#define GNB_CONFIG_HLP_FORCE256QAMOFF "suppress activation of 256 QAM despite UE support"
|
||||||
@@ -148,6 +149,7 @@ typedef enum {
|
|||||||
#define GNB_CONFIG_HLP_GNB_CU_UP_ID "defines the gNB-CU-UP ID (only applicable for CU-UP)"
|
#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_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"
|
#define GNB_CONFIG_HLP_NUM_UL_HARQ "Set Num UL harq processes. Valid values 16,32. Default 16"
|
||||||
|
#define GNB_CONFIG_HLP_UESS_AGG_LEVEL_LIST "List of aggregation levels with number of candidates per level. Element 0 - aggregation level 1"
|
||||||
|
|
||||||
/*-----------------------------------------------------------------------------------------------------------------------------------------*/
|
/*-----------------------------------------------------------------------------------------------------------------------------------------*/
|
||||||
/* cell configuration parameters */
|
/* cell configuration parameters */
|
||||||
@@ -191,6 +193,8 @@ typedef enum {
|
|||||||
{GNB_CONFIG_STRING_NUM_DL_HARQPROCESSES, GNB_CONFIG_HLP_NUM_DL_HARQ, 0, .iptr=NULL, .defintval=16, 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}, \
|
{GNB_CONFIG_STRING_NUM_UL_HARQPROCESSES, GNB_CONFIG_HLP_NUM_UL_HARQ, 0, .iptr=NULL, .defintval=16, TYPE_INT, 0}, \
|
||||||
{GNB_CONFIG_STRING_BEAM_WEIGHTS_LIST, NULL, 0, .iptr=NULL, .defintarrayval=0, TYPE_INTARRAY, 0}, \
|
{GNB_CONFIG_STRING_BEAM_WEIGHTS_LIST, NULL, 0, .iptr=NULL, .defintarrayval=0, TYPE_INTARRAY, 0}, \
|
||||||
|
{GNB_CONFIG_STRING_UESS_AGG_LEVEL_LIST, \
|
||||||
|
GNB_CONFIG_HLP_UESS_AGG_LEVEL_LIST, 0, .iptr=NULL, .defintarrayval=NULL, TYPE_INTARRAY, 0}, \
|
||||||
}
|
}
|
||||||
// clang-format on
|
// clang-format on
|
||||||
|
|
||||||
@@ -231,6 +235,7 @@ typedef enum {
|
|||||||
#define GNB_NUM_DL_HARQ_IDX 33
|
#define GNB_NUM_DL_HARQ_IDX 33
|
||||||
#define GNB_NUM_UL_HARQ_IDX 34
|
#define GNB_NUM_UL_HARQ_IDX 34
|
||||||
#define GNB_BEAMWEIGHTS_IDX 35
|
#define GNB_BEAMWEIGHTS_IDX 35
|
||||||
|
#define GNB_UESS_AGG_LEVEL_LIST_IDX 36
|
||||||
|
|
||||||
#define TRACKING_AREA_CODE_OKRANGE {0x0001,0xFFFD}
|
#define TRACKING_AREA_CODE_OKRANGE {0x0001,0xFFFD}
|
||||||
#define NUM_DL_HARQ_OKVALUES {2,4,6,8,10,12,16,32}
|
#define NUM_DL_HARQ_OKVALUES {2,4,6,8,10,12,16,32}
|
||||||
@@ -273,6 +278,7 @@ typedef enum {
|
|||||||
{ .s1 = { config_check_intval, NUM_DL_HARQ_OKVALUES,8 } }, \
|
{ .s1 = { config_check_intval, NUM_DL_HARQ_OKVALUES,8 } }, \
|
||||||
{ .s1 = { config_check_intval, NUM_UL_HARQ_OKVALUES,2 } }, \
|
{ .s1 = { config_check_intval, NUM_UL_HARQ_OKVALUES,2 } }, \
|
||||||
{ .s5 = { NULL } }, \
|
{ .s5 = { NULL } }, \
|
||||||
|
{ .s5 = { NULL } }, \
|
||||||
}
|
}
|
||||||
|
|
||||||
/*-------------------------------------------------------------------------------------------------------------------------------------------------*/
|
/*-------------------------------------------------------------------------------------------------------------------------------------------------*/
|
||||||
|
|||||||
@@ -125,15 +125,6 @@ typedef enum {
|
|||||||
nrRA_WAIT_Msg4_MsgB_ACK,
|
nrRA_WAIT_Msg4_MsgB_ACK,
|
||||||
} RA_gNB_state_t;
|
} RA_gNB_state_t;
|
||||||
|
|
||||||
typedef enum {
|
|
||||||
PDCCH_AGG_LEVEL1 = 0,
|
|
||||||
PDCCH_AGG_LEVEL2,
|
|
||||||
PDCCH_AGG_LEVEL4,
|
|
||||||
PDCCH_AGG_LEVEL8,
|
|
||||||
PDCCH_AGG_LEVEL16,
|
|
||||||
NUM_PDCCH_AGG_LEVELS
|
|
||||||
} Pdcch_Aggregation_Level_t;
|
|
||||||
|
|
||||||
static const char *const nrra_text[] =
|
static const char *const nrra_text[] =
|
||||||
{"IDLE", "Msg2", "WAIT_MsgA_PUSCH", "WAIT_Msg3", "Msg3_retransmission", "Msg3_dcch_dtch", "Msg4", "MsgB", "WAIT_Msg4_ACK"};
|
{"IDLE", "Msg2", "WAIT_MsgA_PUSCH", "WAIT_Msg3", "Msg3_retransmission", "Msg3_dcch_dtch", "Msg4", "MsgB", "WAIT_Msg4_ACK"};
|
||||||
|
|
||||||
@@ -181,6 +172,7 @@ typedef struct nr_mac_config_t {
|
|||||||
/// beamforming weight matrix size
|
/// beamforming weight matrix size
|
||||||
int nb_bfw[2];
|
int nb_bfw[2];
|
||||||
int32_t *bw_list;
|
int32_t *bw_list;
|
||||||
|
int num_agg_level_candidates[NUM_PDCCH_AGG_LEVELS];
|
||||||
} nr_mac_config_t;
|
} nr_mac_config_t;
|
||||||
|
|
||||||
typedef struct NR_preamble_ue {
|
typedef struct NR_preamble_ue {
|
||||||
|
|||||||
@@ -72,6 +72,50 @@ static NR_BWP_t clone_generic_parameters(const NR_BWP_t *gp)
|
|||||||
return clone;
|
return clone;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief Verifies the aggregation level candidates
|
||||||
|
*
|
||||||
|
* This function checks the input aggregation level candidates and translates the value provided
|
||||||
|
* in the config to a valid field in RRC message.
|
||||||
|
*
|
||||||
|
* @param[in] num_cce_in_coreset number of CCE in coreset
|
||||||
|
* @param[in] in_num_agg_level_candidates input array of aggregation level candidates, interpreted as number of candidates.
|
||||||
|
* @param[in] coresetid coreset id
|
||||||
|
* @param[in] searchspaceid searchspace id
|
||||||
|
* @param[out] out_num_agg_level_candidates array of aggregation level candidates, output is a valid 3gpp field value.
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
static void verify_agg_levels(int num_cce_in_coreset,
|
||||||
|
const int in_num_agg_level_candidates[NUM_PDCCH_AGG_LEVELS],
|
||||||
|
int coresetid,
|
||||||
|
int searchspaceid,
|
||||||
|
int out_num_agg_level_candidates[NUM_PDCCH_AGG_LEVELS])
|
||||||
|
{
|
||||||
|
int agg_level_to_n_cces[] = {1, 2, 4, 8, 16};
|
||||||
|
for (int i = 0; i < NUM_PDCCH_AGG_LEVELS; i++) {
|
||||||
|
// 7 is not a valid value, the mapping in 38.331 is from 0-7 mapped to 0-8 candidates and value 7 means 8 candidates instead. If
|
||||||
|
// the user wants 7 candidates round it up to 8.
|
||||||
|
int num_agg_level_candidates = in_num_agg_level_candidates[i];
|
||||||
|
if (num_agg_level_candidates == 7) {
|
||||||
|
num_agg_level_candidates = 8;
|
||||||
|
}
|
||||||
|
if (num_agg_level_candidates * agg_level_to_n_cces[i] > num_cce_in_coreset) {
|
||||||
|
int new_agg_level_candidates = num_cce_in_coreset / agg_level_to_n_cces[i];
|
||||||
|
LOG_E(NR_RRC,
|
||||||
|
"Invalid configuration: Not enough CCEs in coreset %d, searchspace %d, agg_level %d, number of requested "
|
||||||
|
"candidates = %d, number of CCES in coreset %d. Aggregation level candidates limited to %d\n",
|
||||||
|
coresetid,
|
||||||
|
searchspaceid,
|
||||||
|
agg_level_to_n_cces[i],
|
||||||
|
in_num_agg_level_candidates[i],
|
||||||
|
num_cce_in_coreset,
|
||||||
|
new_agg_level_candidates);
|
||||||
|
num_agg_level_candidates = new_agg_level_candidates;
|
||||||
|
}
|
||||||
|
out_num_agg_level_candidates[i] = min(num_agg_level_candidates, 7);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
static NR_SetupRelease_RACH_ConfigCommon_t *clone_rach_configcommon(const NR_SetupRelease_RACH_ConfigCommon_t *rcc)
|
static NR_SetupRelease_RACH_ConfigCommon_t *clone_rach_configcommon(const NR_SetupRelease_RACH_ConfigCommon_t *rcc)
|
||||||
{
|
{
|
||||||
if (rcc == NULL || rcc->present == NR_SetupRelease_RACH_ConfigCommon_PR_NOTHING)
|
if (rcc == NULL || rcc->present == NR_SetupRelease_RACH_ConfigCommon_PR_NOTHING)
|
||||||
@@ -208,9 +252,11 @@ static int get_nb_pucch2_per_slot(const NR_ServingCellConfigCommon_t *scc, int b
|
|||||||
return nb_pucch2;
|
return nb_pucch2;
|
||||||
}
|
}
|
||||||
|
|
||||||
NR_SearchSpace_t *rrc_searchspace_config(bool is_common, int searchspaceid, int coresetid)
|
NR_SearchSpace_t *rrc_searchspace_config(bool is_common,
|
||||||
|
int searchspaceid,
|
||||||
|
int coresetid,
|
||||||
|
const int num_agg_level_candidates[NUM_PDCCH_AGG_LEVELS])
|
||||||
{
|
{
|
||||||
|
|
||||||
NR_SearchSpace_t *ss = calloc(1,sizeof(*ss));
|
NR_SearchSpace_t *ss = calloc(1,sizeof(*ss));
|
||||||
ss->searchSpaceId = searchspaceid;
|
ss->searchSpaceId = searchspaceid;
|
||||||
ss->controlResourceSetId = calloc(1,sizeof(*ss->controlResourceSetId));
|
ss->controlResourceSetId = calloc(1,sizeof(*ss->controlResourceSetId));
|
||||||
@@ -226,23 +272,12 @@ NR_SearchSpace_t *rrc_searchspace_config(bool is_common, int searchspaceid, int
|
|||||||
ss->monitoringSymbolsWithinSlot->buf[1] = 0x0;
|
ss->monitoringSymbolsWithinSlot->buf[1] = 0x0;
|
||||||
ss->monitoringSymbolsWithinSlot->bits_unused = 2;
|
ss->monitoringSymbolsWithinSlot->bits_unused = 2;
|
||||||
ss->nrofCandidates = calloc(1,sizeof(*ss->nrofCandidates));
|
ss->nrofCandidates = calloc(1,sizeof(*ss->nrofCandidates));
|
||||||
// TODO temporary hardcoded implementation
|
ss->nrofCandidates->aggregationLevel1 = num_agg_level_candidates[PDCCH_AGG_LEVEL1];
|
||||||
ss->nrofCandidates->aggregationLevel1 = NR_SearchSpace__nrofCandidates__aggregationLevel1_n0;
|
ss->nrofCandidates->aggregationLevel2 = num_agg_level_candidates[PDCCH_AGG_LEVEL2];
|
||||||
if (get_softmodem_params()->usim_test) {
|
ss->nrofCandidates->aggregationLevel4 = num_agg_level_candidates[PDCCH_AGG_LEVEL4];
|
||||||
ss->nrofCandidates->aggregationLevel2 = NR_SearchSpace__nrofCandidates__aggregationLevel2_n0;
|
ss->nrofCandidates->aggregationLevel8 = num_agg_level_candidates[PDCCH_AGG_LEVEL8];
|
||||||
ss->nrofCandidates->aggregationLevel4 = NR_SearchSpace__nrofCandidates__aggregationLevel4_n1;
|
ss->nrofCandidates->aggregationLevel16 = num_agg_level_candidates[PDCCH_AGG_LEVEL16];
|
||||||
ss->nrofCandidates->aggregationLevel8 = NR_SearchSpace__nrofCandidates__aggregationLevel8_n1;
|
|
||||||
} else {
|
|
||||||
if (is_common) {
|
|
||||||
ss->nrofCandidates->aggregationLevel2 = NR_SearchSpace__nrofCandidates__aggregationLevel2_n0;
|
|
||||||
ss->nrofCandidates->aggregationLevel4 = NR_SearchSpace__nrofCandidates__aggregationLevel4_n1;
|
|
||||||
} else {
|
|
||||||
ss->nrofCandidates->aggregationLevel2 = NR_SearchSpace__nrofCandidates__aggregationLevel2_n2;
|
|
||||||
ss->nrofCandidates->aggregationLevel4 = NR_SearchSpace__nrofCandidates__aggregationLevel4_n0;
|
|
||||||
}
|
|
||||||
ss->nrofCandidates->aggregationLevel8 = NR_SearchSpace__nrofCandidates__aggregationLevel8_n0;
|
|
||||||
}
|
|
||||||
ss->nrofCandidates->aggregationLevel16 = NR_SearchSpace__nrofCandidates__aggregationLevel16_n0;
|
|
||||||
ss->searchSpaceType = calloc(1,sizeof(*ss->searchSpaceType));
|
ss->searchSpaceType = calloc(1,sizeof(*ss->searchSpaceType));
|
||||||
if (is_common) {
|
if (is_common) {
|
||||||
ss->searchSpaceType->present = NR_SearchSpace__searchSpaceType_PR_common;
|
ss->searchSpaceType->present = NR_SearchSpace__searchSpaceType_PR_common;
|
||||||
@@ -1545,7 +1580,8 @@ static void config_downlinkBWP(NR_BWP_Downlink_t *bwp,
|
|||||||
int dl_antenna_ports,
|
int dl_antenna_ports,
|
||||||
bool force_256qam_off,
|
bool force_256qam_off,
|
||||||
int bwp_loop,
|
int bwp_loop,
|
||||||
bool is_SA)
|
bool is_SA,
|
||||||
|
const int num_agg_level_candidates[NUM_PDCCH_AGG_LEVELS])
|
||||||
{
|
{
|
||||||
bwp->bwp_Common = calloc(1,sizeof(*bwp->bwp_Common));
|
bwp->bwp_Common = calloc(1,sizeof(*bwp->bwp_Common));
|
||||||
|
|
||||||
@@ -1577,8 +1613,12 @@ static void config_downlinkBWP(NR_BWP_Downlink_t *bwp,
|
|||||||
bwp->bwp_Common->pdcch_ConfigCommon->choice.setup->commonSearchSpaceList=NULL;
|
bwp->bwp_Common->pdcch_ConfigCommon->choice.setup->commonSearchSpaceList=NULL;
|
||||||
bwp->bwp_Common->pdcch_ConfigCommon->choice.setup->commonSearchSpaceList=calloc(1,sizeof(*bwp->bwp_Common->pdcch_ConfigCommon->choice.setup->commonSearchSpaceList));
|
bwp->bwp_Common->pdcch_ConfigCommon->choice.setup->commonSearchSpaceList=calloc(1,sizeof(*bwp->bwp_Common->pdcch_ConfigCommon->choice.setup->commonSearchSpaceList));
|
||||||
|
|
||||||
NR_SearchSpace_t *ss = rrc_searchspace_config(true, 5+bwp->bwp_Id, coreset->controlResourceSetId);
|
int searchspaceid = 5 + bwp->bwp_Id;
|
||||||
asn1cSeqAdd(&bwp->bwp_Common->pdcch_ConfigCommon->choice.setup->commonSearchSpaceList->list,ss);
|
int rrc_num_agg_level_candidates[NUM_PDCCH_AGG_LEVELS];
|
||||||
|
int num_cces = get_coreset_num_cces(coreset->frequencyDomainResources.buf, coreset->duration);
|
||||||
|
verify_agg_levels(num_cces, num_agg_level_candidates, coreset->controlResourceSetId, searchspaceid, rrc_num_agg_level_candidates);
|
||||||
|
NR_SearchSpace_t *ss = rrc_searchspace_config(true, searchspaceid, coreset->controlResourceSetId, rrc_num_agg_level_candidates);
|
||||||
|
asn1cSeqAdd(&bwp->bwp_Common->pdcch_ConfigCommon->choice.setup->commonSearchSpaceList->list, ss);
|
||||||
|
|
||||||
bwp->bwp_Common->pdcch_ConfigCommon->choice.setup->searchSpaceSIB1=NULL;
|
bwp->bwp_Common->pdcch_ConfigCommon->choice.setup->searchSpaceSIB1=NULL;
|
||||||
bwp->bwp_Common->pdcch_ConfigCommon->choice.setup->searchSpaceOtherSystemInformation=NULL;
|
bwp->bwp_Common->pdcch_ConfigCommon->choice.setup->searchSpaceOtherSystemInformation=NULL;
|
||||||
@@ -1613,7 +1653,11 @@ static void config_downlinkBWP(NR_BWP_Downlink_t *bwp,
|
|||||||
NR_ControlResourceSet_t *coreset2 = get_coreset_config(bwp->bwp_Id, curr_bwp, ssb_bitmap);
|
NR_ControlResourceSet_t *coreset2 = get_coreset_config(bwp->bwp_Id, curr_bwp, ssb_bitmap);
|
||||||
asn1cSeqAdd(&bwp->bwp_Dedicated->pdcch_Config->choice.setup->controlResourceSetToAddModList->list, coreset2);
|
asn1cSeqAdd(&bwp->bwp_Dedicated->pdcch_Config->choice.setup->controlResourceSetToAddModList->list, coreset2);
|
||||||
|
|
||||||
NR_SearchSpace_t *ss2 = rrc_searchspace_config(false, 10+bwp->bwp_Id, coreset2->controlResourceSetId);
|
searchspaceid = 10 + bwp->bwp_Id;
|
||||||
|
num_cces = get_coreset_num_cces(coreset2->frequencyDomainResources.buf, coreset2->duration);
|
||||||
|
verify_agg_levels(num_cces, num_agg_level_candidates, coreset->controlResourceSetId, searchspaceid, rrc_num_agg_level_candidates);
|
||||||
|
NR_SearchSpace_t *ss2 =
|
||||||
|
rrc_searchspace_config(false, searchspaceid, coreset2->controlResourceSetId, rrc_num_agg_level_candidates);
|
||||||
asn1cSeqAdd(&bwp->bwp_Dedicated->pdcch_Config->choice.setup->searchSpacesToAddModList->list, ss2);
|
asn1cSeqAdd(&bwp->bwp_Dedicated->pdcch_Config->choice.setup->searchSpacesToAddModList->list, ss2);
|
||||||
|
|
||||||
bwp->bwp_Dedicated->pdcch_Config->choice.setup->searchSpacesToReleaseList = NULL;
|
bwp->bwp_Dedicated->pdcch_Config->choice.setup->searchSpacesToReleaseList = NULL;
|
||||||
@@ -3069,7 +3113,15 @@ static NR_SpCellConfig_t *get_initial_SpCellConfig(int uid,
|
|||||||
|
|
||||||
asn1cSeqAdd(&bwp_Dedicated->pdcch_Config->choice.setup->controlResourceSetToAddModList->list, coreset);
|
asn1cSeqAdd(&bwp_Dedicated->pdcch_Config->choice.setup->controlResourceSetToAddModList->list, coreset);
|
||||||
|
|
||||||
NR_SearchSpace_t *ss2 = rrc_searchspace_config(false, 5, coreset->controlResourceSetId);
|
int searchspaceid = 5;
|
||||||
|
int rrc_num_agg_level_candidates[NUM_PDCCH_AGG_LEVELS];
|
||||||
|
int num_cces = get_coreset_num_cces(coreset->frequencyDomainResources.buf, coreset->duration);
|
||||||
|
verify_agg_levels(num_cces,
|
||||||
|
configuration->num_agg_level_candidates,
|
||||||
|
coreset->controlResourceSetId,
|
||||||
|
searchspaceid,
|
||||||
|
rrc_num_agg_level_candidates);
|
||||||
|
NR_SearchSpace_t *ss2 = rrc_searchspace_config(false, searchspaceid, coreset->controlResourceSetId, rrc_num_agg_level_candidates);
|
||||||
asn1cSeqAdd(&bwp_Dedicated->pdcch_Config->choice.setup->searchSpacesToAddModList->list, ss2);
|
asn1cSeqAdd(&bwp_Dedicated->pdcch_Config->choice.setup->searchSpacesToAddModList->list, ss2);
|
||||||
|
|
||||||
bwp_Dedicated->pdsch_Config = config_pdsch(bitmap, 0, pdsch_AntennaPorts);
|
bwp_Dedicated->pdsch_Config = config_pdsch(bitmap, 0, pdsch_AntennaPorts);
|
||||||
@@ -3113,7 +3165,7 @@ static NR_SpCellConfig_t *get_initial_SpCellConfig(int uid,
|
|||||||
calloc(1, sizeof(*SpCellConfig->spCellConfigDedicated->downlinkBWP_ToAddModList));
|
calloc(1, sizeof(*SpCellConfig->spCellConfigDedicated->downlinkBWP_ToAddModList));
|
||||||
for (int bwp_loop = 0; bwp_loop < n_dl_bwp; bwp_loop++) {
|
for (int bwp_loop = 0; bwp_loop < n_dl_bwp; bwp_loop++) {
|
||||||
NR_BWP_Downlink_t *bwp = calloc(1, sizeof(*bwp));
|
NR_BWP_Downlink_t *bwp = calloc(1, sizeof(*bwp));
|
||||||
config_downlinkBWP(bwp, scc, servingcellconfigdedicated, NULL, 0, false, bwp_loop, true);
|
config_downlinkBWP(bwp, scc, servingcellconfigdedicated, NULL, 0, false, bwp_loop, true, configuration->num_agg_level_candidates);
|
||||||
asn1cSeqAdd(&SpCellConfig->spCellConfigDedicated->downlinkBWP_ToAddModList->list, bwp);
|
asn1cSeqAdd(&SpCellConfig->spCellConfigDedicated->downlinkBWP_ToAddModList->list, bwp);
|
||||||
}
|
}
|
||||||
const NR_BWP_Id_t *firstActiveDownlinkBWP_Id = servingcellconfigdedicated->firstActiveDownlinkBWP_Id;
|
const NR_BWP_Id_t *firstActiveDownlinkBWP_Id = servingcellconfigdedicated->firstActiveDownlinkBWP_Id;
|
||||||
@@ -3575,7 +3627,8 @@ NR_CellGroupConfig_t *get_default_secondaryCellGroup(const NR_ServingCellConfigC
|
|||||||
dl_antenna_ports,
|
dl_antenna_ports,
|
||||||
configuration->force_256qam_off,
|
configuration->force_256qam_off,
|
||||||
bwp_loop,
|
bwp_loop,
|
||||||
false);
|
false,
|
||||||
|
configuration->num_agg_level_candidates);
|
||||||
asn1cSeqAdd(&secondaryCellGroup->spCellConfig->spCellConfigDedicated->downlinkBWP_ToAddModList->list, bwp);
|
asn1cSeqAdd(&secondaryCellGroup->spCellConfig->spCellConfigDedicated->downlinkBWP_ToAddModList->list, bwp);
|
||||||
}
|
}
|
||||||
secondaryCellGroup->spCellConfig->spCellConfigDedicated->firstActiveDownlinkBWP_Id =
|
secondaryCellGroup->spCellConfig->spCellConfigDedicated->firstActiveDownlinkBWP_Id =
|
||||||
|
|||||||
@@ -55,7 +55,10 @@ void nr_rrc_config_dl_tda(struct NR_PDSCH_TimeDomainResourceAllocationList *pdsc
|
|||||||
NR_TDD_UL_DL_ConfigCommon_t *tdd_UL_DL_ConfigurationCommon,
|
NR_TDD_UL_DL_ConfigCommon_t *tdd_UL_DL_ConfigurationCommon,
|
||||||
int curr_bwp);
|
int curr_bwp);
|
||||||
void nr_rrc_config_ul_tda(NR_ServingCellConfigCommon_t *scc, int min_fb_delay);
|
void nr_rrc_config_ul_tda(NR_ServingCellConfigCommon_t *scc, int min_fb_delay);
|
||||||
NR_SearchSpace_t *rrc_searchspace_config(bool is_common, int searchspaceid, int coresetid);
|
NR_SearchSpace_t *rrc_searchspace_config(bool is_common,
|
||||||
|
int searchspaceid,
|
||||||
|
int coresetid,
|
||||||
|
const int num_agg_level_candidates[NUM_PDCCH_AGG_LEVELS]);
|
||||||
|
|
||||||
void prepare_sim_uecap(NR_UE_NR_Capability_t *cap,
|
void prepare_sim_uecap(NR_UE_NR_Capability_t *cap,
|
||||||
NR_ServingCellConfigCommon_t *scc,
|
NR_ServingCellConfigCommon_t *scc,
|
||||||
|
|||||||
@@ -20,6 +20,7 @@ gNBs =
|
|||||||
do_CSIRS = 1;
|
do_CSIRS = 1;
|
||||||
do_SRS = 1;
|
do_SRS = 1;
|
||||||
|
|
||||||
|
#uess_agg_levels = [0,1,2,2,1]
|
||||||
servingCellConfigCommon = (
|
servingCellConfigCommon = (
|
||||||
{
|
{
|
||||||
#spCellConfigCommon
|
#spCellConfigCommon
|
||||||
|
|||||||
@@ -19,6 +19,7 @@ gNBs:
|
|||||||
# Physical parameters:
|
# Physical parameters:
|
||||||
do_CSIRS: 1
|
do_CSIRS: 1
|
||||||
do_SRS: 1
|
do_SRS: 1
|
||||||
|
#uess_agg_levels: [0,1,1,1,1]
|
||||||
servingCellConfigCommon:
|
servingCellConfigCommon:
|
||||||
#spCellConfigCommon
|
#spCellConfigCommon
|
||||||
- physCellId: 0
|
- physCellId: 0
|
||||||
|
|||||||
Reference in New Issue
Block a user