From 7d37143bac46034430d7e5ba7fc3336c5426d067 Mon Sep 17 00:00:00 2001 From: Robert Schmidt Date: Thu, 28 Sep 2023 20:02:20 +0200 Subject: [PATCH] Read and forward NSSAI in E1AP Setup Request --- openair2/COMMON/e1ap_messages_types.h | 7 ++++- openair2/E1AP/e1ap.c | 44 +++++++++++++++++++++++---- openair2/E1AP/e1ap_asnc.h | 2 ++ openair2/E1AP/e1ap_setup.c | 20 ++++++++++-- openair2/RRC/NR/rrc_gNB_cuup.c | 2 +- 5 files changed, 64 insertions(+), 11 deletions(-) diff --git a/openair2/COMMON/e1ap_messages_types.h b/openair2/COMMON/e1ap_messages_types.h index 11a27635d5..67f5a883e2 100644 --- a/openair2/COMMON/e1ap_messages_types.h +++ b/openair2/COMMON/e1ap_messages_types.h @@ -32,6 +32,7 @@ #define E1AP_MAX_NUM_TRANSAC_IDS 4 #define E1AP_MAX_NUM_PLMNS 4 +#define E1AP_MAX_NUM_SLICES 1024 #define E1AP_MAX_NUM_CELL_GROUPS 4 #define E1AP_MAX_NUM_QOS_FLOWS 4 #define E1AP_MAX_NUM_NGRAN_DRB 4 @@ -76,7 +77,11 @@ typedef struct e1ap_setup_req_s { char * gNB_cu_up_name; uint64_t transac_id; int supported_plmns; - PLMN_ID_t plmns[E1AP_MAX_NUM_PLMNS]; + struct { + PLMN_ID_t id; + int supported_slices; + e1ap_nssai_t *slice; + } plmn[E1AP_MAX_NUM_PLMNS]; } e1ap_setup_req_t; typedef struct e1ap_register_req_t { diff --git a/openair2/E1AP/e1ap.c b/openair2/E1AP/e1ap.c index e7503874a3..690810bbe8 100644 --- a/openair2/E1AP/e1ap.c +++ b/openair2/E1AP/e1ap.c @@ -198,7 +198,24 @@ static void fill_SETUP_REQUEST(e1ap_setup_req_t *setup, E1AP_E1AP_PDU_t *pdu) for (int i=0; i < numSupportedPLMNs; i++) { asn1cSequenceAdd(ieC5->value.choice.SupportedPLMNs_List.list, E1AP_SupportedPLMNs_Item_t, supportedPLMN); /* 5.1 PLMN Identity */ - MCC_MNC_TO_PLMNID(setup->plmns[i].mcc, setup->plmns[i].mnc, setup->plmns[i].mnc_digit_length, &supportedPLMN->pLMN_Identity); + PLMN_ID_t *id = &setup->plmn[i].id; + MCC_MNC_TO_PLMNID(id->mcc, id->mnc, id->mnc_digit_length, &supportedPLMN->pLMN_Identity); + + int n = setup->plmn[i].supported_slices; + if (setup->plmn[i].slice != NULL && n > 0) { + supportedPLMN->slice_Support_List = calloc(1, sizeof(*supportedPLMN->slice_Support_List)); + AssertFatal(supportedPLMN->slice_Support_List != NULL, "out of memory\n"); + for (int s = 0; s < n; ++s) { + asn1cSequenceAdd(supportedPLMN->slice_Support_List->list, E1AP_Slice_Support_Item_t, slice); + e1ap_nssai_t *nssai = &setup->plmn[i].slice[s]; + INT8_TO_OCTET_STRING(nssai->sst, &slice->sNSSAI.sST); + if (nssai->sd != 0xffffff) { + slice->sNSSAI.sD = malloc(sizeof(*slice->sNSSAI.sD)); + AssertFatal(slice->sNSSAI.sD != NULL, "out of memory\n"); + INT24_TO_OCTET_STRING(nssai->sd, slice->sNSSAI.sD); + } + } + } } } @@ -294,11 +311,26 @@ void extract_SETUP_REQUEST(const E1AP_E1AP_PDU_t *pdu, E1AP_SupportedPLMNs_Item_t *supported_plmn_item = (E1AP_SupportedPLMNs_Item_t *)(ie->value.choice.SupportedPLMNs_List.list.array[i]); /* PLMN Identity */ - PLMNID_TO_MCC_MNC(&supported_plmn_item->pLMN_Identity, - req->plmns[i].mcc, - req->plmns[i].mnc, - req->plmns[i].mnc_digit_length); - LOG_D(E1AP, "MCC: %d\nMNC: %d\n", req->plmns[i].mcc, req->plmns[i].mnc); + PLMN_ID_t *id = &req->plmn[i].id; + PLMNID_TO_MCC_MNC(&supported_plmn_item->pLMN_Identity, id->mcc, id->mnc, id->mnc_digit_length); + LOG_D(E1AP, "MCC %d MNC %d\n", id->mcc, id->mnc); + + /* NSSAI */ + if (supported_plmn_item->slice_Support_List) { + int n = supported_plmn_item->slice_Support_List->list.count; + req->plmn[i].supported_slices = n; + req->plmn[i].slice = calloc(n, sizeof(*req->plmn[i].slice)); + AssertFatal(req->plmn[i].slice != NULL, "out of memory\n"); + for (int s = 0; s < n; ++s) { + e1ap_nssai_t *slice = &req->plmn[i].slice[s]; + const E1AP_SNSSAI_t *es = &supported_plmn_item->slice_Support_List->list.array[s]->sNSSAI; + OCTET_STRING_TO_INT8(&es->sST, slice->sst); + slice->sd = 0xffffff; + if (es->sD != NULL) + OCTET_STRING_TO_INT24(es->sD, slice->sd); + LOG_D(E1AP, "SST %d SD %06x\n", slice->sst, slice->sd); + } + } } } diff --git a/openair2/E1AP/e1ap_asnc.h b/openair2/E1AP/e1ap_asnc.h index 00dbcc13f3..3916f4aeb7 100644 --- a/openair2/E1AP/e1ap_asnc.h +++ b/openair2/E1AP/e1ap_asnc.h @@ -61,5 +61,7 @@ #include #include #include +#include +#include #endif diff --git a/openair2/E1AP/e1ap_setup.c b/openair2/E1AP/e1ap_setup.c index 97a3bcb627..97a8b93700 100644 --- a/openair2/E1AP/e1ap_setup.c +++ b/openair2/E1AP/e1ap_setup.c @@ -102,10 +102,24 @@ MessageDef *RCconfig_NR_CU_E1(bool separate_CUUP_process) e1Setup->supported_plmns = numPLMNs; for (int I = 0; I < numPLMNs; I++) { - e1Setup->plmns[I].mcc = *PLMNParamList.paramarray[I][GNB_MOBILE_COUNTRY_CODE_IDX].uptr; - e1Setup->plmns[I].mnc = *PLMNParamList.paramarray[I][GNB_MOBILE_NETWORK_CODE_IDX].uptr; + e1Setup->plmn[I].id.mcc = *PLMNParamList.paramarray[I][GNB_MOBILE_COUNTRY_CODE_IDX].uptr; + e1Setup->plmn[I].id.mnc = *PLMNParamList.paramarray[I][GNB_MOBILE_NETWORK_CODE_IDX].uptr; + e1Setup->plmn[I].id.mnc_digit_length = *PLMNParamList.paramarray[I][GNB_MNC_DIGIT_LENGTH].uptr; + + char snssaistr[MAX_OPTNAME_SIZE*2 + 8]; + sprintf(snssaistr, "%s.[%i].%s.[%i]", GNB_CONFIG_STRING_GNB_LIST, 0, GNB_CONFIG_STRING_PLMN_LIST, I); + paramlist_def_t SNSSAIParamList = {GNB_CONFIG_STRING_SNSSAI_LIST, NULL, 0}; + paramdef_t SNSSAIParams[] = GNBSNSSAIPARAMS_DESC; + config_getlist(&SNSSAIParamList, SNSSAIParams, sizeof(SNSSAIParams)/sizeof(paramdef_t), snssaistr); + e1Setup->plmn[I].supported_slices = SNSSAIParamList.numelt; + e1Setup->plmn[I].slice = calloc(SNSSAIParamList.numelt, sizeof(*e1Setup->plmn[I].slice)); + AssertFatal(e1Setup->plmn[I].slice != NULL, "out of memory\n"); + for (int s = 0; s < SNSSAIParamList.numelt; ++s) { + e1ap_nssai_t *slice = &e1Setup->plmn[I].slice[s]; + slice->sst = *SNSSAIParamList.paramarray[s][GNB_SLICE_SERVICE_TYPE_IDX].uptr; + slice->sd = *SNSSAIParamList.paramarray[s][GNB_SLICE_DIFFERENTIATOR_IDX].uptr; + } } - /* TODO add NSSAIs */ e1ap_net_config_t *e1ap_nc = &E1AP_REGISTER_REQ(msgConfig).net_config; e1ap_nc->remotePortF1U = *(GNBParamList.paramarray[0][GNB_REMOTE_S_PORTD_IDX].uptr); diff --git a/openair2/RRC/NR/rrc_gNB_cuup.c b/openair2/RRC/NR/rrc_gNB_cuup.c index ace4a5f62d..56ee7d59ca 100644 --- a/openair2/RRC/NR/rrc_gNB_cuup.c +++ b/openair2/RRC/NR/rrc_gNB_cuup.c @@ -30,7 +30,7 @@ int rrc_gNB_process_e1_setup_req(e1ap_setup_req_t *req) for (int i = 0; i < req->supported_plmns; i++) { - PLMN_ID_t *id = &req->plmns[i]; + PLMN_ID_t *id = &req->plmn[i].id; if (rrc->configuration.mcc[i] != id->mcc || rrc->configuration.mnc[i] != id->mnc) { LOG_E(NR_RRC, "PLMNs received from CUUP (mcc:%d, mnc:%d) did not match with PLMNs in RRC (mcc:%d, mnc:%d)\n",