From 27e01e081b9fd557e37b163a2d7fd5f70beb0450 Mon Sep 17 00:00:00 2001 From: Robert Schmidt Date: Mon, 17 Nov 2025 01:09:10 +0100 Subject: [PATCH] Read PDU session configuration and request Use the new PDU session configuration functionality of the parent commit. It is now possible to request multiple PDU sessions, and to request specific PDU session types. While the new uicc0.pdu_sessions is preferred, it is still possible to use the "legacy" uicc0.dnn/nssai_sst/nssai_sd. The old parameters --default-pdu-id and --extra-pdu-id are not allowed anymore, as it is possible to manually define this in the UE configuration. Correspondingly, fix the use of those options, where applicable. Note: since the default_pdu_id is changed to -1, all interface names will have pX to interface names appended (oaitun_ue1pX). The next commit will correct this. --- ci-scripts/conf_files/nrue.uicc.2pdu.conf | 11 ++++++ .../docker-compose.yaml | 4 +-- common/utils/telnetsrv/telnetsrv_ciUE.c | 5 +-- executables/nr-uesoftmodem.c | 6 ++-- executables/softmodem-common.c | 4 +++ executables/softmodem-common.h | 2 +- openair3/NAS/NR_UE/nr_nas_msg.c | 31 +++++++++------- openair3/NAS/NR_UE/nr_nas_msg.h | 2 +- openair3/UICC/pdu_session.c | 4 +-- openair3/UICC/pdu_session.h | 2 +- openair3/UICC/usim_interface.c | 36 ++++++++++++++++--- openair3/UICC/usim_interface.h | 3 ++ 12 files changed, 80 insertions(+), 30 deletions(-) create mode 100644 ci-scripts/conf_files/nrue.uicc.2pdu.conf diff --git a/ci-scripts/conf_files/nrue.uicc.2pdu.conf b/ci-scripts/conf_files/nrue.uicc.2pdu.conf new file mode 100644 index 0000000000..03f64f47fc --- /dev/null +++ b/ci-scripts/conf_files/nrue.uicc.2pdu.conf @@ -0,0 +1,11 @@ +uicc0 = { + imsi = "208990100001100"; + key = "fec86ba6eb707ed08905757b1bb44b8f"; + opc= "C42449363BBAD02B66D16BC975D77CC1"; + pdu_sessions = ( + { id = 1; dnn = "oai"; nssai_sst = 1; }, + { id = 2; dnn = "oai"; nssai_sst = 1; } + ) +} + +thread-pool = "-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1" diff --git a/ci-scripts/yaml_files/5g_rfsimulator_u0_25prb/docker-compose.yaml b/ci-scripts/yaml_files/5g_rfsimulator_u0_25prb/docker-compose.yaml index c4a4e2ebea..ebb006213d 100644 --- a/ci-scripts/yaml_files/5g_rfsimulator_u0_25prb/docker-compose.yaml +++ b/ci-scripts/yaml_files/5g_rfsimulator_u0_25prb/docker-compose.yaml @@ -149,7 +149,7 @@ services: - NET_RAW # for ping environment: USE_ADDITIONAL_OPTIONS: --rfsim -r 25 --numerology 0 --uicc0.imsi 208990100001100 --band 66 -C 2152680000 --CO -400000000 --ssb 48 - --rfsimulator.serveraddr 192.168.71.141 --extra-pdu-id 2 --log_config.global_log_options level,nocolor,time + --rfsimulator.serveraddr 192.168.71.141 --log_config.global_log_options level,nocolor,time --telnetsrv --telnetsrv.shrmod ciUE --telnetsrv.listenaddr 192.168.71.150 --telnetsrv.listenport 8091 ASAN_OPTIONS: detect_leaks=0:detect_odr_violation=0 depends_on: @@ -160,7 +160,7 @@ services: devices: - /dev/net/tun:/dev/net/tun volumes: - - ../../conf_files/nrue.uicc.conf:/opt/oai-nr-ue/etc/nr-ue.conf + - ../../conf_files/nrue.uicc.2pdu.conf:/opt/oai-nr-ue/etc/nr-ue.conf healthcheck: test: /bin/bash -c "pgrep nr-uesoftmodem" start_period: 10s diff --git a/common/utils/telnetsrv/telnetsrv_ciUE.c b/common/utils/telnetsrv/telnetsrv_ciUE.c index 81451796e0..457ba77b4b 100644 --- a/common/utils/telnetsrv/telnetsrv_ciUE.c +++ b/common/utils/telnetsrv/telnetsrv_ciUE.c @@ -174,8 +174,9 @@ static int add_pdu_session(char *buf, int debug, telnet_printfunc_t prnt) DevAssert(nas->uicc); nssai_t nssai = {nas->uicc->nssai_sst, nas->uicc->nssai_sd}; - const char *dnn = nas->uicc->dnnStr; - request_pdusession(nas, pdusession_id, 1 /* = PDU_SESSION_TYPE_IPV4 */, nssai, dnn); + pdu_session_config_t c = {pdusession_id, 1 /* = PDU_SESSION_TYPE_IPV4 */, nssai, nas->uicc->dnnStr}; + nas->uicc->pdu_sessions[nas->uicc->n_pdu_sessions++] = c; + request_pdusession(nas, &c); prnt("Triggered PDU session request for UE %d with ID %d\n", ue_id, pdusession_id); return 0; } diff --git a/executables/nr-uesoftmodem.c b/executables/nr-uesoftmodem.c index f1cc659cae..0d3c4053b2 100644 --- a/executables/nr-uesoftmodem.c +++ b/executables/nr-uesoftmodem.c @@ -181,10 +181,8 @@ static void get_options(configmodule_interface_t *cfg) config_get(cfg, cmdline_params, numparams, NULL); if (nrUE_params.vcdflag > 0) ouput_vcd = 1; - AssertFatal(nrUE_params.extra_pdu_id != get_softmodem_params()->default_pdu_session_id, - "Default PDU ID (%d) and Extra PDU ID (%d) must be different!\n", - get_softmodem_params()->default_pdu_session_id, - nrUE_params.extra_pdu_id); + AssertFatal(nrUE_params.extra_pdu_id == -1, + "Add additional PDU sessions in uicc.pdu_sessions array instead\n"); } // set PHY vars from command line diff --git a/executables/softmodem-common.c b/executables/softmodem-common.c index 09fced4aa3..558fd4968b 100644 --- a/executables/softmodem-common.c +++ b/executables/softmodem-common.c @@ -156,6 +156,10 @@ void get_common_options(configmodule_interface_t *cfg) nfapi_setmode(nfapi_mode); if (stats_disabled) IS_SOFTMODEM_NOSTATS = true; + + // To be removed in a future release (after 1 month) + AssertFatal(get_softmodem_params()->default_pdu_session_id == -1, + "Use uicc0.pdu_sessions.[0].id to change the requested PDU session ID (is %d)\n", get_softmodem_params()->default_pdu_session_id); } void softmodem_verify_mode(const softmodem_params_t *p) diff --git a/executables/softmodem-common.h b/executables/softmodem-common.h index 4dfa5eb680..cf5c6ad553 100644 --- a/executables/softmodem-common.h +++ b/executables/softmodem-common.h @@ -180,7 +180,7 @@ extern int usrp_tx_thread; {"E" , CONFIG_HLP_TQFS, PARAMFLAG_BOOL, .iptr=&softmodem_params.threequarter_fs, .defintval=0, TYPE_INT, 0}, \ {"imscope" , CONFIG_HLP_IMSCOPE, PARAMFLAG_BOOL, .uptr=&enable_imscope, .defintval=0, TYPE_UINT, 0}, \ {"imscope-record" , CONFIG_HLP_IMSCOPE_RECORD,PARAMFLAG_BOOL, .uptr=&enable_imscope_record, .defintval=0, TYPE_UINT, 0}, \ - {"default-pdu-id", NULL, 0, .iptr=&DEFAULT_PDU_ID, .defintval=10, TYPE_INT, 0}, \ + {"default-pdu-id", NULL, 0, .iptr=&DEFAULT_PDU_ID, .defintval=-1, TYPE_INT, 0}, \ } // clang-format on diff --git a/openair3/NAS/NR_UE/nr_nas_msg.c b/openair3/NAS/NR_UE/nr_nas_msg.c index f839ff4be6..59472df32a 100644 --- a/openair3/NAS/NR_UE/nr_nas_msg.c +++ b/openair3/NAS/NR_UE/nr_nas_msg.c @@ -1773,8 +1773,9 @@ static void send_nas_5gmm_ind(instance_t instance, const Guti5GSMobileIdentity_t itti_send_msg_to_task(TASK_RRC_NRUE, instance, msg); } -void request_pdusession(nr_ue_nas_t *nas, int pdusession_id, int t, nssai_t nssai, const char *dnn) +void request_pdusession(nr_ue_nas_t *nas, const pdu_session_config_t *pdu) { + int t = pdu->type; AssertFatal(t == PDU_SESSION_TYPE_IPV4 || t == PDU_SESSION_TYPE_IPV6 || t == PDU_SESSION_TYPE_IPV4V6 || t == PDU_SESSION_TYPE_UNSTRUCT || t == PDU_SESSION_TYPE_ETHER, "illegal PDU session type %d\n", @@ -1782,12 +1783,12 @@ void request_pdusession(nr_ue_nas_t *nas, int pdusession_id, int t, nssai_t nssa AssertFatal(t != PDU_SESSION_TYPE_UNSTRUCT, "unstructured PDU sessions not handled yet\n"); MessageDef *message_p = itti_alloc_new_message(TASK_NAS_NRUE, nas->UE_id, NAS_PDU_SESSION_REQ); nas_pdu_session_req_t *pdu_req = &NAS_PDU_SESSION_REQ(message_p); - pdu_req->pdusession_id = pdusession_id; + pdu_req->pdusession_id = pdu->id; // 24.501: joint PDU session type IEI (0x9-, Table 8.3.1.1.1) and type (9.11.4.11) pdu_req->pdusession_type = 0x90 | t; - pdu_req->sst = nssai.sst; - pdu_req->sd = nssai.sd; - snprintf(pdu_req->dnn, sizeof(pdu_req->dnn), "%s", dnn); + pdu_req->sst = pdu->nssai.sst; + pdu_req->sd = pdu->nssai.sd; + snprintf(pdu_req->dnn, sizeof(pdu_req->dnn), "%s", pdu->dnn); itti_send_msg_to_task(TASK_NAS_NRUE, nas->UE_id, message_p); } @@ -1873,14 +1874,18 @@ static void handle_registration_accept(nr_ue_nas_t *nas, const uint8_t *pdu_buff send_nas_uplink_data_req(nas, &initialNasMsg); LOG_I(NAS, "Send NAS_UPLINK_DATA_REQ message(RegistrationComplete)\n"); } - nssai_t ch_nssai = {nas->uicc->nssai_sst, nas->uicc->nssai_sd}; - if (get_user_nssai_idx(ch_nssai, msg.nas_allowed_nssai) < 0) { - LOG_E(NAS, "NSSAI parameters not match with allowed NSSAI. Couldn't request PDU session.\n"); - } else { - nssai_t nssai = {nas->uicc->nssai_sst, nas->uicc->nssai_sd}; - request_pdusession(nas, get_softmodem_params()->default_pdu_session_id, PDU_SESSION_TYPE_IPV4, nssai, nas->uicc->dnnStr); - if (get_nrUE_params()->extra_pdu_id != -1) { - request_pdusession(nas, get_nrUE_params()->extra_pdu_id, PDU_SESSION_TYPE_IPV4, nssai, nas->uicc->dnnStr); + if (nas->uicc->n_pdu_sessions == 0) + LOG_W(SIM, "no PDU sessions to request configured\n"); + for (const pdu_session_config_t *pdu = nas->uicc->pdu_sessions; pdu < nas->uicc->pdu_sessions + nas->uicc->n_pdu_sessions; ++pdu) { + if (get_user_nssai_idx(pdu->nssai, msg.nas_allowed_nssai) < 0) { + LOG_E(NAS, + "PDU session ID %d NSSAI %d.%d: mismatch for allowed NSSAI. Couldn't request PDU session.\n", + pdu->id, + pdu->nssai.sst, + pdu->nssai.sd); + } else { + LOG_I(NAS, "requested PDU session ID %d type %d NSSAI %d.%d DNN %s\n", pdu->id, pdu->type, pdu->nssai.sst, pdu->nssai.sd, pdu->dnn); + request_pdusession(nas, pdu); } } // Free local message after processing diff --git a/openair3/NAS/NR_UE/nr_nas_msg.h b/openair3/NAS/NR_UE/nr_nas_msg.h index 1dd5afafe9..1bed56aa3c 100644 --- a/openair3/NAS/NR_UE/nr_nas_msg.h +++ b/openair3/NAS/NR_UE/nr_nas_msg.h @@ -114,6 +114,6 @@ void *nas_nrue_task(void *args_p); void *nas_nrue(void *args_p); void nas_init_nrue(int num_ues); void nr_ue_create_ip_if(const char *ifnameprefix, const char *ipv4, const char *ipv6, int ue_id, int pdu_session_id); -void request_pdusession(nr_ue_nas_t *nas, int pdusession_id, int type, nssai_t nssai, const char *dnn); +void request_pdusession(nr_ue_nas_t *nas, const pdu_session_config_t *pdu); #endif /* __NR_NAS_MSG_SIM_H__*/ diff --git a/openair3/UICC/pdu_session.c b/openair3/UICC/pdu_session.c index f3d13334f7..1eabeb7f37 100644 --- a/openair3/UICC/pdu_session.c +++ b/openair3/UICC/pdu_session.c @@ -82,7 +82,7 @@ static int config_check_dnn(configmodule_interface_t *cfg, paramdef_t *param) return 0; } -int get_pdu_session_configs(int module_id, pdu_session_config_t *configs, int max_len) +int get_pdu_session_configs(const char *uiccName, pdu_session_config_t *configs, int max_len) { paramdef_t pdu_sess_params[] = PDU_SESS_PARAMS_DESC; const int npsp = sizeofArray(pdu_sess_params); @@ -92,7 +92,7 @@ int get_pdu_session_configs(int module_id, pdu_session_config_t *configs, int ma "param_def_t array and corresponding checkedparam_t array should have the same size"); for (int i = 0; i < sizeofArray(pdu_sess_params); ++i) pdu_sess_params[i].chkPptr = &pdu_sess_params_check[i]; - int ret = config_getlist(config_get_if(), &pdu_sess_list, pdu_sess_params, sizeofArray(pdu_sess_params), NULL); + int ret = config_getlist(config_get_if(), &pdu_sess_list, pdu_sess_params, sizeofArray(pdu_sess_params), uiccName); if (ret < 0) { // couldn't load configuration from pdu_sessions, caller has to handle return -1; diff --git a/openair3/UICC/pdu_session.h b/openair3/UICC/pdu_session.h index d74d4664ab..c1acaa82b1 100644 --- a/openair3/UICC/pdu_session.h +++ b/openair3/UICC/pdu_session.h @@ -31,6 +31,6 @@ typedef struct { char *dnn; // [103]? } pdu_session_config_t; -int get_pdu_session_configs(int module_id, pdu_session_config_t *configs, int max_len); +int get_pdu_session_configs(const char *uiccName, pdu_session_config_t *configs, int max_len); #endif /* PDU_SESSION_H_ */ diff --git a/openair3/UICC/usim_interface.c b/openair3/UICC/usim_interface.c index f1019366b1..f722d6ccd6 100644 --- a/openair3/UICC/usim_interface.c +++ b/openair3/UICC/usim_interface.c @@ -22,6 +22,7 @@ */ #include +#include "common/platform_constants.h" #include #include extern uint16_t NB_UE_INST; @@ -76,10 +77,7 @@ uicc_t *init_uicc(char *sectionName) { // key, OPc, sqn, amf don't need to be read from the true USIM int ret = config_get(config_get_if(), uicc_params, sizeofArray(uicc_params), sectionName); AssertFatal(ret >= 0, "configuration couldn't be performed for uicc name: %s", sectionName); - LOG_I(SIM, - "UICC simulation: IMSI=%s, IMEISV=%s, Ki=%s, OPc=%s, DNN=%s, SST=0x%02x, SD=0x%06x\n", - uicc->imsiStr, uicc->imeisvStr, uicc->keyStr, uicc->opcStr, - uicc->dnnStr, uicc->nssai_sst, uicc->nssai_sd); + LOG_I(SIM, "UICC simulation: IMSI=%s, IMEISV=%s, Ki=%s, OPc=%s\n", uicc->imsiStr, uicc->imeisvStr, uicc->keyStr, uicc->opcStr); to_hex(uicc->keyStr,uicc->key, sizeof(uicc->key) ); to_hex(uicc->opcStr,uicc->opc, sizeof(uicc->opc) ); to_hex(uicc->sqnStr,uicc->sqn, sizeof(uicc->sqn) ); @@ -112,6 +110,36 @@ uicc_t * checkUicc(int Mod_id) { char uiccName[64]; sprintf(uiccName,"uicc%d", Mod_id); uiccArray[Mod_id]=(void*)init_uicc(uiccName); + uicc_t *uicc = uiccArray[Mod_id]; + uicc->n_pdu_sessions = get_pdu_session_configs(uiccName, uicc->pdu_sessions, sizeof(uicc->pdu_sessions)); + if (uicc->n_pdu_sessions > 0) { + LOG_I(SIM, "overriding potential %s.dnn/nssai_sst/nssai_sd from %s.pdu_sessions\n", uiccName, uiccName); + } else if (uicc->n_pdu_sessions < 0) { + // we could not load from "new" pdu_sessions list, so read from "legacy" + // config + LOG_W(SIM, + "loading PDU session parameters from legacy UICC configuration. Please update to use %s.pdu_sessions instead to make this warning disappear\n", + uiccName); + sleep(3); + uicc->n_pdu_sessions = 1; + pdu_session_config_t *pdu = &uicc->pdu_sessions[0]; + AssertFatal(uicc->dnnStr != NULL, "no default DNN, cannot create\n"); + pdu->id = DEFAULT_NOS1_PDU_ID; // any default would do + pdu->dnn = strdup(uicc->dnnStr); + pdu->nssai.sst = uicc->nssai_sst; + pdu->nssai.sd = uicc->nssai_sd; + pdu->type = 1; /* = PDU_SESSION_TYPE_IPV4 */ + } // else: uicc->n_pdu_sessions == 0 => don't request a PDU session + for (int i = 0; i < uicc->n_pdu_sessions; ++i) { + const pdu_session_config_t *pdu = &uicc->pdu_sessions[i]; + LOG_I(SIM, + "will request PDU session ID %d, type %d, DNN %s, NSSAI %d.%6x\n", + pdu->id, + pdu->type, + pdu->dnn, + pdu->nssai.sst, + pdu->nssai.sd); + } } return (uicc_t*) uiccArray[Mod_id]; } diff --git a/openair3/UICC/usim_interface.h b/openair3/UICC/usim_interface.h index 1a275db887..f4689594c2 100644 --- a/openair3/UICC/usim_interface.h +++ b/openair3/UICC/usim_interface.h @@ -34,6 +34,7 @@ #include #include #include "common_lib.h" +#include "pdu_session.h" /* 3GPP glossary RES RESponse @@ -53,6 +54,8 @@ typedef struct { char *dnnStr; int nssai_sst; int nssai_sd; + pdu_session_config_t pdu_sessions[256]; + int n_pdu_sessions; uint8_t key[16]; uint8_t opc[16]; uint8_t amf[2];