From 8d225a7e1064757fac77d3c12c8ce7c09f2f1c56 Mon Sep 17 00:00:00 2001 From: Robert Schmidt Date: Thu, 2 May 2024 18:43:12 +0200 Subject: [PATCH] NGAP Release Cplt: indicate release PDU sessions We can optionally indicate the PDU session IDs. At least with OAI 5GC, that should help it clean up. --- openair2/COMMON/ngap_messages_types.h | 2 ++ openair2/RRC/NR/rrc_gNB.c | 5 ++++- openair2/RRC/NR/rrc_gNB_NGAP.c | 17 ++++++++++------- openair2/RRC/NR/rrc_gNB_NGAP.h | 5 ++++- .../ngap_gNB_context_management_procedures.c | 16 +++++++++++++++- 5 files changed, 35 insertions(+), 10 deletions(-) diff --git a/openair2/COMMON/ngap_messages_types.h b/openair2/COMMON/ngap_messages_types.h index 0c9be504ca..29ea48294a 100644 --- a/openair2/COMMON/ngap_messages_types.h +++ b/openair2/COMMON/ngap_messages_types.h @@ -583,6 +583,8 @@ typedef struct ngap_ue_ctxt_modification_resp_s { typedef struct ngap_ue_release_complete_s { uint32_t gNB_ue_ngap_id; + int num_pdu_sessions; + uint32_t pdu_session_id[256]; } ngap_ue_release_complete_t; //-------------------------------------------------------------------------------------------// diff --git a/openair2/RRC/NR/rrc_gNB.c b/openair2/RRC/NR/rrc_gNB.c index 0bb2d27e9a..1e6915624b 100644 --- a/openair2/RRC/NR/rrc_gNB.c +++ b/openair2/RRC/NR/rrc_gNB.c @@ -1810,7 +1810,10 @@ void rrc_remove_ue(gNB_RRC_INST *rrc, rrc_gNB_ue_context_t *ue_context_p) * are in E1, we also need to free the UE in the CU-CP, so call it twice to * cover all cases */ nr_pdcp_remove_UE(UE->rrc_ue_id); - rrc_gNB_send_NGAP_UE_CONTEXT_RELEASE_COMPLETE(0, UE->rrc_ue_id); + uint32_t pdu_sessions[256]; + for (int i = 0; i < UE->nb_of_pdusessions && i < 256; ++i) + pdu_sessions[i] = UE->pduSession[i].param.pdusession_id; + rrc_gNB_send_NGAP_UE_CONTEXT_RELEASE_COMPLETE(0, UE->rrc_ue_id, UE->nb_of_pdusessions, pdu_sessions); LOG_I(NR_RRC, "removed UE CU UE ID %u/RNTI %04x \n", UE->rrc_ue_id, UE->rnti); rrc_delete_ue_data(UE); rrc_gNB_remove_ue_context(rrc, ue_context_p); diff --git a/openair2/RRC/NR/rrc_gNB_NGAP.c b/openair2/RRC/NR/rrc_gNB_NGAP.c index ec6922b598..a6d5c86449 100644 --- a/openair2/RRC/NR/rrc_gNB_NGAP.c +++ b/openair2/RRC/NR/rrc_gNB_NGAP.c @@ -1164,13 +1164,10 @@ int rrc_gNB_process_NGAP_UE_CONTEXT_RELEASE_COMMAND(MessageDef *msg_p, instance_ if (ue_context_p == NULL) { /* Can not associate this message to an UE index */ - MessageDef *msg_complete_p = NULL; LOG_W(NR_RRC, "[gNB %ld] In NGAP_UE_CONTEXT_RELEASE_COMMAND: unknown UE from gNB_ue_ngap_id (%u)\n", instance, gNB_ue_ngap_id); - msg_complete_p = itti_alloc_new_message(TASK_RRC_GNB, 0, NGAP_UE_CONTEXT_RELEASE_COMPLETE); - NGAP_UE_CONTEXT_RELEASE_COMPLETE(msg_complete_p).gNB_ue_ngap_id = gNB_ue_ngap_id; - itti_send_msg_to_task(TASK_NGAP, instance, msg_complete_p); + rrc_gNB_send_NGAP_UE_CONTEXT_RELEASE_COMPLETE(instance, gNB_ue_ngap_id, 0, NULL); return -1; } @@ -1206,11 +1203,17 @@ int rrc_gNB_process_NGAP_UE_CONTEXT_RELEASE_COMMAND(MessageDef *msg_p, instance_ return 0; } -void rrc_gNB_send_NGAP_UE_CONTEXT_RELEASE_COMPLETE( - instance_t instance, - uint32_t gNB_ue_ngap_id) { +void rrc_gNB_send_NGAP_UE_CONTEXT_RELEASE_COMPLETE(instance_t instance, + uint32_t gNB_ue_ngap_id, + int num_pdu, + uint32_t pdu_session_id[256]) +{ MessageDef *msg = itti_alloc_new_message(TASK_RRC_GNB, 0, NGAP_UE_CONTEXT_RELEASE_COMPLETE); NGAP_UE_CONTEXT_RELEASE_COMPLETE(msg).gNB_ue_ngap_id = gNB_ue_ngap_id; + NGAP_UE_CONTEXT_RELEASE_COMPLETE(msg).num_pdu_sessions = num_pdu; + for (int i = 0; i < num_pdu; ++i) + NGAP_UE_CONTEXT_RELEASE_COMPLETE(msg).pdu_session_id[i] = pdu_session_id[i]; + LOG_W(RRC, "trigger release with %d pdu\n", num_pdu); itti_send_msg_to_task(TASK_NGAP, instance, msg); } diff --git a/openair2/RRC/NR/rrc_gNB_NGAP.h b/openair2/RRC/NR/rrc_gNB_NGAP.h index 25e7974632..533aa8d15d 100644 --- a/openair2/RRC/NR/rrc_gNB_NGAP.h +++ b/openair2/RRC/NR/rrc_gNB_NGAP.h @@ -94,7 +94,10 @@ int rrc_gNB_process_NGAP_UE_CONTEXT_RELEASE_REQ(MessageDef *msg_p, instance_t in int rrc_gNB_process_NGAP_UE_CONTEXT_RELEASE_COMMAND(MessageDef *msg_p, instance_t instance); -void rrc_gNB_send_NGAP_UE_CONTEXT_RELEASE_COMPLETE(instance_t instance, uint32_t gNB_ue_ngap_id); +void rrc_gNB_send_NGAP_UE_CONTEXT_RELEASE_COMPLETE(instance_t instance, + uint32_t gNB_ue_ngap_id, + int num_pdu, + uint32_t pdu_session_id[256]); void rrc_gNB_send_NGAP_UE_CAPABILITIES_IND(const protocol_ctxt_t *const ctxt_pP, rrc_gNB_ue_context_t *const ue_context_pP, diff --git a/openair3/NGAP/ngap_gNB_context_management_procedures.c b/openair3/NGAP/ngap_gNB_context_management_procedures.c index b05f96b899..242da7a257 100644 --- a/openair3/NGAP/ngap_gNB_context_management_procedures.c +++ b/openair3/NGAP/ngap_gNB_context_management_procedures.c @@ -50,7 +50,7 @@ #include "ngap_gNB_management_procedures.h" #include "ngap_gNB_context_management_procedures.h" #include "NGAP_PDUSessionResourceItemCxtRelReq.h" - +#include "NGAP_PDUSessionResourceItemCxtRelCpl.h" int ngap_ue_context_release_complete(instance_t instance, ngap_ue_release_complete_t *ue_release_complete_p) @@ -100,6 +100,20 @@ int ngap_ue_context_release_complete(instance_t instance, ie->value.choice.RAN_UE_NGAP_ID = ue_release_complete_p->gNB_ue_ngap_id; } + /* number of PDU sessions */ + if (ue_release_complete_p->num_pdu_sessions > 0) { + asn1cSequenceAdd(out->protocolIEs.list, NGAP_UEContextReleaseComplete_IEs_t, ie); + ie->id = NGAP_ProtocolIE_ID_id_PDUSessionResourceListCxtRelCpl; + ie->criticality = NGAP_Criticality_reject; + ie->value.present = NGAP_UEContextReleaseComplete_IEs__value_PR_PDUSessionResourceListCxtRelCpl; + NGAP_PDUSessionResourceListCxtRelCpl_t *l = &ie->value.choice.PDUSessionResourceListCxtRelCpl; + DevAssert(ue_release_complete_p->num_pdu_sessions <= 256); + for (int i = 0; i < ue_release_complete_p->num_pdu_sessions; ++i) { + asn1cSequenceAdd(l->list, NGAP_PDUSessionResourceItemCxtRelCpl_t, pdu); + pdu->pDUSessionID = ue_release_complete_p->pdu_session_id[i]; + } + } + if (ngap_gNB_encode_pdu(&pdu, &buffer, &length) < 0) { /* Encode procedure has failed... */ NGAP_ERROR("Failed to encode UE context release complete\n");