Send MeasConfig to DU, Receive MeasGapConfig from DU

This commit is contained in:
rmagueta
2025-07-15 16:55:36 +02:00
committed by Robert Schmidt
parent 5e0307d845
commit d5b9f81285
3 changed files with 64 additions and 15 deletions
+14
View File
@@ -1152,3 +1152,17 @@ int do_NR_HandoverPreparationInformation(const uint8_t *uecap_buf, int uecap_buf
ASN_STRUCT_FREE(asn_DEF_NR_HandoverPreparationInformation, hpi); ASN_STRUCT_FREE(asn_DEF_NR_HandoverPreparationInformation, hpi);
return (enc_rval.encoded + 7) / 8; return (enc_rval.encoded + 7) / 8;
} }
int do_NR_MeasConfig(const NR_MeasConfig_t *measconfig, uint8_t *buf, int buf_size)
{
asn_enc_rval_t enc_rval = uper_encode_to_buffer(&asn_DEF_NR_MeasConfig, NULL, measconfig, buf, buf_size);
AssertFatal(enc_rval.encoded > 0, "ASN1 message encoding failed (%s, %lu)!\n", enc_rval.failed_type->name, enc_rval.encoded);
return (enc_rval.encoded + 7) / 8;
}
int do_NR_MeasurementTimingConfiguration(const NR_MeasurementTimingConfiguration_t *mtc, uint8_t *buf, int buf_size)
{
asn_enc_rval_t enc_rval = uper_encode_to_buffer(&asn_DEF_NR_MeasurementTimingConfiguration, NULL, mtc, buf, buf_size);
AssertFatal(enc_rval.encoded > 0, "ASN1 message encoding failed (%s, %lu)!\n", enc_rval.failed_type->name, enc_rval.encoded);
return (enc_rval.encoded + 7) / 8;
}
+5
View File
@@ -50,6 +50,7 @@
#include "NR_ReestablishmentCause.h" #include "NR_ReestablishmentCause.h"
#include "NR_SRB-ToAddModList.h" #include "NR_SRB-ToAddModList.h"
#include "NR_SecurityConfig.h" #include "NR_SecurityConfig.h"
#include "NR_MeasurementTimingConfiguration.h"
#include "ds/seq_arr.h" #include "ds/seq_arr.h"
#include "ds/byte_array.h" #include "ds/byte_array.h"
#include "rrc_messages_types.h" #include "rrc_messages_types.h"
@@ -120,6 +121,10 @@ int do_RRCSetupComplete(uint8_t *buffer,
int do_NR_HandoverPreparationInformation(const uint8_t *uecap_buf, int uecap_buf_size, uint8_t *buf, int buf_size); int do_NR_HandoverPreparationInformation(const uint8_t *uecap_buf, int uecap_buf_size, uint8_t *buf, int buf_size);
int do_NR_MeasConfig(const NR_MeasConfig_t *measconfig, uint8_t *buf, int buf_size);
int do_NR_MeasurementTimingConfiguration(const NR_MeasurementTimingConfiguration_t *mtc, uint8_t *buf, int buf_size);
int do_RRCSetupRequest(uint8_t *buffer, size_t buffer_size, uint8_t *rv, uint64_t fiveG_S_TMSI_part1); int do_RRCSetupRequest(uint8_t *buffer, size_t buffer_size, uint8_t *rv, uint64_t fiveG_S_TMSI_part1);
int do_NR_RRCReconfigurationComplete_for_nsa(uint8_t *buffer, size_t buffer_size, NR_RRC_TransactionIdentifier_t Transaction_id); int do_NR_RRCReconfigurationComplete_for_nsa(uint8_t *buffer, size_t buffer_size, NR_RRC_TransactionIdentifier_t Transaction_id);
+45 -15
View File
@@ -557,14 +557,11 @@ void free_RRCReconfiguration_params(nr_rrc_reconfig_param_t params)
FREE_AND_ZERO_BYTE_ARRAY(params.dedicated_NAS_msg_list[i]); FREE_AND_ZERO_BYTE_ARRAY(params.dedicated_NAS_msg_list[i]);
} }
/** @brief Prepare the instance of RRCReconfigurationParams to be pass to RRC encoding */ static NR_MeasConfig_t *nr_rrc_get_measconfig(const gNB_RRC_INST *rrc, const gNB_RRC_UE_t *UE)
nr_rrc_reconfig_param_t get_RRCReconfiguration_params(gNB_RRC_INST *rrc, gNB_RRC_UE_t *UE, uint8_t srb_reest_bitmap, bool drb_reestablish)
{ {
uint8_t xid = rrc_gNB_get_next_transaction_identifier(rrc->module_id); nr_rrc_du_container_t *du = get_du_for_ue((gNB_RRC_INST *)rrc, UE->rrc_ue_id);
nr_rrc_du_container_t *du = get_du_for_ue(rrc, UE->rrc_ue_id);
DevAssert(du != NULL); DevAssert(du != NULL);
f1ap_served_cell_info_t *cell_info = &du->setup_req->cell[0].info; f1ap_served_cell_info_t *cell_info = &du->setup_req->cell[0].info;
NR_MeasConfig_t *measconfig = NULL;
NR_ReportConfigToAddMod_t *rc_PER = NULL; NR_ReportConfigToAddMod_t *rc_PER = NULL;
NR_ReportConfigToAddMod_t *rc_A2 = NULL; NR_ReportConfigToAddMod_t *rc_A2 = NULL;
seq_arr_t *rc_A3_seq = NULL; seq_arr_t *rc_A3_seq = NULL;
@@ -578,9 +575,7 @@ nr_rrc_reconfig_param_t get_RRCReconfiguration_params(gNB_RRC_INST *rrc, gNB_RRC
if (neighbour_config) if (neighbour_config)
neighbour_cells = neighbour_config->neighbour_cells; neighbour_cells = neighbour_config->neighbour_cells;
if (neighbour_cells if (neighbour_cells && rrc->measurementConfiguration.a3_event_list && rrc->measurementConfiguration.a3_event_list->size > 0) {
&& rrc->measurementConfiguration.a3_event_list
&& rrc->measurementConfiguration.a3_event_list->size > 0) {
/* Loop through neighbours and find related A3 configuration /* Loop through neighbours and find related A3 configuration
If no related A3 but there is default add the default one. If no related A3 but there is default add the default one.
If default one added once as a report, no need to add it again && duplication. If default one added once as a report, no need to add it again && duplication.
@@ -591,7 +586,7 @@ nr_rrc_reconfig_param_t get_RRCReconfiguration_params(gNB_RRC_INST *rrc, gNB_RRC
bool is_default_a3_added = false; bool is_default_a3_added = false;
for (int i = 0; i < neighbour_cells->size; i++) { for (int i = 0; i < neighbour_cells->size; i++) {
nr_neighbour_cell_t *neighbourCell = (nr_neighbour_cell_t *)seq_arr_at(neighbour_cells, i); nr_neighbour_cell_t *neighbourCell = (nr_neighbour_cell_t *)seq_arr_at(neighbour_cells, i);
const nr_a3_event_t *a3Event = get_a3_configuration(rrc, neighbourCell->physicalCellId); const nr_a3_event_t *a3Event = get_a3_configuration((gNB_RRC_INST *)rrc, neighbourCell->physicalCellId);
if (!a3Event || is_default_a3_added) if (!a3Event || is_default_a3_added)
continue; continue;
if (a3Event->pci == -1) if (a3Event->pci == -1)
@@ -603,14 +598,15 @@ nr_rrc_reconfig_param_t get_RRCReconfiguration_params(gNB_RRC_INST *rrc, gNB_RRC
rc_PER = prepare_periodic_event_report(rrc->measurementConfiguration.per_event); rc_PER = prepare_periodic_event_report(rrc->measurementConfiguration.per_event);
if (rrc->measurementConfiguration.a2_event) if (rrc->measurementConfiguration.a2_event)
rc_A2 = prepare_a2_event_report(rrc->measurementConfiguration.a2_event); rc_A2 = prepare_a2_event_report(rrc->measurementConfiguration.a2_event);
return get_MeasConfig(mt, band, scs, rc_PER, rc_A2, rc_A3_seq, neighbour_cells);
measconfig = get_MeasConfig(mt, band, scs, rc_PER, rc_A2, rc_A3_seq, neighbour_cells);
} }
return NULL;
}
if (UE->measConfig) /** @brief Prepare the instance of RRCReconfigurationParams to be pass to RRC encoding */
free_MeasConfig(UE->measConfig); nr_rrc_reconfig_param_t get_RRCReconfiguration_params(gNB_RRC_INST *rrc, gNB_RRC_UE_t *UE, uint8_t srb_reest_bitmap, bool drb_reestablish)
{
UE->measConfig = measconfig; uint8_t xid = rrc_gNB_get_next_transaction_identifier(rrc->module_id);
// Re-establish PDCP for SRB2 only // Re-establish PDCP for SRB2 only
NR_SRB_ToAddModList_t *SRBs = createSRBlist(UE, srb_reest_bitmap); NR_SRB_ToAddModList_t *SRBs = createSRBlist(UE, srb_reest_bitmap);
@@ -1155,6 +1151,7 @@ static void rrc_handle_RRCSetupRequest(gNB_RRC_INST *rrc,
UE->nr_cellid = msg->nr_cellid; UE->nr_cellid = msg->nr_cellid;
UE->masterCellGroup = cellGroupConfig; UE->masterCellGroup = cellGroupConfig;
UE->ongoing_reconfiguration = false; UE->ongoing_reconfiguration = false;
UE->measConfig = nr_rrc_get_measconfig(rrc, UE);
activate_srb(UE, 1); activate_srb(UE, 1);
rrc_gNB_generate_RRCSetup(0, msg->crnti, ue_context_p, msg->du2cu_rrc_container, msg->du2cu_rrc_container_length); rrc_gNB_generate_RRCSetup(0, msg->crnti, ue_context_p, msg->du2cu_rrc_container, msg->du2cu_rrc_container_length);
} }
@@ -2091,6 +2088,17 @@ static void rrc_CU_process_ue_context_setup_response(MessageDef *msg_p, instance
uper_decode_complete(NULL, &asn_DEF_NR_CellGroupConfig, (void **)&cellGroupConfig, (uint8_t *)cgc->buf, cgc->len); uper_decode_complete(NULL, &asn_DEF_NR_CellGroupConfig, (void **)&cellGroupConfig, (uint8_t *)cgc->buf, cgc->len);
AssertFatal(dec_rval.code == RC_OK && dec_rval.consumed > 0, "Cell group config decode error\n"); AssertFatal(dec_rval.code == RC_OK && dec_rval.consumed > 0, "Cell group config decode error\n");
if (resp->du_to_cu_rrc_info.meas_gap_config) {
NR_MeasGapConfig_t *measGapConfig = NULL;
asn_dec_rval_t dec_rval_mgc = uper_decode_complete(NULL,
&asn_DEF_NR_MeasGapConfig,
(void **)&measGapConfig,
(uint8_t *)resp->du_to_cu_rrc_info.meas_gap_config->buf,
resp->du_to_cu_rrc_info.meas_gap_config->len);
AssertFatal(dec_rval_mgc.code == RC_OK && dec_rval_mgc.consumed > 0, "measGapConfig decode error\n");
UE->measConfig->measGapConfig = measGapConfig;
}
if (UE->masterCellGroup) { if (UE->masterCellGroup) {
ASN_STRUCT_FREE(asn_DEF_NR_CellGroupConfig, UE->masterCellGroup); ASN_STRUCT_FREE(asn_DEF_NR_CellGroupConfig, UE->masterCellGroup);
LOG_I(RRC, "UE %04x replacing existing CellGroupConfig with new one received from DU\n", UE->rnti); LOG_I(RRC, "UE %04x replacing existing CellGroupConfig with new one received from DU\n", UE->rnti);
@@ -3039,6 +3047,28 @@ void rrc_gNB_generate_UeContextSetupRequest(const gNB_RRC_INST *rrc,
*cu2du.ue_cap = copy_byte_array(ue_p->ue_cap_buffer); *cu2du.ue_cap = copy_byte_array(ue_p->ue_cap_buffer);
} }
nr_rrc_du_container_t *du = get_du_for_ue((gNB_RRC_INST *)rrc, ue_p->rrc_ue_id);
byte_array_t *meas_timing_config = NULL;
if (du->mtc && ue_p->measConfig && ue_p->measConfig->measObjectToAddModList) {
NR_MeasObjectToAddModList_t *mo_list = ue_p->measConfig->measObjectToAddModList;
NR_ARFCN_ValueNR_t ssbFrequency0;
for (int i = 0; i < mo_list->list.count; i++) {
NR_MeasObjectToAddMod_t *mo = mo_list->list.array[i];
if (mo->measObject.present == NR_MeasObjectToAddMod__measObject_PR_measObjectNR) {
NR_MeasObjectNR_t *monr = mo->measObject.choice.measObjectNR;
if (i == 0) {
ssbFrequency0 = *monr->ssbFrequency;
} else if (ssbFrequency0 != *monr->ssbFrequency) {
meas_timing_config = calloc_or_fail(1, sizeof(*meas_timing_config));
meas_timing_config->buf = calloc_or_fail(1, NR_RRC_BUF_SIZE);
meas_timing_config->len = do_NR_MeasurementTimingConfiguration(du->mtc, meas_timing_config->buf, NR_RRC_BUF_SIZE);
cu2du.meas_timing_config = meas_timing_config;
break;
}
}
}
}
int nb_srb = 1; int nb_srb = 1;
f1ap_srb_to_setup_t *srbs = calloc_or_fail(nb_srb, sizeof(*srbs)); f1ap_srb_to_setup_t *srbs = calloc_or_fail(nb_srb, sizeof(*srbs));
srbs[0].id = 2; srbs[0].id = 2;