diff --git a/CMakeLists.txt b/CMakeLists.txt
index 6d06d30c17..948f623f2b 100644
--- a/CMakeLists.txt
+++ b/CMakeLists.txt
@@ -413,6 +413,7 @@ target_link_libraries(x2ap PRIVATE asn1_lte_rrc_hdrs asn1_nr_rrc_hdrs)
set(F1AP_DIR ${OPENAIR2_DIR}/F1AP)
add_library(f1ap
${F1AP_DIR}/f1ap_common.c
+ ${F1AP_DIR}/f1ap_ids.c
${F1AP_DIR}/f1ap_cu_interface_management.c
${F1AP_DIR}/f1ap_cu_paging.c
${F1AP_DIR}/f1ap_cu_rrc_message_transfer.c
@@ -431,7 +432,7 @@ add_library(f1ap
${F1AP_DIR}/f1ap_itti_messaging.c)
target_include_directories(f1ap PUBLIC F1AP_DIR)
target_link_libraries(f1ap PUBLIC asn1_f1ap)
-target_link_libraries(f1ap PRIVATE ngap nr_rrc)
+target_link_libraries(f1ap PRIVATE ngap nr_rrc HASHTABLE)
# LPP
##############
diff --git a/ci-scripts/xml_files/container_sa_b200_quectel.xml b/ci-scripts/xml_files/container_sa_b200_quectel.xml
index 121b836769..0296ecfe93 100644
--- a/ci-scripts/xml_files/container_sa_b200_quectel.xml
+++ b/ci-scripts/xml_files/container_sa_b200_quectel.xml
@@ -111,7 +111,7 @@
IdleSleep
Sleep
- 20
+ 10
@@ -168,14 +168,14 @@
Custom_Command
Trigger Reestablishment
ofqot
- echo ci force_reestab | nc -N 192.168.68.194 9090 | grep -E 'force-remove UE RNTI [0-9a-f]{4} from RLC to trigger reestablishment'
+ echo ci force_reestab | nc -N 192.168.68.194 9090 | grep -E 'Reset RLC counters of UE RNTI [0-9a-f]{4} to trigger reestablishment'
yes
Custom_Command
Verify Reestablishment
ofqot
- echo ci get_reestab_count | nc -N 192.168.68.194 9090 | grep -E 'UE RNTI [0-9a-f]{4} reestab 1 reconf_after_reestab 1'
+ echo ci get_reestab_count | nc -N 192.168.68.194 9090 | grep -E 'UE RNTI [0-9a-f]{4} reestab 1'
yes
diff --git a/ci-scripts/xml_files/container_sa_f1_b200_quectel.xml b/ci-scripts/xml_files/container_sa_f1_b200_quectel.xml
index a20ea8845e..1f28fce309 100644
--- a/ci-scripts/xml_files/container_sa_f1_b200_quectel.xml
+++ b/ci-scripts/xml_files/container_sa_f1_b200_quectel.xml
@@ -39,6 +39,10 @@
110011
110001
150001
+ 160001
+ 100002
+ 160002
+ 150001
110011
110001
150000
@@ -114,7 +118,7 @@
IdleSleep
Sleep
- 20
+ 10
@@ -184,6 +188,21 @@
single-ue
+
+ Custom_Command
+ Trigger Reestablishment (on DU)
+ ofqot
+ echo ci force_reestab | nc -N 192.168.68.195 9090 | grep -E 'Reset RLC counters of UE RNTI [0-9a-f]{4} to trigger reestablishment'
+ yes
+
+
+ Custom_Command
+ Verify Reestablishment (on CU)
+ ofqot
+ echo ci get_reestab_count | nc -N 192.168.68.194 9090 | grep -E 'UE RNTI [0-9a-f]{4} reestab 1'
+ yes
+
+
Undeploy_Object
Undeploy CU-DU
diff --git a/ci-scripts/xml_files/container_sa_sc_b200_quectel.xml b/ci-scripts/xml_files/container_sa_sc_b200_quectel.xml
index 0d4dd8f27e..d603b3f1ea 100644
--- a/ci-scripts/xml_files/container_sa_sc_b200_quectel.xml
+++ b/ci-scripts/xml_files/container_sa_sc_b200_quectel.xml
@@ -105,7 +105,7 @@
IdleSleep
Sleep
- 20
+ 10
@@ -162,14 +162,14 @@
Custom_Command
Trigger Reestablishment
ofqot
- echo ci force_reestab | nc -N 192.168.68.194 9090 | grep -E 'force-remove UE RNTI [0-9a-f]{4} from RLC to trigger reestablishment'
+ echo ci force_reestab | nc -N 192.168.68.194 9090 | grep -E 'Reset RLC counters of UE RNTI [0-9a-f]{4} to trigger reestablishment'
yes
Custom_Command
Verify Reestablishment
ofqot
- echo ci get_reestab_count | nc -N 192.168.68.194 9090 | grep -E 'UE RNTI [0-9a-f]{4} reestab 1 reconf_after_reestab 1'
+ echo ci get_reestab_count | nc -N 192.168.68.194 9090 | grep -E 'UE RNTI [0-9a-f]{4} reestab 1'
yes
diff --git a/ci-scripts/yaml_files/sa_f1_b200_gnb/docker-compose.yml b/ci-scripts/yaml_files/sa_f1_b200_gnb/docker-compose.yml
index e40dc686d7..2be92cdb38 100644
--- a/ci-scripts/yaml_files/sa_f1_b200_gnb/docker-compose.yml
+++ b/ci-scripts/yaml_files/sa_f1_b200_gnb/docker-compose.yml
@@ -6,7 +6,7 @@ services:
privileged: true
container_name: sa-cu-gnb
environment:
- USE_ADDITIONAL_OPTIONS: --sa --log_config.global_log_options level,nocolor,time,line_num,function
+ USE_ADDITIONAL_OPTIONS: --sa --telnetsrv --telnetsrv.shrmod ci --log_config.global_log_options level,nocolor,time,line_num,function
volumes:
- ../../conf_files/gnb-cu.sa.band78.106prb.usrpb200.conf:/opt/oai-gnb/etc/gnb.conf
networks:
@@ -26,7 +26,7 @@ services:
container_name: sa-du-b200-gnb
environment:
USE_B2XX: 'yes'
- USE_ADDITIONAL_OPTIONS: --sa --RUs.[0].sdr_addrs serial=30C51D4 --continuous-tx -E --log_config.global_log_options level,nocolor,time,line_num,function --gNBs.[0].min_rxtxtime 2 --gNBs.[0].do_CSIRS 1 --gNBs.[0].do_SRS 1 --RUs.[0].att_rx 14 --RUs.[0].att_tx 14
+ USE_ADDITIONAL_OPTIONS: --sa --RUs.[0].sdr_addrs serial=30C51D4 --continuous-tx -E --telnetsrv --telnetsrv.shrmod ci --log_config.global_log_options level,nocolor,time,line_num,function --gNBs.[0].min_rxtxtime 2 --gNBs.[0].do_CSIRS 1 --gNBs.[0].do_SRS 1 --RUs.[0].att_rx 14 --RUs.[0].att_tx 14
volumes:
- ../../conf_files/gnb-du.sa.band78.106prb.usrpb200.conf:/opt/oai-gnb/etc/gnb.conf
- /dev:/dev
diff --git a/common/utils/telnetsrv/telnetsrv_ci.c b/common/utils/telnetsrv/telnetsrv_ci.c
index 3f4930d02b..2d7019b00e 100644
--- a/common/utils/telnetsrv/telnetsrv_ci.c
+++ b/common/utils/telnetsrv/telnetsrv_ci.c
@@ -28,15 +28,17 @@
#include
#include "openair2/RRC/NR/rrc_gNB_UE_context.h"
-#include "openair2/LAYER2/nr_rlc/nr_rlc_oai_api.h"
#include "openair2/LAYER2/NR_MAC_gNB/nr_mac_gNB.h"
+#include "openair2/LAYER2/nr_rlc/nr_rlc_oai_api.h"
+#include "openair2/LAYER2/nr_rlc/nr_rlc_ue_manager.h"
+#include "openair2/LAYER2/nr_rlc/nr_rlc_entity_am.h"
#define TELNETSERVERCODE
#include "telnetsrv.h"
#define ERROR_MSG_RET(mSG, aRGS...) do { prnt(mSG, ##aRGS); return 1; } while (0)
-static int get_single_ue_rnti(void)
+static int get_single_ue_rnti_mac(void)
{
NR_UE_info_t *ue = NULL;
UE_iterator(RC.nrmac[0]->UE_info.list, it) {
@@ -48,11 +50,6 @@ static int get_single_ue_rnti(void)
if (!ue)
return -1;
- // verify it exists in RRC as well
- rrc_gNB_ue_context_t *rrcue = rrc_gNB_get_ue_context_by_rnti(RC.nrrrc[0], ue->rnti);
- if (!rrcue)
- return -1;
-
return ue->rnti;
}
@@ -61,7 +58,7 @@ int get_single_rnti(char *buf, int debug, telnet_printfunc_t prnt)
if (buf)
ERROR_MSG_RET("no parameter allowed\n");
- int rnti = get_single_ue_rnti();
+ int rnti = get_single_ue_rnti_mac();
if (rnti < 1)
ERROR_MSG_RET("different number of UEs\n");
@@ -71,23 +68,32 @@ int get_single_rnti(char *buf, int debug, telnet_printfunc_t prnt)
int get_reestab_count(char *buf, int debug, telnet_printfunc_t prnt)
{
+ if (!RC.nrrrc)
+ ERROR_MSG_RET("no RRC present, cannot list counts\n");
+ rrc_gNB_ue_context_t *ue = NULL;
int rnti = -1;
if (!buf) {
- rnti = get_single_ue_rnti();
- if (rnti < 1)
- ERROR_MSG_RET("no UE found\n");
+ rrc_gNB_ue_context_t *l = NULL;
+ int n = 0;
+ RB_FOREACH(l, rrc_nr_ue_tree_s, &RC.nrrrc[0]->rrc_ue_head) {
+ if (ue == NULL) ue = l;
+ n++;
+ }
+ if (!ue)
+ ERROR_MSG_RET("could not find any UE in RRC\n");
+ if (n > 1)
+ ERROR_MSG_RET("more than one UE in RRC present\n");
} else {
rnti = strtol(buf, NULL, 16);
if (rnti < 1 || rnti >= 0xfffe)
ERROR_MSG_RET("RNTI needs to be [1,0xfffe]\n");
+ ue = rrc_gNB_get_ue_context_by_rnti(RC.nrrrc[0], rnti);
+ if (!ue)
+ ERROR_MSG_RET("could not find UE with RNTI %04x in RRC\n");
}
- rrc_gNB_ue_context_t *ue = rrc_gNB_get_ue_context_by_rnti(RC.nrrrc[0], rnti);
- if (!ue)
- ERROR_MSG_RET("could not find UE with RNTI %04x\n", rnti);
-
prnt("UE RNTI %04x reestab %d reconf_after_reestab %d\n",
- rnti,
+ ue->ue_context.rnti,
ue->ue_context.ue_reestablishment_counter,
ue->ue_context.ue_reconfiguration_after_reestablishment_counter);
return 0;
@@ -95,9 +101,11 @@ int get_reestab_count(char *buf, int debug, telnet_printfunc_t prnt)
int trigger_reestab(char *buf, int debug, telnet_printfunc_t prnt)
{
+ if (!RC.nrmac)
+ ERROR_MSG_RET("no MAC/RLC present, cannot trigger reestablishment\n");
int rnti = -1;
if (!buf) {
- rnti = get_single_ue_rnti();
+ rnti = get_single_ue_rnti_mac();
if (rnti < 1)
ERROR_MSG_RET("no UE found\n");
} else {
@@ -106,13 +114,9 @@ int trigger_reestab(char *buf, int debug, telnet_printfunc_t prnt)
ERROR_MSG_RET("RNTI needs to be [1,0xfffe]\n");
}
- // verify it exists in RRC as well
- rrc_gNB_ue_context_t *rrcue = rrc_gNB_get_ue_context_by_rnti(RC.nrrrc[0], rnti);
- if (!rrcue)
- ERROR_MSG_RET("could not find UE with RNTI %04x\n", rnti);
+ nr_rlc_test_trigger_reestablishment(rnti);
- nr_rlc_remove_ue(rnti);
- prnt("force-remove UE RNTI %04x from RLC to trigger reestablishment\n", rnti);
+ prnt("Reset RLC counters of UE RNTI %04x to trigger reestablishment\n", rnti);
return 0;
}
diff --git a/executables/nr-cuup.c b/executables/nr-cuup.c
index ffa50a766b..81d255b87d 100644
--- a/executables/nr-cuup.c
+++ b/executables/nr-cuup.c
@@ -27,6 +27,7 @@
#include "common/ran_context.h"
#include "nfapi/oai_integration/vendor_ext.h"
#include "openair2/F1AP/f1ap_common.h"
+#include "openair2/F1AP/f1ap_ids.h"
#include "openair2/GNB_APP/gnb_config.h"
#include "nr_pdcp/nr_pdcp_oai_api.h"
@@ -134,6 +135,7 @@ int main(int argc, char **argv)
rc = itti_create_task(TASK_CUUP_E1, E1AP_CUUP_task, NULL);
AssertFatal(rc >= 0, "Create task for CUUP E1 failed\n");
nr_pdcp_layer_init();
+ cu_init_f1_ue_data(); // for CU-UP/CP mapping: we use the same
MessageDef *msg = RCconfig_NR_CU_E1(true);
AssertFatal(msg != NULL, "Send init to task for E1AP UP failed\n");
itti_send_msg_to_task(TASK_CUUP_E1, 0, msg);
diff --git a/openair2/COMMON/e1ap_messages_types.h b/openair2/COMMON/e1ap_messages_types.h
index 7a88344efc..7a1a8b2698 100644
--- a/openair2/COMMON/e1ap_messages_types.h
+++ b/openair2/COMMON/e1ap_messages_types.h
@@ -156,7 +156,6 @@ typedef struct pdu_session_to_setup_s {
typedef struct e1ap_bearer_setup_req_s {
uint32_t gNB_cu_cp_ue_id;
uint32_t gNB_cu_up_ue_id;
- rnti_t rnti;
uint64_t cipheringAlgorithm;
uint64_t integrityProtectionAlgorithm;
char encryptionKey[128];
@@ -216,8 +215,8 @@ typedef struct pdu_session_setup_s {
} pdu_session_setup_t;
typedef struct e1ap_bearer_setup_resp_s {
- uint64_t gNB_cu_cp_ue_id;
- uint64_t gNB_cu_up_ue_id;
+ uint32_t gNB_cu_cp_ue_id;
+ uint32_t gNB_cu_up_ue_id;
int numDRBs;
drb_setup_t DRBList[E1AP_MAX_NUM_DRBS];
int numPDUSessions;
diff --git a/openair2/COMMON/f1ap_messages_types.h b/openair2/COMMON/f1ap_messages_types.h
index 08cc03c4fa..3d594a695e 100644
--- a/openair2/COMMON/f1ap_messages_types.h
+++ b/openair2/COMMON/f1ap_messages_types.h
@@ -286,8 +286,7 @@ typedef struct f1ap_dl_rrc_message_s {
uint32_t gNB_CU_ue_id;
uint32_t gNB_DU_ue_id;
- uint32_t old_gNB_DU_ue_id;
- uint16_t rnti;
+ uint32_t *old_gNB_DU_ue_id;
uint8_t srb_id;
uint8_t execute_duplication;
uint8_t *rrc_container;
@@ -318,7 +317,8 @@ typedef struct f1ap_initial_ul_rrc_message_s {
} f1ap_initial_ul_rrc_message_t;
typedef struct f1ap_ul_rrc_message_s {
- uint16_t rnti;
+ uint32_t gNB_CU_ue_id;
+ uint32_t gNB_DU_ue_id;
uint8_t srb_id;
uint8_t *rrc_container;
int rrc_container_length;
@@ -378,9 +378,8 @@ typedef enum ReconfigurationCompl_e {
} ReconfigurationCompl_t;
typedef struct f1ap_ue_context_setup_s {
- uint32_t gNB_CU_ue_id; // BK: need to replace by use from rnti
+ uint32_t gNB_CU_ue_id;
uint32_t gNB_DU_ue_id;
- uint16_t rnti;
// SpCell Info
uint16_t mcc;
uint16_t mnc;
@@ -419,7 +418,8 @@ typedef enum F1ap_Cause_e {
} f1ap_Cause_t;
typedef struct f1ap_ue_context_release_s {
- uint16_t rnti;
+ uint32_t gNB_CU_ue_id;
+ uint32_t gNB_DU_ue_id;
f1ap_Cause_t cause;
long cause_value;
uint8_t *rrc_container;
diff --git a/openair2/E1AP/e1ap.c b/openair2/E1AP/e1ap.c
index 6c33ddf973..27eb9f5848 100644
--- a/openair2/E1AP/e1ap.c
+++ b/openair2/E1AP/e1ap.c
@@ -1095,7 +1095,7 @@ static int fill_BEARER_CONTEXT_MODIFICATION_REQUEST(e1ap_setup_req_t *setupReq,
ieC2->id = E1AP_ProtocolIE_ID_id_gNB_CU_UP_UE_E1AP_ID;
ieC2->criticality = E1AP_Criticality_reject;
ieC2->value.present = E1AP_BearerContextModificationRequestIEs__value_PR_GNB_CU_UP_UE_E1AP_ID;
- ieC2->value.choice.GNB_CU_UP_UE_E1AP_ID = bearerCxt->gNB_cu_cp_ue_id;
+ ieC2->value.choice.GNB_CU_UP_UE_E1AP_ID = bearerCxt->gNB_cu_up_ue_id;
/* optional */
/* */
asn1cSequenceAdd(out->protocolIEs.list, E1AP_BearerContextModificationRequestIEs_t, ieC3);
diff --git a/openair2/E1AP/e1ap_api.c b/openair2/E1AP/e1ap_api.c
index cf167f64e8..9cec6b69f3 100644
--- a/openair2/E1AP/e1ap_api.c
+++ b/openair2/E1AP/e1ap_api.c
@@ -30,6 +30,7 @@
#include "openair2/RRC/LTE/MESSAGES/asn1_msg.h"
#include "openair3/SECU/key_nas_deriver.h"
#include "openair3/ocp-gtpu/gtp_itf.h"
+#include "openair2/F1AP/f1ap_ids.h"
#include "e1ap_asnc.h"
#include "e1ap_common.h"
#include "e1ap.h"
@@ -109,7 +110,7 @@ static int drb_config_N3gtpu_create(e1ap_bearer_setup_req_t * const req,
fill_DRB_configList_e1(&DRB_configList, pdu);
}
create_tunnel_req.num_tunnels = req->numPDUSessions;
- create_tunnel_req.ue_id = (req->gNB_cu_cp_ue_id & 0xFFFF);
+ create_tunnel_req.ue_id = req->gNB_cu_cp_ue_id;
// Create N3 tunnel
int ret = gtpv1u_create_ngu_tunnel(instance, &create_tunnel_req, create_tunnel_resp, nr_pdcp_data_req_drb, sdap_data_req);
@@ -136,6 +137,11 @@ void process_e1_bearer_context_setup_req(instance_t instance, e1ap_bearer_setup_
AssertFatal(inst, "");
gtpv1u_gnb_create_tunnel_resp_t create_tunnel_resp_N3={0};
+ uint32_t gNB_cu_up_ue_id = req ->gNB_cu_cp_ue_id;
+ LOG_I(E1AP, "adding UE with CU-CP UE ID %d and CU-UP UE ID %d\n", req->gNB_cu_cp_ue_id, gNB_cu_up_ue_id);
+ f1_ue_data_t ue_data = {.secondary_ue = req->gNB_cu_cp_ue_id};
+ cu_add_f1_ue_data(gNB_cu_up_ue_id, &ue_data);
+
// GTP tunnel for UL
drb_config_N3gtpu_create(req, &create_tunnel_resp_N3, inst->gtpInstN3);
@@ -148,6 +154,7 @@ void process_e1_bearer_context_setup_req(instance_t instance, e1ap_bearer_setup_
fill_e1ap_bearer_setup_resp(resp, req, inst->gtpInstF1U, req->gNB_cu_cp_ue_id, inst->setupReq.remotePortF1U, my_addr);
resp->gNB_cu_cp_ue_id = req->gNB_cu_cp_ue_id;
+ resp->gNB_cu_up_ue_id = gNB_cu_up_ue_id;
resp->numPDUSessions = req->numPDUSessions;
for (int i=0; i < req->numPDUSessions; i++) {
pdu_session_setup_t *pduSetup = resp->pduSession + i;
diff --git a/openair2/F1AP/CMakeLists.txt b/openair2/F1AP/CMakeLists.txt
index 7537bd661d..e6490b96b0 100644
--- a/openair2/F1AP/CMakeLists.txt
+++ b/openair2/F1AP/CMakeLists.txt
@@ -1 +1,8 @@
add_subdirectory(MESSAGES)
+
+if(ENABLE_TESTS)
+ add_executable(f1ap_ids_test f1ap_ids_test.c f1ap_ids.c)
+ target_link_libraries(f1ap_ids_test UTIL HASHTABLE minimal_lib)
+ add_dependencies(tests f1ap_ids_test)
+ add_test(NAME F1AP_ID_test COMMAND f1ap_ids_test)
+endif()
diff --git a/openair2/F1AP/f1ap_common.c b/openair2/F1AP/f1ap_common.c
index f417a1c337..f396d570df 100644
--- a/openair2/F1AP/f1ap_common.c
+++ b/openair2/F1AP/f1ap_common.c
@@ -66,123 +66,6 @@ void createF1inst(F1_t isCU, instance_t instanceP, f1ap_setup_req_t *req) {
}
}
-int f1ap_add_ue(F1_t isCu,
- instance_t instanceP,
- rnti_t rntiP) {
- f1ap_cudu_inst_t *f1_inst=getCxt(isCu, instanceP);
-
- for (int i = 0; i < MAX_MOBILES_PER_GNB; i++) {
- if (f1_inst->f1ap_ue[i].rnti == rntiP) {
- f1_inst->f1ap_ue[i].f1ap_uid = i;
- LOG_I(F1AP, "Updating the index of UE with RNTI %x and du_ue_f1ap_id %ld\n", f1_inst->f1ap_ue[i].rnti, f1_inst->f1ap_ue[i].du_ue_f1ap_id);
- return i;
- }
- }
-
- // We didn't find the rnti
- for (int i = 0; i < MAX_MOBILES_PER_GNB; i++) {
- if (f1_inst->f1ap_ue[i].rnti == 0 ) {
- f1_inst->f1ap_ue[i].rnti = rntiP;
- f1_inst->f1ap_ue[i].f1ap_uid = i;
- f1_inst->f1ap_ue[i].du_ue_f1ap_id = rntiP;
- f1_inst->f1ap_ue[i].cu_ue_f1ap_id = rntiP;
- f1_inst->num_ues++;
- LOG_I(F1AP, "Adding a new UE with RNTI %x and cu/du ue_f1ap_id %ld\n", f1_inst->f1ap_ue[i].rnti, f1_inst->f1ap_ue[i].du_ue_f1ap_id);
- return i;
- }
- }
-
- return -1;
-}
-
-
-int f1ap_remove_ue(F1_t isCu, instance_t instanceP,
- rnti_t rntiP) {
- f1ap_cudu_inst_t *f1_inst=getCxt(isCu, instanceP);
-
- for (int i = 0; i < MAX_MOBILES_PER_GNB; i++) {
- if (f1_inst->f1ap_ue[i].rnti == rntiP) {
- f1_inst->f1ap_ue[i].rnti = 0;
- break;
- }
- }
-
- f1_inst->num_ues--;
- return 0;
-}
-
-int f1ap_get_du_ue_f1ap_id(F1_t isCu, instance_t instanceP,
- rnti_t rntiP) {
- f1ap_cudu_inst_t *f1_inst=getCxt(isCu, instanceP);
-
- for (int i = 0; i < MAX_MOBILES_PER_GNB; i++) {
- if (f1_inst->f1ap_ue[i].rnti == rntiP) {
- return f1_inst->f1ap_ue[i].du_ue_f1ap_id;
- }
- }
-
- return -1;
-}
-
-int f1ap_get_cu_ue_f1ap_id(F1_t isCu, instance_t instanceP,
- rnti_t rntiP) {
- f1ap_cudu_inst_t *f1_inst=getCxt(isCu, instanceP);
-
- for (int i = 0; i < MAX_MOBILES_PER_GNB; i++) {
- if (f1_inst->f1ap_ue[i].rnti == rntiP) {
- return f1_inst->f1ap_ue[i].cu_ue_f1ap_id;
- }
- }
-
- return -1;
-}
-
-int f1ap_get_rnti_by_du_id(F1_t isCu, instance_t instanceP,
- instance_t du_ue_f1ap_id ) {
- f1ap_cudu_inst_t *f1_inst=getCxt(isCu, instanceP);
-
- for (int i = 0; i < MAX_MOBILES_PER_GNB; i++) {
- if (f1_inst->f1ap_ue[i].du_ue_f1ap_id == du_ue_f1ap_id) {
- return f1_inst->f1ap_ue[i].rnti;
- }
- }
-
- return -1;
-}
-
-int f1ap_get_rnti_by_cu_id(F1_t isCu, instance_t instanceP,
- instance_t cu_ue_f1ap_id ) {
- f1ap_cudu_inst_t *f1_inst=getCxt(isCu, instanceP);
-
- for (int i = 0; i < MAX_MOBILES_PER_GNB; i++) {
- if (f1_inst->f1ap_ue[i].cu_ue_f1ap_id == cu_ue_f1ap_id) {
- return f1_inst->f1ap_ue[i].rnti;
- }
- }
-
- return -1;
-}
-
-int f1ap_du_add_cu_ue_id(instance_t instanceP,
- instance_t du_ue_f1ap_id,
- instance_t cu_ue_f1ap_id) {
- f1ap_cudu_inst_t *f1_inst=getCxt(DUtype, instanceP);
- instance_t f1ap_uid=-1;
-
- for (int i = 0; i < MAX_MOBILES_PER_GNB; i++) {
- if (f1_inst->f1ap_ue[i].du_ue_f1ap_id == du_ue_f1ap_id) {
- f1ap_uid=i;
- break;
- }
- }
-
- if (f1ap_uid < 0 || f1ap_uid >= MAX_MOBILES_PER_GNB)
- return -1;
-
- f1_inst->f1ap_ue[f1ap_uid].cu_ue_f1ap_id = cu_ue_f1ap_id;
- LOG_D(F1AP, "Adding cu_ue_f1ap_id %ld for UE with RNTI %x\n", cu_ue_f1ap_id, f1_inst->f1ap_ue[f1ap_uid].rnti);
- return 0;
-}
int f1ap_assoc_id(F1_t isCu, instance_t instanceP) {
f1ap_setup_req_t *f1_inst=f1ap_req(isCu, instanceP);
diff --git a/openair2/F1AP/f1ap_common.h b/openair2/F1AP/f1ap_common.h
index ff492820d7..a346d9682a 100644
--- a/openair2/F1AP/f1ap_common.h
+++ b/openair2/F1AP/f1ap_common.h
@@ -427,30 +427,6 @@ uint8_t F1AP_get_next_transaction_identifier(instance_t mod_idP, instance_t cu_m
f1ap_cudu_inst_t *getCxt(F1_t isCU, instance_t instanceP);
void createF1inst(F1_t isCU, instance_t instanceP, f1ap_setup_req_t *req);
-int f1ap_add_ue(F1_t isCu,
- instance_t instanceP,
- rnti_t rntiP);
-
-int f1ap_remove_ue(F1_t isCu, instance_t instanceP,
- rnti_t rntiP);
-
-int f1ap_get_du_ue_f1ap_id (F1_t isCu, instance_t instanceP,
- rnti_t rntiP);
-
-int f1ap_get_cu_ue_f1ap_id (F1_t isCu, instance_t instanceP,
- rnti_t rntiP);
-
-
-int f1ap_get_rnti_by_du_id(F1_t isCu, instance_t instanceP,
- instance_t du_ue_f1ap_id );
-
-
-int f1ap_get_rnti_by_cu_id(F1_t isCu, instance_t instanceP,
- instance_t cu_ue_f1ap_id );
-
-int f1ap_du_add_cu_ue_id(instance_t instanceP,
- instance_t du_ue_f1ap_id,
- instance_t cu_ue_f1ap_id);
int f1ap_assoc_id(F1_t isCu, instance_t instanceP);
diff --git a/openair2/F1AP/f1ap_cu_rrc_message_transfer.c b/openair2/F1AP/f1ap_cu_rrc_message_transfer.c
index 5c3b100efd..13bc9954a3 100644
--- a/openair2/F1AP/f1ap_cu_rrc_message_transfer.c
+++ b/openair2/F1AP/f1ap_cu_rrc_message_transfer.c
@@ -32,6 +32,7 @@
#include "f1ap_common.h"
#include "f1ap_encoder.h"
+#include "f1ap_ids.h"
#include "f1ap_itti_messaging.h"
#include "f1ap_cu_rrc_message_transfer.h"
#include "common/ran_context.h"
@@ -53,9 +54,6 @@ int CU_handle_INITIAL_UL_RRC_MESSAGE_TRANSFER(instance_t instance,
MessageDef *message_p;
F1AP_InitialULRRCMessageTransfer_t *container;
F1AP_InitialULRRCMessageTransferIEs_t *ie;
- rnti_t rnti;
- sdu_size_t ccch_sdu_len;
- int CC_id =0;
DevAssert(pdu != NULL);
if (stream != 0) {
@@ -68,6 +66,8 @@ int CU_handle_INITIAL_UL_RRC_MESSAGE_TRANSFER(instance_t instance,
/* GNB_DU_UE_F1AP_ID */
F1AP_FIND_PROTOCOLIE_BY_ID(F1AP_InitialULRRCMessageTransferIEs_t, ie, container,
F1AP_ProtocolIE_ID_id_gNB_DU_UE_F1AP_ID, true);
+ uint32_t du_ue_id = ie->value.choice.GNB_DU_UE_F1AP_ID;
+
/* NRCGI
* Fixme: process NRCGI
*/
@@ -78,7 +78,7 @@ int CU_handle_INITIAL_UL_RRC_MESSAGE_TRANSFER(instance_t instance,
/* RNTI */
F1AP_FIND_PROTOCOLIE_BY_ID(F1AP_InitialULRRCMessageTransferIEs_t, ie, container,
F1AP_ProtocolIE_ID_id_C_RNTI, true);
- rnti = ie->value.choice.C_RNTI;
+ rnti_t rnti = ie->value.choice.C_RNTI;
F1AP_InitialULRRCMessageTransferIEs_t *rrccont;
F1AP_FIND_PROTOCOLIE_BY_ID(F1AP_InitialULRRCMessageTransferIEs_t, rrccont, container,
F1AP_ProtocolIE_ID_id_RRCContainer, true);
@@ -88,51 +88,22 @@ int CU_handle_INITIAL_UL_RRC_MESSAGE_TRANSFER(instance_t instance,
F1AP_FIND_PROTOCOLIE_BY_ID(F1AP_InitialULRRCMessageTransferIEs_t, du2cu, container,
F1AP_ProtocolIE_ID_id_DUtoCURRCContainer, false);
- int f1ap_uid = f1ap_add_ue(CUtype, instance, rnti);
-
- if (f1ap_uid < 0 ) {
- LOG_E(F1AP, "Failed to add UE \n");
- return -1;
- }
-
// create an ITTI message and copy SDU
- if (f1ap_req(true, instance)->cell_type==CELL_MACRO_GNB) {
- message_p = itti_alloc_new_message (TASK_CU_F1, 0, F1AP_INITIAL_UL_RRC_MESSAGE);
- f1ap_initial_ul_rrc_message_t *ul_rrc = &F1AP_INITIAL_UL_RRC_MESSAGE(message_p);
- ul_rrc->nr_cellid = nr_cellid; // CU instance
- ul_rrc->crnti = rnti;
- ul_rrc->rrc_container_length = rrccont->value.choice.RRCContainer.size;
- ul_rrc->rrc_container = malloc(ul_rrc->rrc_container_length);
- memcpy(ul_rrc->rrc_container, rrccont->value.choice.RRCContainer.buf, ul_rrc->rrc_container_length);
- AssertFatal(du2cu != NULL, "no masterCellGroup in initial UL RRC message\n");
- ul_rrc->du2cu_rrc_container_length = du2cu->value.choice.DUtoCURRCContainer.size;
- ul_rrc->du2cu_rrc_container = malloc(ul_rrc->du2cu_rrc_container_length);
- memcpy(ul_rrc->du2cu_rrc_container, du2cu->value.choice.DUtoCURRCContainer.buf, ul_rrc->du2cu_rrc_container_length);
- itti_send_msg_to_task(TASK_RRC_GNB, instance, message_p);
- } else {
- message_p = itti_alloc_new_message (TASK_CU_F1, 0, RRC_MAC_CCCH_DATA_IND);
- memset (RRC_MAC_CCCH_DATA_IND (message_p).sdu, 0, CCCH_SDU_SIZE);
- ccch_sdu_len = rrccont->value.choice.RRCContainer.size;
- memcpy(RRC_MAC_CCCH_DATA_IND (message_p).sdu, rrccont->value.choice.RRCContainer.buf,
- ccch_sdu_len);
- NR_RRC_MAC_CCCH_DATA_IND (message_p).frame = 0;
- NR_RRC_MAC_CCCH_DATA_IND (message_p).slot = 0;
- NR_RRC_MAC_CCCH_DATA_IND (message_p).sdu_size = ccch_sdu_len;
- NR_RRC_MAC_CCCH_DATA_IND (message_p).nr_cellid = nr_cellid; // CU instance
- NR_RRC_MAC_CCCH_DATA_IND (message_p).rnti = rnti;
- NR_RRC_MAC_CCCH_DATA_IND (message_p).CC_id = CC_id;
- if (du2cu) {
- NR_RRC_MAC_CCCH_DATA_IND (message_p).du_to_cu_rrc_container = malloc(sizeof(OCTET_STRING_t));
- NR_RRC_MAC_CCCH_DATA_IND (message_p).du_to_cu_rrc_container->size = du2cu->value.choice.DUtoCURRCContainer.size;
- NR_RRC_MAC_CCCH_DATA_IND (message_p).du_to_cu_rrc_container->buf = malloc(du2cu->value.choice.DUtoCURRCContainer.size);
- memcpy(NR_RRC_MAC_CCCH_DATA_IND (message_p).du_to_cu_rrc_container->buf,
- du2cu->value.choice.DUtoCURRCContainer.buf,
- du2cu->value.choice.DUtoCURRCContainer.size);
- }
- itti_send_msg_to_task (TASK_RRC_ENB, instance, message_p);
- }
+ AssertFatal(f1ap_req(true, instance)->cell_type == CELL_MACRO_GNB, "illegal cell type %d\n", f1ap_req(true, instance)->cell_type);
+ message_p = itti_alloc_new_message(TASK_CU_F1, 0, F1AP_INITIAL_UL_RRC_MESSAGE);
+ f1ap_initial_ul_rrc_message_t *ul_rrc = &F1AP_INITIAL_UL_RRC_MESSAGE(message_p);
+ ul_rrc->gNB_DU_ue_id = du_ue_id;
+ ul_rrc->nr_cellid = nr_cellid; // CU instance
+ ul_rrc->crnti = rnti;
+ ul_rrc->rrc_container_length = rrccont->value.choice.RRCContainer.size;
+ ul_rrc->rrc_container = malloc(ul_rrc->rrc_container_length);
+ memcpy(ul_rrc->rrc_container, rrccont->value.choice.RRCContainer.buf, ul_rrc->rrc_container_length);
+ AssertFatal(du2cu != NULL, "no masterCellGroup in initial UL RRC message\n");
+ ul_rrc->du2cu_rrc_container_length = du2cu->value.choice.DUtoCURRCContainer.size;
+ ul_rrc->du2cu_rrc_container = malloc(ul_rrc->du2cu_rrc_container_length);
+ memcpy(ul_rrc->du2cu_rrc_container, du2cu->value.choice.DUtoCURRCContainer.buf, ul_rrc->du2cu_rrc_container_length);
+ itti_send_msg_to_task(TASK_RRC_GNB, instance, message_p);
- //getCxt(true,ITTI_MSG_DESTINATION_ID(message_p))->f1ap_ue[f1ap_uid].du_ue_f1ap_id = du_ue_f1ap_id;
return 0;
}
@@ -161,26 +132,28 @@ int CU_send_DL_RRC_MESSAGE_TRANSFER(instance_t instance,
ie1->id = F1AP_ProtocolIE_ID_id_gNB_CU_UE_F1AP_ID;
ie1->criticality = F1AP_Criticality_reject;
ie1->value.present = F1AP_DLRRCMessageTransferIEs__value_PR_GNB_CU_UE_F1AP_ID;
- ie1->value.choice.GNB_CU_UE_F1AP_ID = f1ap_get_cu_ue_f1ap_id(CUtype, instance, f1ap_dl_rrc->rnti);
- LOG_D(F1AP, "Setting GNB_CU_UE_F1AP_ID %llu associated with UE RNTI %x (instance %ld)\n",
- (unsigned long long int)ie1->value.choice.GNB_CU_UE_F1AP_ID, f1ap_dl_rrc->rnti, instance);
+ DevAssert(f1ap_dl_rrc->gNB_CU_ue_id != 0);
+ ie1->value.choice.GNB_CU_UE_F1AP_ID = f1ap_dl_rrc->gNB_CU_ue_id;
+
/* mandatory */
/* c2. GNB_DU_UE_F1AP_ID */
asn1cSequenceAdd(out->protocolIEs.list, F1AP_DLRRCMessageTransferIEs_t, ie2);
ie2->id = F1AP_ProtocolIE_ID_id_gNB_DU_UE_F1AP_ID;
ie2->criticality = F1AP_Criticality_reject;
ie2->value.present = F1AP_DLRRCMessageTransferIEs__value_PR_GNB_DU_UE_F1AP_ID;
- ie2->value.choice.GNB_DU_UE_F1AP_ID = f1ap_get_du_ue_f1ap_id(CUtype, instance, f1ap_dl_rrc->rnti);
- LOG_D(F1AP, "GNB_DU_UE_F1AP_ID %llu associated with UE RNTI %x \n", (unsigned long long int)ie2->value.choice.GNB_DU_UE_F1AP_ID, f1ap_dl_rrc->rnti);
+ DevAssert(f1ap_dl_rrc->gNB_DU_ue_id != 0);
+ ie2->value.choice.GNB_DU_UE_F1AP_ID = f1ap_dl_rrc->gNB_DU_ue_id;
+
/* optional */
/* c3. oldgNB_DU_UE_F1AP_ID */
- /* if (f1ap_dl_rrc->old_gNB_DU_ue_id != 0xFFFFFFFF) {
- asn1cSequenceAdd(out->protocolIEs.list, F1AP_DLRRCMessageTransferIEs_t, ie3);
- ie3->id = F1AP_ProtocolIE_ID_id_oldgNB_DU_UE_F1AP_ID;
- ie3->criticality = F1AP_Criticality_reject;
- ie3->value.present = F1AP_DLRRCMessageTransferIEs__value_PR_NOTHING;
- ie3->value.choice.oldgNB_DU_UE_F1AP_ID = f1ap_dl_rrc->old_gNB_DU_ue_id;
- }*/
+ if (f1ap_dl_rrc->old_gNB_DU_ue_id != NULL) {
+ asn1cSequenceAdd(out->protocolIEs.list, F1AP_DLRRCMessageTransferIEs_t, ie3);
+ ie3->id = F1AP_ProtocolIE_ID_id_oldgNB_DU_UE_F1AP_ID;
+ ie3->criticality = F1AP_Criticality_reject;
+ ie3->value.present = F1AP_DLRRCMessageTransferIEs__value_PR_GNB_DU_UE_F1AP_ID_1;
+ ie3->value.choice.GNB_DU_UE_F1AP_ID_1 = *f1ap_dl_rrc->old_gNB_DU_ue_id;
+ }
+
/* mandatory */
/* c4. SRBID */
asn1cSequenceAdd(out->protocolIEs.list, F1AP_DLRRCMessageTransferIEs_t, ie4);
@@ -267,14 +240,19 @@ int CU_handle_UL_RRC_MESSAGE_TRANSFER(instance_t instance,
F1AP_FIND_PROTOCOLIE_BY_ID(F1AP_ULRRCMessageTransferIEs_t, ie, container,
F1AP_ProtocolIE_ID_id_gNB_CU_UE_F1AP_ID, true);
cu_ue_f1ap_id = ie->value.choice.GNB_CU_UE_F1AP_ID;
- LOG_D(F1AP, "cu_ue_f1ap_id %lu associated with RNTI %x\n",
- cu_ue_f1ap_id, f1ap_get_rnti_by_cu_id(CUtype, instance, cu_ue_f1ap_id));
/* GNB_DU_UE_F1AP_ID */
F1AP_FIND_PROTOCOLIE_BY_ID(F1AP_ULRRCMessageTransferIEs_t, ie, container,
F1AP_ProtocolIE_ID_id_gNB_DU_UE_F1AP_ID, true);
du_ue_f1ap_id = ie->value.choice.GNB_DU_UE_F1AP_ID;
- LOG_D(F1AP, "du_ue_f1ap_id %lu associated with RNTI %x\n",
- du_ue_f1ap_id, f1ap_get_rnti_by_cu_id(CUtype, instance, du_ue_f1ap_id));
+ /* the RLC-PDCP does not transport the DU UE ID (yet), so we drop it here.
+ * For the moment, let's hope this won't become relevant; to sleep in peace,
+ * let's put an assert to check that it is the expected DU UE ID. */
+ f1_ue_data_t ue_data = cu_get_f1_ue_data(cu_ue_f1ap_id);
+ AssertFatal(ue_data.secondary_ue == du_ue_f1ap_id,
+ "unexpected DU UE ID %d received, expected it to be %ld\n",
+ ue_data.secondary_ue,
+ du_ue_f1ap_id);
+
/* mandatory */
/* SRBID */
F1AP_FIND_PROTOCOLIE_BY_ID(F1AP_ULRRCMessageTransferIEs_t, ie, container,
@@ -294,7 +272,7 @@ int CU_handle_UL_RRC_MESSAGE_TRANSFER(instance_t instance,
protocol_ctxt_t ctxt={0};
ctxt.instance = instance;
ctxt.module_id = instance;
- ctxt.rntiMaybeUEid = f1ap_get_rnti_by_cu_id(CUtype, instance, cu_ue_f1ap_id);
+ ctxt.rntiMaybeUEid = cu_ue_f1ap_id;
ctxt.enb_flag = 1;
ctxt.eNB_index = 0;
mem_block_t *mb = get_free_mem_block(ie->value.choice.RRCContainer.size,__func__);
diff --git a/openair2/F1AP/f1ap_cu_ue_context_management.c b/openair2/F1AP/f1ap_cu_ue_context_management.c
index 8fdee52abb..a72a359c5b 100644
--- a/openair2/F1AP/f1ap_cu_ue_context_management.c
+++ b/openair2/F1AP/f1ap_cu_ue_context_management.c
@@ -82,7 +82,7 @@ int CU_send_UE_CONTEXT_SETUP_REQUEST(instance_t instance,
ie1->id = F1AP_ProtocolIE_ID_id_gNB_CU_UE_F1AP_ID;
ie1->criticality = F1AP_Criticality_reject;
ie1->value.present = F1AP_UEContextSetupRequestIEs__value_PR_GNB_CU_UE_F1AP_ID;
- ie1->value.choice.GNB_CU_UE_F1AP_ID = f1ap_get_cu_ue_f1ap_id(CUtype, instance, f1ap_ue_context_setup_req->rnti); //f1ap_ue_context_setup_req->gNB_CU_ue_id;
+ ie1->value.choice.GNB_CU_UE_F1AP_ID = f1ap_ue_context_setup_req->gNB_CU_ue_id;
/* optional */
/* c2. GNB_DU_UE_F1AP_ID */
@@ -91,7 +91,7 @@ int CU_send_UE_CONTEXT_SETUP_REQUEST(instance_t instance,
ie2->id = F1AP_ProtocolIE_ID_id_gNB_DU_UE_F1AP_ID;
ie2->criticality = F1AP_Criticality_ignore;
ie2->value.present = F1AP_UEContextSetupRequestIEs__value_PR_GNB_DU_UE_F1AP_ID;
- ie2->value.choice.GNB_DU_UE_F1AP_ID = f1ap_get_du_ue_f1ap_id(CUtype, instance, f1ap_ue_context_setup_req->rnti); //*f1ap_ue_context_setup_req->gNB_DU_ue_id;
+ ie2->value.choice.GNB_DU_UE_F1AP_ID = f1ap_ue_context_setup_req->gNB_DU_ue_id;
}
/* mandatory */
@@ -510,7 +510,7 @@ int CU_send_UE_CONTEXT_SETUP_REQUEST(instance_t instance,
/* Use a dummy address and teid for the outgoing GTP-U tunnel (DU) which will be updated once we get the UE context setup response from the DU */
transport_layer_addr_t addr = { .length= 32, .buffer= { 0 } };
f1ap_ue_context_setup_req->drbs_to_be_setup[i].up_ul_tnl[j].teid = newGtpuCreateTunnel(getCxt(CUtype, instance)->gtpInst,
- f1ap_ue_context_setup_req->rnti,
+ f1ap_ue_context_setup_req->gNB_CU_ue_id,
f1ap_ue_context_setup_req->drbs_to_be_setup[i].drb_id,
f1ap_ue_context_setup_req->drbs_to_be_setup[i].drb_id,
0xFFFF, // We will set the right value from DU answer
@@ -654,8 +654,6 @@ int CU_handle_UE_CONTEXT_SETUP_RESPONSE(instance_t instance,
F1AP_ProtocolIE_ID_id_gNB_DU_UE_F1AP_ID, true);
f1ap_ue_context_setup_resp->gNB_DU_ue_id = ie->value.choice.GNB_DU_UE_F1AP_ID;
LOG_D(F1AP, "f1ap_ue_context_setup_resp->gNB_DU_ue_id is: %d \n", f1ap_ue_context_setup_resp->gNB_DU_ue_id);
- f1ap_ue_context_setup_resp->rnti =
- f1ap_get_rnti_by_du_id(CUtype, instance, f1ap_ue_context_setup_resp->gNB_DU_ue_id);
// DUtoCURRCInformation
F1AP_FIND_PROTOCOLIE_BY_ID(F1AP_UEContextSetupResponseIEs_t, ie, container,
F1AP_ProtocolIE_ID_id_DUtoCURRCInformation, true);
@@ -695,7 +693,7 @@ int CU_handle_UE_CONTEXT_SETUP_RESPONSE(instance_t instance,
BIT_STRING_TO_TRANSPORT_LAYER_ADDRESS_IPv4(&dl_up_tnl0->transportLayerAddress, drb_p->up_dl_tnl[0].tl_address);
OCTET_STRING_TO_UINT32(&dl_up_tnl0->gTP_TEID, drb_p->up_dl_tnl[0].teid);
GtpuUpdateTunnelOutgoingAddressAndTeid(getCxt(CUtype, instance)->gtpInst,
- f1ap_ue_context_setup_resp->rnti,
+ f1ap_ue_context_setup_resp->gNB_DU_ue_id,
(ebi_t)drbs_setup_item_p->dRBID,
drb_p->up_dl_tnl[0].tl_address,
drb_p->up_dl_tnl[0].teid);
@@ -786,17 +784,12 @@ int CU_handle_UE_CONTEXT_RELEASE_REQUEST(instance_t instance, uint32_t assoc_id,
/* GNB_CU_UE_F1AP_ID */
F1AP_FIND_PROTOCOLIE_BY_ID(F1AP_UEContextReleaseRequestIEs_t, ie, container,
F1AP_ProtocolIE_ID_id_gNB_CU_UE_F1AP_ID, true);
- const rnti_t rnti = f1ap_get_rnti_by_cu_id(true, instance,
- ie->value.choice.GNB_CU_UE_F1AP_ID);
- req->rnti = rnti;
+ req->gNB_CU_ue_id = ie->value.choice.GNB_CU_UE_F1AP_ID;
/* GNB_DU_UE_F1AP_ID */
F1AP_FIND_PROTOCOLIE_BY_ID(F1AP_UEContextReleaseRequestIEs_t, ie, container,
F1AP_ProtocolIE_ID_id_gNB_DU_UE_F1AP_ID, true);
- const rnti_t rnti2 = f1ap_get_rnti_by_du_id(CUtype, instance,
- ie->value.choice.GNB_DU_UE_F1AP_ID);
- AssertFatal(rnti == rnti2, "RNTI obtained through DU ID (%x) is different from CU ID (%x)\n",
- rnti2, rnti);
+ req->gNB_DU_ue_id = ie->value.choice.GNB_DU_UE_F1AP_ID;
/* Cause */
F1AP_FIND_PROTOCOLIE_BY_ID(F1AP_UEContextReleaseRequestIEs_t, ie, container,
@@ -857,14 +850,14 @@ int CU_send_UE_CONTEXT_RELEASE_COMMAND(instance_t instance,
ie1->id = F1AP_ProtocolIE_ID_id_gNB_CU_UE_F1AP_ID;
ie1->criticality = F1AP_Criticality_reject;
ie1->value.present = F1AP_UEContextReleaseCommandIEs__value_PR_GNB_CU_UE_F1AP_ID;
- ie1->value.choice.GNB_CU_UE_F1AP_ID = f1ap_get_cu_ue_f1ap_id(CUtype, instance, cmd->rnti);
+ ie1->value.choice.GNB_CU_UE_F1AP_ID = cmd->gNB_CU_ue_id;
/* mandatory */
/* c2. GNB_DU_UE_F1AP_ID */
asn1cSequenceAdd(out->protocolIEs.list, F1AP_UEContextReleaseCommandIEs_t, ie2);
ie2->id = F1AP_ProtocolIE_ID_id_gNB_DU_UE_F1AP_ID;
ie2->criticality = F1AP_Criticality_reject;
ie2->value.present = F1AP_UEContextReleaseCommandIEs__value_PR_GNB_DU_UE_F1AP_ID;
- ie2->value.choice.GNB_DU_UE_F1AP_ID = f1ap_get_du_ue_f1ap_id(CUtype, instance, cmd->rnti);
+ ie2->value.choice.GNB_DU_UE_F1AP_ID = cmd->gNB_DU_ue_id;
/* mandatory */
/* c3. Cause */
asn1cSequenceAdd(out->protocolIEs.list, F1AP_UEContextReleaseCommandIEs_t, ie3);
@@ -933,19 +926,18 @@ int CU_handle_UE_CONTEXT_RELEASE_COMPLETE(instance_t instance,
F1AP_UEContextReleaseComplete_t *container;
F1AP_UEContextReleaseCompleteIEs_t *ie;
DevAssert(pdu);
+ MessageDef *msg_p = itti_alloc_new_message(TASK_DU_F1, 0, F1AP_UE_CONTEXT_RELEASE_COMPLETE);
+ f1ap_ue_context_release_complete_t *complete = &F1AP_UE_CONTEXT_RELEASE_COMPLETE(msg_p);
container = &pdu->choice.successfulOutcome->value.choice.UEContextReleaseComplete;
/* GNB_CU_UE_F1AP_ID */
F1AP_FIND_PROTOCOLIE_BY_ID(F1AP_UEContextReleaseCompleteIEs_t, ie, container,
F1AP_ProtocolIE_ID_id_gNB_CU_UE_F1AP_ID, true);
- const rnti_t rnti = f1ap_get_rnti_by_cu_id(CUtype, instance,
- ie->value.choice.GNB_CU_UE_F1AP_ID);
+ complete->gNB_CU_ue_id = ie->value.choice.GNB_CU_UE_F1AP_ID;
/* GNB_DU_UE_F1AP_ID */
F1AP_FIND_PROTOCOLIE_BY_ID(F1AP_UEContextReleaseCompleteIEs_t, ie, container,
F1AP_ProtocolIE_ID_id_gNB_DU_UE_F1AP_ID, true);
- const rnti_t rnti2 = f1ap_get_rnti_by_du_id(CUtype, instance,
- ie->value.choice.GNB_DU_UE_F1AP_ID);
- AssertFatal(rnti == rnti2, "RNTI obtained through DU ID (%x) is different from CU ID (%x)\n",
- rnti2, rnti);
+ complete->gNB_DU_ue_id = ie->value.choice.GNB_DU_UE_F1AP_ID;
+
/* Optional*/
/* CriticalityDiagnostics */
F1AP_FIND_PROTOCOLIE_BY_ID(F1AP_UEContextReleaseCompleteIEs_t, ie, container,
@@ -959,24 +951,8 @@ int CU_handle_UE_CONTEXT_RELEASE_COMPLETE(instance_t instance,
// F1AP_CriticalityDiagnostics_IE_List
}
- protocol_ctxt_t ctxt;
- PROTOCOL_CTXT_SET_BY_MODULE_ID(&ctxt, instance, GNB_FLAG_YES, rnti, 0, 0, instance);
+ itti_send_msg_to_task(TASK_RRC_GNB, instance, msg_p);
- rrc_gNB_ue_context_t *ue_context_p = rrc_gNB_get_ue_context_by_rnti(RC.nrrrc[instance], rnti);
-
- if (ue_context_p) {
- MessageDef *msg = itti_alloc_new_message(TASK_CU_F1, 0, NGAP_UE_CONTEXT_RELEASE_COMPLETE);
- NGAP_UE_CONTEXT_RELEASE_COMPLETE(msg).gNB_ue_ngap_id = ue_context_p->ue_context.gNB_ue_ngap_id;
- itti_send_msg_to_task(TASK_NGAP, instance, msg);
- rrc_gNB_remove_ue_context(RC.nrrrc[instance], ue_context_p);
- } else {
- LOG_E(F1AP, "could not find ue_context of UE RNTI %x\n", rnti);
- }
-
- nr_pdcp_remove_UE(ctxt.rntiMaybeUEid);
-
- LOG_I(F1AP, "Received UE CONTEXT RELEASE COMPLETE: Removing CU UE entry for RNTI %x\n", rnti);
- f1ap_remove_ue(CUtype, instance, rnti);
return 0;
}
@@ -1002,14 +978,14 @@ int CU_send_UE_CONTEXT_MODIFICATION_REQUEST(instance_t instance, f1ap_ue_context
ie1->id = F1AP_ProtocolIE_ID_id_gNB_CU_UE_F1AP_ID;
ie1->criticality = F1AP_Criticality_reject;
ie1->value.present = F1AP_UEContextModificationRequestIEs__value_PR_GNB_CU_UE_F1AP_ID;
- ie1->value.choice.GNB_CU_UE_F1AP_ID = f1ap_get_cu_ue_f1ap_id(CUtype, instance, f1ap_ue_context_modification_req->rnti);;
+ ie1->value.choice.GNB_CU_UE_F1AP_ID = f1ap_ue_context_modification_req->gNB_CU_ue_id;
/* mandatory */
/* c2. GNB_DU_UE_F1AP_ID */
asn1cSequenceAdd(out->protocolIEs.list, F1AP_UEContextModificationRequestIEs_t, ie2);
ie2->id = F1AP_ProtocolIE_ID_id_gNB_DU_UE_F1AP_ID;
ie2->criticality = F1AP_Criticality_reject;
ie2->value.present = F1AP_UEContextModificationRequestIEs__value_PR_GNB_DU_UE_F1AP_ID;
- ie2->value.choice.GNB_DU_UE_F1AP_ID = f1ap_get_du_ue_f1ap_id(CUtype, instance, f1ap_ue_context_modification_req->rnti);;
+ ie2->value.choice.GNB_DU_UE_F1AP_ID = f1ap_ue_context_modification_req->gNB_DU_ue_id;
/* optional */
/* c3. NRCGI */
@@ -1618,9 +1594,6 @@ int CU_handle_UE_CONTEXT_MODIFICATION_RESPONSE(instance_t instance,
LOG_D(F1AP, "f1ap_ue_context_modification_resp->gNB_DU_ue_id is: %d \n", f1ap_ue_context_modification_resp->gNB_DU_ue_id);
- f1ap_ue_context_modification_resp->rnti =
- f1ap_get_rnti_by_du_id(CUtype, instance, f1ap_ue_context_modification_resp->gNB_DU_ue_id);
-
// DUtoCURRCInformation
F1AP_FIND_PROTOCOLIE_BY_ID(F1AP_UEContextModificationResponseIEs_t, ie, container,
F1AP_ProtocolIE_ID_id_DUtoCURRCInformation, false);
@@ -1656,7 +1629,7 @@ int CU_handle_UE_CONTEXT_MODIFICATION_RESPONSE(instance_t instance,
BIT_STRING_TO_TRANSPORT_LAYER_ADDRESS_IPv4(&dl_up_tnl0->transportLayerAddress, drb_p->up_dl_tnl[0].tl_address);
OCTET_STRING_TO_UINT32(&dl_up_tnl0->gTP_TEID, drb_p->up_dl_tnl[0].teid);
GtpuUpdateTunnelOutgoingAddressAndTeid(getCxt(CUtype, instance)->gtpInst,
- f1ap_ue_context_modification_resp->rnti,
+ f1ap_ue_context_modification_resp->gNB_CU_ue_id,
(ebi_t)drbs_setupmod_item_p->dRBID,
drb_p->up_dl_tnl[0].tl_address,
drb_p->up_dl_tnl[0].teid);
diff --git a/openair2/F1AP/f1ap_du_rrc_message_transfer.c b/openair2/F1AP/f1ap_du_rrc_message_transfer.c
index 5fc8daef3f..bcb38029cd 100644
--- a/openair2/F1AP/f1ap_du_rrc_message_transfer.c
+++ b/openair2/F1AP/f1ap_du_rrc_message_transfer.c
@@ -50,6 +50,7 @@
#include "asn1_msg.h"
#include "intertask_interface.h"
#include "LAYER2/NR_MAC_gNB/mac_proto.h"
+#include
#include "openair2/LAYER2/NR_MAC_gNB/mac_rrc_dl_handler.h"
@@ -60,8 +61,6 @@ int DU_handle_DL_RRC_MESSAGE_TRANSFER(instance_t instance,
F1AP_F1AP_PDU_t *pdu) {
F1AP_DLRRCMessageTransfer_t *container;
F1AP_DLRRCMessageTransferIEs_t *ie;
- uint64_t cu_ue_f1ap_id;
- uint64_t du_ue_f1ap_id;
int executeDuplication;
//uint64_t subscriberProfileIDforRFP;
//uint64_t rAT_FrequencySelectionPriority;
@@ -70,26 +69,23 @@ int DU_handle_DL_RRC_MESSAGE_TRANSFER(instance_t instance,
/* GNB_CU_UE_F1AP_ID */
F1AP_FIND_PROTOCOLIE_BY_ID(F1AP_DLRRCMessageTransferIEs_t, ie, container,
F1AP_ProtocolIE_ID_id_gNB_CU_UE_F1AP_ID, true);
- cu_ue_f1ap_id = ie->value.choice.GNB_CU_UE_F1AP_ID;
- LOG_D(F1AP, "cu_ue_f1ap_id %lu \n", cu_ue_f1ap_id);
+ uint32_t cu_ue_f1ap_id = ie->value.choice.GNB_CU_UE_F1AP_ID;
/* GNB_DU_UE_F1AP_ID */
F1AP_FIND_PROTOCOLIE_BY_ID(F1AP_DLRRCMessageTransferIEs_t, ie, container,
F1AP_ProtocolIE_ID_id_gNB_DU_UE_F1AP_ID, true);
- du_ue_f1ap_id = ie->value.choice.GNB_DU_UE_F1AP_ID;
- LOG_D(F1AP, "du_ue_f1ap_id %lu associated with UE RNTI %x \n",
- du_ue_f1ap_id,
- f1ap_get_rnti_by_du_id(DUtype, instance, du_ue_f1ap_id)); // this should be the one transmitted via initial ul rrc message transfer
-
- if (f1ap_du_add_cu_ue_id(instance,du_ue_f1ap_id, cu_ue_f1ap_id) < 0 ) {
- LOG_E(F1AP, "Failed to find the F1AP UID \n");
- //return -1;
- }
+ uint32_t du_ue_f1ap_id = ie->value.choice.GNB_DU_UE_F1AP_ID;
/* optional */
/* oldgNB_DU_UE_F1AP_ID */
- if (0) {
- F1AP_FIND_PROTOCOLIE_BY_ID(F1AP_DLRRCMessageTransferIEs_t, ie, container,
- F1AP_ProtocolIE_ID_id_oldgNB_DU_UE_F1AP_ID, true);
+ uint32_t *old_gNB_DU_ue_id = NULL;
+ uint32_t old_gNB_DU_ue_id_stack = 0;
+ F1AP_FIND_PROTOCOLIE_BY_ID(F1AP_DLRRCMessageTransferIEs_t, ie, container,
+ F1AP_ProtocolIE_ID_id_oldgNB_DU_UE_F1AP_ID, false);
+ if (ie) {
+ /* strange: it is not named OLD_GNB_DU_UE... */
+ old_gNB_DU_ue_id_stack = ie->value.choice.GNB_DU_UE_F1AP_ID_1;
+ old_gNB_DU_ue_id = &old_gNB_DU_ue_id_stack;
+ gtpv1u_update_ue_id(getCxt(false, instance)->gtpInst, old_gNB_DU_ue_id_stack, du_ue_f1ap_id);
}
/* mandatory */
@@ -135,34 +131,24 @@ int DU_handle_DL_RRC_MESSAGE_TRANSFER(instance_t instance,
}
f1ap_dl_rrc_message_t dl_rrc = {
+ .gNB_CU_ue_id = cu_ue_f1ap_id,
+ .gNB_DU_ue_id = du_ue_f1ap_id,
+ .old_gNB_DU_ue_id = old_gNB_DU_ue_id,
.rrc_container_length = ie->value.choice.RRCContainer.size,
.rrc_container = ie->value.choice.RRCContainer.buf,
- .rnti = f1ap_get_rnti_by_du_id(DUtype, instance, du_ue_f1ap_id),
.srb_id = srb_id
};
- dl_rrc_message(instance, &dl_rrc);
+ dl_rrc_message_transfer(&dl_rrc);
return 0;
}
/* UL RRC Message Transfer */
-int DU_send_INITIAL_UL_RRC_MESSAGE_TRANSFER(instance_t instanceP,
- int CC_idP,
- int UE_id,
- rnti_t rntiP,
- const uint8_t *sduP,
- sdu_size_t sdu_lenP,
- const uint8_t *sdu2P,
- sdu_size_t sdu2_lenP) {
+int DU_send_INITIAL_UL_RRC_MESSAGE_TRANSFER(instance_t instanceP, const f1ap_initial_ul_rrc_message_t *msg)
+{
F1AP_F1AP_PDU_t pdu= {0};
F1AP_InitialULRRCMessageTransfer_t *out;
uint8_t *buffer=NULL;
uint32_t len=0;
- int f1ap_uid = f1ap_add_ue (DUtype, instanceP, rntiP);
-
- if (f1ap_uid < 0 ) {
- LOG_E(F1AP, "Failed to add UE \n");
- return -1;
- }
/* Create */
/* 0. Message Type */
@@ -178,7 +164,7 @@ int DU_send_INITIAL_UL_RRC_MESSAGE_TRANSFER(instance_t instanceP,
ie1->id = F1AP_ProtocolIE_ID_id_gNB_DU_UE_F1AP_ID;
ie1->criticality = F1AP_Criticality_reject;
ie1->value.present = F1AP_InitialULRRCMessageTransferIEs__value_PR_GNB_DU_UE_F1AP_ID;
- ie1->value.choice.GNB_DU_UE_F1AP_ID = getCxt(DUtype, instanceP)->f1ap_ue[f1ap_uid].du_ue_f1ap_id;
+ ie1->value.choice.GNB_DU_UE_F1AP_ID = msg->gNB_DU_ue_id;
/* mandatory */
/* c2. NRCGI */
asn1cSequenceAdd(out->protocolIEs.list, F1AP_InitialULRRCMessageTransferIEs_t, ie2);
@@ -193,25 +179,25 @@ int DU_send_INITIAL_UL_RRC_MESSAGE_TRANSFER(instance_t instanceP,
ie3->id = F1AP_ProtocolIE_ID_id_C_RNTI;
ie3->criticality = F1AP_Criticality_reject;
ie3->value.present = F1AP_InitialULRRCMessageTransferIEs__value_PR_C_RNTI;
- ie3->value.choice.C_RNTI=rntiP;
+ ie3->value.choice.C_RNTI = msg->crnti;
/* mandatory */
/* c4. RRCContainer */
asn1cSequenceAdd(out->protocolIEs.list, F1AP_InitialULRRCMessageTransferIEs_t, ie4);
ie4->id = F1AP_ProtocolIE_ID_id_RRCContainer;
ie4->criticality = F1AP_Criticality_reject;
ie4->value.present = F1AP_InitialULRRCMessageTransferIEs__value_PR_RRCContainer;
- OCTET_STRING_fromBuf(&ie4->value.choice.RRCContainer, (const char *)sduP, sdu_lenP);
+ OCTET_STRING_fromBuf(&ie4->value.choice.RRCContainer, (const char *)msg->rrc_container, msg->rrc_container_length);
/* optional */
/* c5. DUtoCURRCContainer */
- if (sdu2P) {
+ if (msg->du2cu_rrc_container != NULL) {
asn1cSequenceAdd(out->protocolIEs.list, F1AP_InitialULRRCMessageTransferIEs_t, ie5);
ie5->id = F1AP_ProtocolIE_ID_id_DUtoCURRCContainer;
ie5->criticality = F1AP_Criticality_reject;
ie5->value.present = F1AP_InitialULRRCMessageTransferIEs__value_PR_DUtoCURRCContainer;
OCTET_STRING_fromBuf(&ie5->value.choice.DUtoCURRCContainer,
- (const char *)sdu2P,
- sdu2_lenP);
+ (const char *)msg->du2cu_rrc_container,
+ msg->du2cu_rrc_container_length);
}
/* mandatory */
/* c6. Transaction ID (integer value) */
@@ -231,16 +217,19 @@ int DU_send_INITIAL_UL_RRC_MESSAGE_TRANSFER(instance_t instanceP,
return 0;
}
-
-int DU_send_UL_NR_RRC_MESSAGE_TRANSFER(instance_t instance,
- const f1ap_ul_rrc_message_t *msg) {
- const rnti_t rnti = msg->rnti;
+int DU_send_UL_NR_RRC_MESSAGE_TRANSFER(instance_t instance, const f1ap_ul_rrc_message_t *msg)
+{
F1AP_F1AP_PDU_t pdu= {0};
F1AP_ULRRCMessageTransfer_t *out;
uint8_t *buffer = NULL;
uint32_t len;
- LOG_D(F1AP, "[DU %ld] %s: size %d UE RNTI %x in SRB %d\n",
- instance, __func__, msg->rrc_container_length, rnti, msg->srb_id);
+ LOG_D(F1AP,
+ "[DU %ld] %s: size %d UE RNTI %x in SRB %d\n",
+ instance,
+ __func__,
+ msg->rrc_container_length,
+ msg->gNB_DU_ue_id,
+ msg->srb_id);
//for (int i = 0;i < msg->rrc_container_length; i++)
// printf("%02x ", msg->rrc_container[i]);
//printf("\n");
@@ -258,14 +247,14 @@ int DU_send_UL_NR_RRC_MESSAGE_TRANSFER(instance_t instance,
ie1->id = F1AP_ProtocolIE_ID_id_gNB_CU_UE_F1AP_ID;
ie1->criticality = F1AP_Criticality_reject;
ie1->value.present = F1AP_ULRRCMessageTransferIEs__value_PR_GNB_CU_UE_F1AP_ID;
- ie1->value.choice.GNB_CU_UE_F1AP_ID = f1ap_get_cu_ue_f1ap_id(DUtype, instance, rnti);
+ ie1->value.choice.GNB_CU_UE_F1AP_ID = msg->gNB_CU_ue_id;
/* mandatory */
/* c2. GNB_DU_UE_F1AP_ID */
asn1cSequenceAdd(out->protocolIEs.list, F1AP_ULRRCMessageTransferIEs_t, ie2);
ie2->id = F1AP_ProtocolIE_ID_id_gNB_DU_UE_F1AP_ID;
ie2->criticality = F1AP_Criticality_reject;
ie2->value.present = F1AP_ULRRCMessageTransferIEs__value_PR_GNB_DU_UE_F1AP_ID;
- ie2->value.choice.GNB_DU_UE_F1AP_ID = f1ap_get_du_ue_f1ap_id(DUtype, instance, rnti);
+ ie2->value.choice.GNB_DU_UE_F1AP_ID = msg->gNB_DU_ue_id;
/* mandatory */
/* c3. SRBID */
asn1cSequenceAdd(out->protocolIEs.list, F1AP_ULRRCMessageTransferIEs_t, ie3);
diff --git a/openair2/F1AP/f1ap_du_rrc_message_transfer.h b/openair2/F1AP/f1ap_du_rrc_message_transfer.h
index 7a0c1f8974..f784b7a0cf 100644
--- a/openair2/F1AP/f1ap_du_rrc_message_transfer.h
+++ b/openair2/F1AP/f1ap_du_rrc_message_transfer.h
@@ -43,13 +43,6 @@ int DU_handle_DL_RRC_MESSAGE_TRANSFER(instance_t instance,
int DU_send_UL_NR_RRC_MESSAGE_TRANSFER(instance_t instance, const f1ap_ul_rrc_message_t *msg);
-int DU_send_INITIAL_UL_RRC_MESSAGE_TRANSFER(instance_t instanceP,
- int CC_idP,
- int UE_id,
- rnti_t rntiP,
- const uint8_t *sduP,
- sdu_size_t sdu_lenP,
- const uint8_t *sdu2P,
- sdu_size_t sdu2_lenP);
+int DU_send_INITIAL_UL_RRC_MESSAGE_TRANSFER(instance_t instanceP, const f1ap_initial_ul_rrc_message_t *msg);
#endif /* F1AP_DU_RRC_MESSAGE_TRANSFER_H_ */
diff --git a/openair2/F1AP/f1ap_du_task.c b/openair2/F1AP/f1ap_du_task.c
index 098f957194..a7af049c2a 100644
--- a/openair2/F1AP/f1ap_du_task.c
+++ b/openair2/F1AP/f1ap_du_task.c
@@ -145,7 +145,7 @@ void *F1AP_DU_task(void *arg) {
case F1AP_INITIAL_UL_RRC_MESSAGE: // from rrc
{
f1ap_initial_ul_rrc_message_t *msgRrc = &F1AP_INITIAL_UL_RRC_MESSAGE(msg);
- DU_send_INITIAL_UL_RRC_MESSAGE_TRANSFER(0, 0, 0, msgRrc->crnti, msgRrc->rrc_container, msgRrc->rrc_container_length, msgRrc->du2cu_rrc_container, msgRrc->du2cu_rrc_container_length);
+ DU_send_INITIAL_UL_RRC_MESSAGE_TRANSFER(myInstance, msgRrc);
} break;
case F1AP_UL_RRC_MESSAGE: // to rrc
diff --git a/openair2/F1AP/f1ap_du_ue_context_management.c b/openair2/F1AP/f1ap_du_ue_context_management.c
index 05833e3fad..2430b2f870 100644
--- a/openair2/F1AP/f1ap_du_ue_context_management.c
+++ b/openair2/F1AP/f1ap_du_ue_context_management.c
@@ -77,21 +77,8 @@ int DU_handle_UE_CONTEXT_SETUP_REQUEST(instance_t instance,
/* GNB_DU_UE_F1AP_ID */
F1AP_UEContextSetupRequestIEs_t *ieDU_UE;
F1AP_FIND_PROTOCOLIE_BY_ID(F1AP_UEContextSetupRequestIEs_t, ieDU_UE, container,
- F1AP_ProtocolIE_ID_id_gNB_DU_UE_F1AP_ID, false);
-
- if (ieDU_UE) {
- f1ap_ue_context_setup_req->gNB_DU_ue_id =
- ieDU_UE->value.choice.GNB_DU_UE_F1AP_ID;
- f1ap_ue_context_setup_req->rnti =
- f1ap_get_rnti_by_du_id(DUtype, instance, f1ap_ue_context_setup_req->gNB_DU_ue_id);
- } else {
- f1ap_ue_context_setup_req->gNB_DU_ue_id = -1;
- f1ap_ue_context_setup_req->rnti =
- f1ap_get_rnti_by_cu_id(DUtype, instance, f1ap_ue_context_setup_req->gNB_CU_ue_id);
- }
-
- if(f1ap_ue_context_setup_req->rnti<0)
- LOG_E(F1AP, "Could not retrieve UE rnti based on the CU/DU UE id \n");
+ F1AP_ProtocolIE_ID_id_gNB_DU_UE_F1AP_ID, true);
+ f1ap_ue_context_setup_req->gNB_DU_ue_id = ieDU_UE->value.choice.GNB_DU_UE_F1AP_ID;
/* SpCell_ID */
F1AP_UEContextSetupRequestIEs_t *ieNet;
@@ -247,7 +234,7 @@ int DU_send_UE_CONTEXT_SETUP_RESPONSE(instance_t instance, f1ap_ue_context_setup
ie2->id = F1AP_ProtocolIE_ID_id_gNB_DU_UE_F1AP_ID;
ie2->criticality = F1AP_Criticality_reject;
ie2->value.present = F1AP_UEContextSetupResponseIEs__value_PR_GNB_DU_UE_F1AP_ID;
- ie2->value.choice.GNB_DU_UE_F1AP_ID = f1ap_get_du_ue_f1ap_id(DUtype, instance, resp->rnti);
+ ie2->value.choice.GNB_DU_UE_F1AP_ID = resp->gNB_DU_ue_id;
/* mandatory */
/* c3. DUtoCURRCInformation */
@@ -285,7 +272,8 @@ int DU_send_UE_CONTEXT_SETUP_RESPONSE(instance_t instance, f1ap_ue_context_setup
ie4->criticality = F1AP_Criticality_ignore;
ie4->value.present = F1AP_UEContextSetupResponseIEs__value_PR_C_RNTI;
//C_RNTI_TO_BIT_STRING(rntiP, &ie->value.choice.C_RNTI);
- ie4->value.choice.C_RNTI=resp->rnti;
+ ie4->value.choice.C_RNTI=0;
+ AssertFatal(false, "not implemented\n");
LOG_E(F1AP,"RNTI to code!\n");
}
@@ -586,14 +574,14 @@ int DU_send_UE_CONTEXT_RELEASE_REQUEST(instance_t instance,
ie1->id = F1AP_ProtocolIE_ID_id_gNB_CU_UE_F1AP_ID;
ie1->criticality = F1AP_Criticality_reject;
ie1->value.present = F1AP_UEContextReleaseRequestIEs__value_PR_GNB_CU_UE_F1AP_ID;
- ie1->value.choice.GNB_CU_UE_F1AP_ID = f1ap_get_cu_ue_f1ap_id(DUtype, instance, req->rnti);
+ ie1->value.choice.GNB_CU_UE_F1AP_ID = req->gNB_CU_ue_id;
/* mandatory */
/* c2. GNB_DU_UE_F1AP_ID */
asn1cSequenceAdd(out->protocolIEs.list, F1AP_UEContextReleaseRequestIEs_t, ie2);
ie2->id = F1AP_ProtocolIE_ID_id_gNB_DU_UE_F1AP_ID;
ie2->criticality = F1AP_Criticality_reject;
ie2->value.present = F1AP_UEContextReleaseRequestIEs__value_PR_GNB_DU_UE_F1AP_ID;
- ie2->value.choice.GNB_DU_UE_F1AP_ID = f1ap_get_du_ue_f1ap_id(DUtype, instance, req->rnti);
+ ie2->value.choice.GNB_DU_UE_F1AP_ID = req->gNB_DU_ue_id;
/* mandatory */
/* c3. Cause */
asn1cSequenceAdd(out->protocolIEs.list, F1AP_UEContextReleaseRequestIEs_t, ie3);
@@ -654,13 +642,11 @@ int DU_handle_UE_CONTEXT_RELEASE_COMMAND(instance_t instance, uint32_t assoc_id,
// GNB_CU_UE_F1AP_ID
F1AP_FIND_PROTOCOLIE_BY_ID(F1AP_UEContextReleaseCommandIEs_t, ie, container,
F1AP_ProtocolIE_ID_id_gNB_CU_UE_F1AP_ID, true);
- f1ap_ue_context_release_cmd->rnti = f1ap_get_rnti_by_cu_id(DUtype, instance, ie->value.choice.GNB_CU_UE_F1AP_ID);
+ f1ap_ue_context_release_cmd->gNB_CU_ue_id = ie->value.choice.GNB_CU_UE_F1AP_ID;
// GNB_DU_UE_F1AP_ID
F1AP_FIND_PROTOCOLIE_BY_ID(F1AP_UEContextReleaseCommandIEs_t, ie, container,
F1AP_ProtocolIE_ID_id_gNB_DU_UE_F1AP_ID, true);
- const rnti_t rnti = f1ap_get_rnti_by_du_id(DUtype, instance,
- ie->value.choice.GNB_DU_UE_F1AP_ID);
- AssertFatal(f1ap_ue_context_release_cmd->rnti == rnti, "RNTI obtained through DU ID (%x) is different from CU ID (%x)\n", rnti, f1ap_ue_context_release_cmd->rnti);
+ f1ap_ue_context_release_cmd->gNB_DU_ue_id = ie->value.choice.GNB_DU_UE_F1AP_ID;
// We don't need the Cause
// Optional RRC Container: if present, send to UE
@@ -721,14 +707,14 @@ int DU_send_UE_CONTEXT_RELEASE_COMPLETE(instance_t instance, f1ap_ue_context_rel
ie1->id = F1AP_ProtocolIE_ID_id_gNB_CU_UE_F1AP_ID;
ie1->criticality = F1AP_Criticality_reject;
ie1->value.present = F1AP_UEContextReleaseCompleteIEs__value_PR_GNB_CU_UE_F1AP_ID;
- ie1->value.choice.GNB_CU_UE_F1AP_ID = f1ap_get_cu_ue_f1ap_id(DUtype, instance, complete->rnti);
+ ie1->value.choice.GNB_CU_UE_F1AP_ID = complete->gNB_CU_ue_id;
/* mandatory */
/* c2. GNB_DU_UE_F1AP_ID */
asn1cSequenceAdd(out->protocolIEs.list,F1AP_UEContextReleaseCompleteIEs_t, ie2);
ie2->id = F1AP_ProtocolIE_ID_id_gNB_DU_UE_F1AP_ID;
ie2->criticality = F1AP_Criticality_reject;
ie2->value.present = F1AP_UEContextReleaseCompleteIEs__value_PR_GNB_DU_UE_F1AP_ID;
- ie2->value.choice.GNB_DU_UE_F1AP_ID = f1ap_get_du_ue_f1ap_id(DUtype, instance, complete->rnti);
+ ie2->value.choice.GNB_DU_UE_F1AP_ID = complete->gNB_DU_ue_id;
/* optional -> currently not used */
/* c3. CriticalityDiagnostics */
//if (0) {
@@ -790,7 +776,6 @@ int DU_send_UE_CONTEXT_RELEASE_COMPLETE(instance_t instance, f1ap_ue_context_rel
buffer,
len,
getCxt(false, instance)->default_sctp_stream_id);
- f1ap_remove_ue(DUtype, instance, complete->rnti);
return 0;
}
@@ -825,12 +810,6 @@ int DU_handle_UE_CONTEXT_MODIFICATION_REQUEST(instance_t instance, uint32_t asso
F1AP_FIND_PROTOCOLIE_BY_ID(F1AP_UEContextModificationRequestIEs_t, ieDU_UE, container,
F1AP_ProtocolIE_ID_id_gNB_DU_UE_F1AP_ID, true);
f1ap_ue_context_modification_req->gNB_DU_ue_id = ieDU_UE->value.choice.GNB_DU_UE_F1AP_ID;
- f1ap_ue_context_modification_req->rnti = f1ap_get_rnti_by_du_id(DUtype, instance, f1ap_ue_context_modification_req->gNB_DU_ue_id);
-
- if(f1ap_ue_context_modification_req->rnti<0)
- LOG_E(F1AP, "Could not retrieve UE rnti based on the DU UE id \n");
- else
- LOG_D(F1AP, "Retrieved rnti is: %d \n", f1ap_ue_context_modification_req->rnti);
/* SRB */
F1AP_UEContextModificationRequestIEs_t *ieSrb;
@@ -944,7 +923,7 @@ int DU_handle_UE_CONTEXT_MODIFICATION_REQUEST(instance_t instance, uint32_t asso
ieRRC->value.choice.RRCContainer.buf, ieRRC->value.choice.RRCContainer.size);
protocol_ctxt_t ctxt;
// decode RRC Container and act on the message type
- ctxt.rntiMaybeUEid = f1ap_ue_context_modification_req->rnti;
+ ctxt.rntiMaybeUEid = f1ap_ue_context_modification_req->gNB_DU_ue_id;
ctxt.instance = instance;
ctxt.module_id = instance;
ctxt.enb_flag = 1;
@@ -991,7 +970,7 @@ int DU_send_UE_CONTEXT_MODIFICATION_RESPONSE(instance_t instance, f1ap_ue_contex
ie2->id = F1AP_ProtocolIE_ID_id_gNB_DU_UE_F1AP_ID;
ie2->criticality = F1AP_Criticality_reject;
ie2->value.present = F1AP_UEContextModificationResponseIEs__value_PR_GNB_DU_UE_F1AP_ID;
- ie2->value.choice.GNB_DU_UE_F1AP_ID = f1ap_get_du_ue_f1ap_id(DUtype, instance, resp->rnti);
+ ie2->value.choice.GNB_DU_UE_F1AP_ID = resp->gNB_DU_ue_id;
/* optional */
/* c3. ResourceCoordinationTransferContainer */
@@ -1057,7 +1036,7 @@ int DU_send_UE_CONTEXT_MODIFICATION_RESPONSE(instance_t instance, f1ap_ue_contex
memcpy(tl_addr.buffer, &drb->up_ul_tnl[0].tl_address, sizeof(drb->up_ul_tnl[0].tl_address));
tl_addr.length = sizeof(drb->up_ul_tnl[0].tl_address) * 8;
drb->up_dl_tnl[j].teid = newGtpuCreateTunnel(getCxt(false, instance)->gtpInst,
- resp->rnti,
+ resp->gNB_DU_ue_id,
drb->drb_id,
drb->drb_id,
drb->up_ul_tnl[j].teid,
diff --git a/openair2/F1AP/f1ap_ids.c b/openair2/F1AP/f1ap_ids.c
new file mode 100644
index 0000000000..e467e074fd
--- /dev/null
+++ b/openair2/F1AP/f1ap_ids.c
@@ -0,0 +1,157 @@
+/*
+ * Licensed to the OpenAirInterface (OAI) Software Alliance under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The OpenAirInterface Software Alliance licenses this file to You under
+ * the OAI Public License, Version 1.1 (the "License"); you may not use this file
+ * except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.openairinterface.org/?page_id=698
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *-------------------------------------------------------------------------------
+ * For more information about the OpenAirInterface (OAI) Software Alliance:
+ * contact@openairinterface.org
+ */
+
+/* "standalone" module to store a "secondary" UE ID for each UE in DU/CU.
+ * Separate from the rest of F1, as it is also relevant for monolithic. */
+
+#include "f1ap_ids.h"
+
+#include
+#include "common/utils/hashtable/hashtable.h"
+#include "common/utils/assertions.h"
+
+
+/* we have separate versions for CU and DU, as both CU&DU might coexist in the
+ * same process */
+static hash_table_t *cu2du_ue_mapping;
+static pthread_mutex_t cu2du_mutex = PTHREAD_MUTEX_INITIALIZER;
+
+void cu_init_f1_ue_data(void)
+{
+ pthread_mutex_lock(&cu2du_mutex);
+ DevAssert(cu2du_ue_mapping == NULL);
+ cu2du_ue_mapping = hashtable_create(1319, NULL, free); // 1319 is prime, default hash func (unit), free()
+ DevAssert(cu2du_ue_mapping != NULL);
+ pthread_mutex_unlock(&cu2du_mutex);
+}
+
+bool cu_add_f1_ue_data(uint32_t ue_id, const f1_ue_data_t *data)
+{
+ pthread_mutex_lock(&cu2du_mutex);
+ DevAssert(cu2du_ue_mapping != NULL);
+ uint64_t key = ue_id;
+ if (hashtable_is_key_exists(cu2du_ue_mapping, key) == HASH_TABLE_OK) {
+ pthread_mutex_unlock(&cu2du_mutex);
+ return false;
+ }
+ f1_ue_data_t *idata = malloc(sizeof(*idata));
+ AssertFatal(idata != NULL, "cannot allocate memory\n");
+ *idata = *data;
+ hashtable_rc_t ret = hashtable_insert(cu2du_ue_mapping, key, idata);
+ pthread_mutex_unlock(&cu2du_mutex);
+ return ret == HASH_TABLE_OK;
+}
+
+bool cu_exists_f1_ue_data(uint32_t ue_id)
+{
+ pthread_mutex_lock(&cu2du_mutex);
+ DevAssert(cu2du_ue_mapping != NULL);
+ uint64_t key = ue_id;
+ hashtable_rc_t ret = hashtable_is_key_exists(cu2du_ue_mapping, key);
+ pthread_mutex_unlock(&cu2du_mutex);
+ return ret == HASH_TABLE_OK;
+}
+
+f1_ue_data_t cu_get_f1_ue_data(uint32_t ue_id)
+{
+ pthread_mutex_lock(&cu2du_mutex);
+ DevAssert(cu2du_ue_mapping != NULL);
+ uint64_t key = ue_id;
+ void *data = NULL;
+ hashtable_rc_t ret = hashtable_get(cu2du_ue_mapping, key, &data);
+ AssertFatal(ret == HASH_TABLE_OK && data != NULL, "element for ue_id %d not found\n", ue_id);
+ f1_ue_data_t ued = *(f1_ue_data_t *)data;
+ pthread_mutex_unlock(&cu2du_mutex);
+ return ued;
+}
+
+bool cu_remove_f1_ue_data(uint32_t ue_id)
+{
+ pthread_mutex_lock(&cu2du_mutex);
+ DevAssert(cu2du_ue_mapping != NULL);
+ uint64_t key = ue_id;
+ hashtable_rc_t ret = hashtable_remove(cu2du_ue_mapping, key);
+ pthread_mutex_unlock(&cu2du_mutex);
+ return ret == HASH_TABLE_OK;
+}
+
+/* DU version below */
+static hash_table_t *du2cu_ue_mapping;
+static pthread_mutex_t du2cu_mutex = PTHREAD_MUTEX_INITIALIZER;
+
+void du_init_f1_ue_data(void)
+{
+ pthread_mutex_lock(&du2cu_mutex);
+ DevAssert(du2cu_ue_mapping == NULL);
+ du2cu_ue_mapping = hashtable_create(1319, NULL, free); // 1319 is prime, default hash func (unit), free()
+ DevAssert(du2cu_ue_mapping != NULL);
+ pthread_mutex_unlock(&du2cu_mutex);
+}
+
+bool du_add_f1_ue_data(uint32_t ue_id, const f1_ue_data_t *data)
+{
+ pthread_mutex_lock(&du2cu_mutex);
+ DevAssert(du2cu_ue_mapping != NULL);
+ uint64_t key = ue_id;
+ if (hashtable_is_key_exists(du2cu_ue_mapping, key) == HASH_TABLE_OK) {
+ pthread_mutex_unlock(&du2cu_mutex);
+ return false;
+ }
+ f1_ue_data_t *idata = malloc(sizeof(*idata));
+ AssertFatal(idata != NULL, "cannot allocate memory\n");
+ *idata = *data;
+ hashtable_rc_t ret = hashtable_insert(du2cu_ue_mapping, key, idata);
+ pthread_mutex_unlock(&du2cu_mutex);
+ return ret == HASH_TABLE_OK;
+}
+
+bool du_exists_f1_ue_data(uint32_t ue_id)
+{
+ pthread_mutex_lock(&du2cu_mutex);
+ DevAssert(du2cu_ue_mapping != NULL);
+ uint64_t key = ue_id;
+ hashtable_rc_t ret = hashtable_is_key_exists(du2cu_ue_mapping, key);
+ pthread_mutex_unlock(&du2cu_mutex);
+ return ret == HASH_TABLE_OK;
+}
+
+f1_ue_data_t du_get_f1_ue_data(uint32_t ue_id)
+{
+ pthread_mutex_lock(&du2cu_mutex);
+ DevAssert(du2cu_ue_mapping != NULL);
+ uint64_t key = ue_id;
+ void *data = NULL;
+ hashtable_rc_t ret = hashtable_get(du2cu_ue_mapping, key, &data);
+ AssertFatal(ret == HASH_TABLE_OK && data != NULL, "element for ue_id %d not found\n", ue_id);
+ f1_ue_data_t ued = *(f1_ue_data_t *)data;
+ pthread_mutex_unlock(&du2cu_mutex);
+ return ued;
+}
+
+bool du_remove_f1_ue_data(uint32_t ue_id)
+{
+ pthread_mutex_lock(&du2cu_mutex);
+ DevAssert(du2cu_ue_mapping != NULL);
+ uint64_t key = ue_id;
+ hashtable_rc_t ret = hashtable_remove(du2cu_ue_mapping, key);
+ pthread_mutex_unlock(&du2cu_mutex);
+ return ret == HASH_TABLE_OK;
+}
diff --git a/openair2/F1AP/f1ap_ids.h b/openair2/F1AP/f1ap_ids.h
new file mode 100644
index 0000000000..96b146f6ba
--- /dev/null
+++ b/openair2/F1AP/f1ap_ids.h
@@ -0,0 +1,48 @@
+/*
+ * Licensed to the OpenAirInterface (OAI) Software Alliance under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The OpenAirInterface Software Alliance licenses this file to You under
+ * the OAI Public License, Version 1.1 (the "License"); you may not use this file
+ * except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.openairinterface.org/?page_id=698
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *-------------------------------------------------------------------------------
+ * For more information about the OpenAirInterface (OAI) Software Alliance:
+ * contact@openairinterface.org
+ */
+
+/* "standalone" module to store a "secondary" UE ID for each UE in DU/CU.
+ * Separate from the rest of F1, as it is also relevant for monolithic. */
+
+#ifndef F1AP_IDS_H_
+#define F1AP_IDS_H_
+
+#include
+#include
+
+typedef struct f1_ue_data_t {
+ uint32_t secondary_ue;
+ /* can be extended with F1-specific data also relevant for monolithic */
+} f1_ue_data_t;
+
+void cu_init_f1_ue_data(void);
+bool cu_add_f1_ue_data(uint32_t ue_id, const f1_ue_data_t *data);
+bool cu_exists_f1_ue_data(uint32_t ue_id);
+f1_ue_data_t cu_get_f1_ue_data(uint32_t ue_id);
+bool cu_remove_f1_ue_data(uint32_t ue_id);
+
+void du_init_f1_ue_data(void);
+bool du_add_f1_ue_data(uint32_t ue_id, const f1_ue_data_t *data);
+bool du_exists_f1_ue_data(uint32_t ue_id);
+f1_ue_data_t du_get_f1_ue_data(uint32_t ue_id);
+bool du_remove_f1_ue_data(uint32_t ue_id);
+
+#endif /* F1AP_IDS_H_ */
diff --git a/openair2/F1AP/f1ap_ids_test.c b/openair2/F1AP/f1ap_ids_test.c
new file mode 100644
index 0000000000..3007db566a
--- /dev/null
+++ b/openair2/F1AP/f1ap_ids_test.c
@@ -0,0 +1,42 @@
+/*
+ * Licensed to the OpenAirInterface (OAI) Software Alliance under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The OpenAirInterface Software Alliance licenses this file to You under
+ * the OAI Public License, Version 1.1 (the "License"); you may not use this file
+ * except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.openairinterface.org/?page_id=698
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *-------------------------------------------------------------------------------
+ * For more information about the OpenAirInterface (OAI) Software Alliance:
+ * contact@openairinterface.org
+ */
+
+#include
+#include
+#include
+#include "common/utils/assertions.h"
+#include "f1ap_ids.h"
+
+int main()
+{
+ du_init_f1_ue_data();
+ int rnti = 13;
+ f1_ue_data_t data = {.secondary_ue = 1};
+ bool ret = du_add_f1_ue_data(rnti, &data);
+ DevAssert(ret);
+ ret = du_add_f1_ue_data(rnti, &data);
+ DevAssert(!ret);
+ bool exists = du_exists_f1_ue_data(rnti);
+ DevAssert(exists);
+ f1_ue_data_t rdata = du_get_f1_ue_data(rnti);
+ DevAssert(rdata.secondary_ue == data.secondary_ue);
+ return 0;
+}
diff --git a/openair2/LAYER2/NR_MAC_UE/main_ue_nr.c b/openair2/LAYER2/NR_MAC_UE/main_ue_nr.c
index 8899be18e6..3d980dd217 100644
--- a/openair2/LAYER2/NR_MAC_UE/main_ue_nr.c
+++ b/openair2/LAYER2/NR_MAC_UE/main_ue_nr.c
@@ -79,7 +79,7 @@ NR_UE_MAC_INST_t * nr_l2_init_ue(NR_UE_RRC_INST_t* rrc_inst) {
// set up PDCP, RLC, MAC
nr_pdcp_layer_init();
- nr_pdcp_add_drbs(ENB_FLAG_NO, nr_ue_mac_inst->crnti, 0, rbconfig->drb_ToAddModList, 0, NULL, NULL, &rlc_bearer_list);
+ nr_pdcp_add_drbs(ENB_FLAG_NO, nr_ue_mac_inst->crnti, rbconfig->drb_ToAddModList, 0, NULL, NULL, &rlc_bearer_list);
nr_rlc_add_drb(nr_ue_mac_inst->crnti, rbconfig->drb_ToAddModList->list.array[0]->drb_Identity, rlc_rbconfig);
nr_ue_mac_inst->logicalChannelBearer_exist[0] = true;
diff --git a/openair2/LAYER2/NR_MAC_gNB/gNB_scheduler_RA.c b/openair2/LAYER2/NR_MAC_gNB/gNB_scheduler_RA.c
index e0c5879e9c..165251e9f4 100644
--- a/openair2/LAYER2/NR_MAC_gNB/gNB_scheduler_RA.c
+++ b/openair2/LAYER2/NR_MAC_gNB/gNB_scheduler_RA.c
@@ -2083,7 +2083,7 @@ static void nr_check_Msg4_Ack(module_id_t module_id, int CC_id, frame_t frame, s
// Pause scheduling according to:
// 3GPP TS 38.331 Section 12 Table 12.1-1: UE performance requirements for RRC procedures for UEs
- const NR_ServingCellConfig_t *servingCellConfig = UE->CellGroup ? UE->CellGroup->spCellConfig->spCellConfigDedicated : NULL;
+ const NR_ServingCellConfig_t *servingCellConfig = UE->CellGroup && UE->CellGroup->spCellConfig ? UE->CellGroup->spCellConfig->spCellConfigDedicated : NULL;
uint32_t delay_ms = servingCellConfig && servingCellConfig->downlinkBWP_ToAddModList ?
NR_RRC_SETUP_DELAY_MS + NR_RRC_BWP_SWITCHING_DELAY_MS : NR_RRC_SETUP_DELAY_MS;
diff --git a/openair2/LAYER2/NR_MAC_gNB/gNB_scheduler_primitives.c b/openair2/LAYER2/NR_MAC_gNB/gNB_scheduler_primitives.c
index 68a44fa0cf..81ea2edcb7 100644
--- a/openair2/LAYER2/NR_MAC_gNB/gNB_scheduler_primitives.c
+++ b/openair2/LAYER2/NR_MAC_gNB/gNB_scheduler_primitives.c
@@ -47,6 +47,7 @@
#include "RRC/NR/MESSAGES/asn1_msg.h"
#include "intertask_interface.h"
+#include "openair2/F1AP/f1ap_ids.h"
#include "T.h"
@@ -1992,22 +1993,7 @@ void delete_nr_ue_data(NR_UE_info_t *UE, NR_COMMON_channels_t *ccPtr, uid_alloca
destroy_nr_list(&sched_ctrl->retrans_ul_harq);
uid_linear_allocator_free(uia, UE->uid);
LOG_I(NR_MAC, "Remove NR rnti 0x%04x\n", UE->rnti);
- const rnti_t rnti = UE->rnti;
free(UE);
-
- /* clear RA process(es?) associated to the UE */
- for (int cc_id = 0; cc_id < NFAPI_CC_MAX; cc_id++) {
- for (int i = 0; i < NR_NB_RA_PROC_MAX; i++) {
- NR_COMMON_channels_t *cc = &ccPtr[cc_id];
- if (cc->ra[i].rnti == rnti) {
- LOG_D(NR_MAC, "free RA process %d for rnti %04x\n", i, rnti);
- /* is it enough? */
- cc->ra[i].cfra = false;
- cc->ra[i].rnti = 0;
- cc->ra[i].crnti = 0;
- }
- }
- }
}
@@ -2922,6 +2908,7 @@ void send_initial_ul_rrc_message(gNB_MAC_INST *mac, int rnti, const uint8_t *sdu
const f1ap_initial_ul_rrc_message_t ul_rrc_msg = {
/* TODO: add mcc, mnc, cell_id, ..., is not available at MAC yet */
+ .gNB_DU_ue_id = rnti,
.crnti = rnti,
.rrc_container = (uint8_t *) sdu,
.rrc_container_length = sdu_len,
@@ -2997,8 +2984,10 @@ void nr_mac_check_ul_failure(const gNB_MAC_INST *nrmac, int rnti, NR_UE_sched_ct
/* to trigger only once: trigger when ul_failure_timer == 1, but timer will
* stop at 0 and we wait for a UE release command from upper layers */
if (sched_ctrl->ul_failure_timer == 1) {
+ f1_ue_data_t ue_data = du_get_f1_ue_data(rnti);
f1ap_ue_context_release_complete_t complete = {
- .rnti = rnti,
+ .gNB_CU_ue_id = ue_data.secondary_ue,
+ .gNB_DU_ue_id = rnti,
.cause = F1AP_CAUSE_RADIO_NETWORK,
.cause_value = 12, // F1AP_CauseRadioNetwork_rl_failure_others
};
diff --git a/openair2/LAYER2/NR_MAC_gNB/mac_rrc_dl_handler.c b/openair2/LAYER2/NR_MAC_gNB/mac_rrc_dl_handler.c
index 582420a0b4..0a450a1198 100644
--- a/openair2/LAYER2/NR_MAC_gNB/mac_rrc_dl_handler.c
+++ b/openair2/LAYER2/NR_MAC_gNB/mac_rrc_dl_handler.c
@@ -22,6 +22,7 @@
#include "mac_rrc_dl_handler.h"
#include "mac_proto.h"
+#include "openair2/F1AP/f1ap_ids.h"
#include "openair2/LAYER2/nr_rlc/nr_rlc_oai_api.h"
#include "openair2/RRC/NR/MESSAGES/asn1_msg.h"
@@ -100,7 +101,6 @@ void ue_context_setup_request(const f1ap_ue_context_setup_t *req)
f1ap_ue_context_setup_t resp = {
.gNB_CU_ue_id = req->gNB_CU_ue_id,
.gNB_DU_ue_id = req->gNB_DU_ue_id,
- .rnti = req->rnti,
};
if (req->cu_to_du_rrc_information != NULL) {
@@ -111,11 +111,11 @@ void ue_context_setup_request(const f1ap_ue_context_setup_t *req)
NR_SCHED_LOCK(&mac->sched_lock);
- NR_UE_info_t *UE = find_nr_UE(&RC.nrmac[0]->UE_info, req->rnti);
- AssertFatal(UE != NULL, "did not find UE with RNTI %04x, but UE Context Setup Failed not implemented\n", req->rnti);
+ NR_UE_info_t *UE = find_nr_UE(&RC.nrmac[0]->UE_info, req->gNB_DU_ue_id);
+ AssertFatal(UE != NULL, "did not find UE with RNTI %04x, but UE Context Setup Failed not implemented\n", req->gNB_DU_ue_id);
if (req->srbs_to_be_setup_length > 0) {
- resp.srbs_to_be_setup_length = handle_ue_context_srbs_setup(req->rnti,
+ resp.srbs_to_be_setup_length = handle_ue_context_srbs_setup(req->gNB_DU_ue_id,
req->srbs_to_be_setup_length,
req->srbs_to_be_setup,
&resp.srbs_to_be_setup,
@@ -123,7 +123,7 @@ void ue_context_setup_request(const f1ap_ue_context_setup_t *req)
}
if (req->drbs_to_be_setup_length > 0) {
- resp.drbs_to_be_setup_length = handle_ue_context_drbs_setup(req->rnti,
+ resp.drbs_to_be_setup_length = handle_ue_context_drbs_setup(req->gNB_DU_ue_id,
req->drbs_to_be_setup_length,
req->drbs_to_be_setup,
&resp.drbs_to_be_setup,
@@ -131,7 +131,7 @@ void ue_context_setup_request(const f1ap_ue_context_setup_t *req)
}
if (req->rrc_container != NULL)
- nr_rlc_srb_recv_sdu(req->rnti, DCCH, req->rrc_container, req->rrc_container_length);
+ nr_rlc_srb_recv_sdu(req->gNB_DU_ue_id, DCCH, req->rrc_container, req->rrc_container_length);
//nr_mac_update_cellgroup()
resp.du_to_cu_rrc_information = calloc(1, sizeof(du_to_cu_rrc_information_t));
@@ -171,7 +171,6 @@ void ue_context_modification_request(const f1ap_ue_context_modif_req_t *req)
f1ap_ue_context_modif_resp_t resp = {
.gNB_CU_ue_id = req->gNB_CU_ue_id,
.gNB_DU_ue_id = req->gNB_DU_ue_id,
- .rnti = req->rnti,
};
if (req->cu_to_du_rrc_information != NULL) {
@@ -181,10 +180,10 @@ void ue_context_modification_request(const f1ap_ue_context_modif_req_t *req)
}
NR_SCHED_LOCK(&mac->sched_lock);
- NR_UE_info_t *UE = find_nr_UE(&RC.nrmac[0]->UE_info, req->rnti);
+ NR_UE_info_t *UE = find_nr_UE(&RC.nrmac[0]->UE_info, req->gNB_DU_ue_id);
if (req->srbs_to_be_setup_length > 0) {
- resp.srbs_to_be_setup_length = handle_ue_context_srbs_setup(req->rnti,
+ resp.srbs_to_be_setup_length = handle_ue_context_srbs_setup(req->gNB_DU_ue_id,
req->srbs_to_be_setup_length,
req->srbs_to_be_setup,
&resp.srbs_to_be_setup,
@@ -192,7 +191,7 @@ void ue_context_modification_request(const f1ap_ue_context_modif_req_t *req)
}
if (req->drbs_to_be_setup_length > 0) {
- resp.drbs_to_be_setup_length = handle_ue_context_drbs_setup(req->rnti,
+ resp.drbs_to_be_setup_length = handle_ue_context_drbs_setup(req->gNB_DU_ue_id,
req->drbs_to_be_setup_length,
req->drbs_to_be_setup,
&resp.drbs_to_be_setup,
@@ -200,7 +199,7 @@ void ue_context_modification_request(const f1ap_ue_context_modif_req_t *req)
}
if (req->rrc_container != NULL)
- nr_rlc_srb_recv_sdu(req->rnti, DCCH, req->rrc_container, req->rrc_container_length);
+ nr_rlc_srb_recv_sdu(req->gNB_DU_ue_id, DCCH, req->rrc_container, req->rrc_container_length);
if (req->ReconfigComplOutcome != RRCreconf_info_not_present && req->ReconfigComplOutcome != RRCreconf_success) {
LOG_E(NR_MAC,
@@ -224,7 +223,7 @@ void ue_context_modification_request(const f1ap_ue_context_modif_req_t *req)
resp.du_to_cu_rrc_information->cellGroupConfig_length = (enc_rval.encoded + 7) >> 3;
/* works? */
- nr_mac_update_cellgroup(RC.nrmac[0], req->rnti, UE->CellGroup);
+ nr_mac_update_cellgroup(RC.nrmac[0], req->gNB_DU_ue_id, UE->CellGroup);
}
NR_SCHED_UNLOCK(&mac->sched_lock);
@@ -249,32 +248,100 @@ void ue_context_release_command(const f1ap_ue_context_release_cmd_t *cmd)
/* mark UE as to be deleted after PUSCH failure */
gNB_MAC_INST *mac = RC.nrmac[0];
pthread_mutex_lock(&mac->sched_lock);
- NR_UE_info_t *UE = find_nr_UE(&mac->UE_info, cmd->rnti);
+ NR_UE_info_t *UE = find_nr_UE(&mac->UE_info, cmd->gNB_DU_ue_id);
if (UE->UE_sched_ctrl.ul_failure || cmd->rrc_container_length == 0) {
/* The UE is already not connected anymore or we have nothing to forward*/
- nr_rlc_remove_ue(cmd->rnti);
- mac_remove_nr_ue(mac, cmd->rnti);
+ nr_rlc_remove_ue(cmd->gNB_DU_ue_id);
+ mac_remove_nr_ue(mac, cmd->gNB_DU_ue_id);
} else {
/* UE is in sync: forward release message and mark to be deleted
* after UL failure */
- nr_rlc_srb_recv_sdu(cmd->rnti, cmd->srb_id, cmd->rrc_container, cmd->rrc_container_length);
+ nr_rlc_srb_recv_sdu(cmd->gNB_DU_ue_id, cmd->srb_id, cmd->rrc_container, cmd->rrc_container_length);
nr_mac_trigger_release_timer(&UE->UE_sched_ctrl, UE->current_UL_BWP.scs);
}
pthread_mutex_unlock(&mac->sched_lock);
f1ap_ue_context_release_complete_t complete = {
- .rnti = cmd->rnti,
+ .gNB_CU_ue_id = cmd->gNB_CU_ue_id,
+ .gNB_DU_ue_id = cmd->gNB_DU_ue_id,
};
mac->mac_rrc.ue_context_release_complete(&complete);
- if (cmd->rrc_container)
- free(cmd->rrc_container);
+ du_remove_f1_ue_data(cmd->gNB_DU_ue_id);
}
-int dl_rrc_message(module_id_t module_id, const f1ap_dl_rrc_message_t *dl_rrc)
+void dl_rrc_message_transfer(const f1ap_dl_rrc_message_t *dl_rrc)
{
- LOG_D(NR_MAC, "DL RRC Message Transfer with %d bytes for RNTI %04x SRB %d\n", dl_rrc->rrc_container_length, dl_rrc->rnti, dl_rrc->srb_id);
+ LOG_D(NR_MAC,
+ "DL RRC Message Transfer with %d bytes for RNTI %04x SRB %d\n",
+ dl_rrc->rrc_container_length,
+ dl_rrc->gNB_DU_ue_id,
+ dl_rrc->srb_id);
- nr_rlc_srb_recv_sdu(dl_rrc->rnti, dl_rrc->srb_id, dl_rrc->rrc_container, dl_rrc->rrc_container_length);
- return 0;
+ gNB_MAC_INST *mac = RC.nrmac[0];
+ pthread_mutex_lock(&mac->sched_lock);
+ /* check first that the scheduler knows such UE */
+ NR_UE_info_t *UE = find_nr_UE(&mac->UE_info, dl_rrc->gNB_DU_ue_id);
+ if (UE == NULL) {
+ LOG_E(MAC, "ERROR: unknown UE with RNTI %04x, ignoring DL RRC Message Transfer\n", dl_rrc->gNB_DU_ue_id);
+ pthread_mutex_unlock(&mac->sched_lock);
+ return;
+ }
+ pthread_mutex_unlock(&mac->sched_lock);
+
+ if (!du_exists_f1_ue_data(dl_rrc->gNB_DU_ue_id)) {
+ LOG_I(NR_MAC, "No CU UE ID stored for UE RNTI %04x, adding CU UE ID %d\n", dl_rrc->gNB_DU_ue_id, dl_rrc->gNB_CU_ue_id);
+ f1_ue_data_t new_ue_data = {.secondary_ue = dl_rrc->gNB_CU_ue_id};
+ du_add_f1_ue_data(dl_rrc->gNB_DU_ue_id, &new_ue_data);
+ }
+
+ if (UE->expect_reconfiguration && dl_rrc->srb_id == DCCH) {
+ /* we expected a reconfiguration, and this is on DCCH. We assume this is
+ * the reconfiguration; nr_mac_update_cellgroup() brings the config into
+ * the form expected by nr_mac_update_timers(), and we set the timer to
+ * apply the real configuration at expiration.
+ * Calling it nr_mac_update_cellgroup() is misleading, and using an
+ * intermediate buffer seems not necessary. This is for historical reasons,
+ * when we only had pointer to an RRC structure, and wanted to duplicate
+ * the contents to be applied later. The actually interesting function here
+ * is also configure_UE_BWP(), only called in nr_mac_update_timers().
+ * TODO: This should be cleaned up when the whole CellGroupConfig is
+ * handled entirely at the DU: no intermediate buffer, trigger the timer
+ * from a function (there is nr_mac_enable_ue_rrc_processing_timer(), which
+ * is called from the RRC, hence locks the scheduler, which we cannot use). */
+ LOG_I(NR_MAC, "triggering rrc_processing_timer time UE %04x\n", UE->rnti);
+ pthread_mutex_lock(&mac->sched_lock);
+ nr_mac_update_cellgroup(mac, dl_rrc->gNB_DU_ue_id, UE->reconfigCellGroup);
+ pthread_mutex_unlock(&mac->sched_lock);
+ const uint16_t sl_ahead = mac->if_inst->sl_ahead;
+ NR_SubcarrierSpacing_t scs = 1;
+ int delay = 10;
+ UE->UE_sched_ctrl.rrc_processing_timer = (delay << scs) + sl_ahead;
+ }
+
+ if (dl_rrc->old_gNB_DU_ue_id != NULL) {
+ AssertFatal(*dl_rrc->old_gNB_DU_ue_id != dl_rrc->gNB_DU_ue_id,
+ "logic bug: current and old gNB DU UE ID cannot be the same\n");
+ /* 38.401 says: "Find UE context based on old gNB-DU UE F1AP ID, replace
+ * old C-RNTI/PCI with new C-RNTI/PCI". So we delete the new contexts
+ * below, then change the C-RNTI of the old one to the new one */
+ NR_UE_info_t *oldUE = find_nr_UE(&mac->UE_info, *dl_rrc->old_gNB_DU_ue_id);
+ DevAssert(oldUE);
+ pthread_mutex_lock(&mac->sched_lock);
+ /* 38.331 5.3.7.2 says that the UE releases the spCellConfig, so we drop it
+ * from the current configuration. Also, expect the reconfiguration from
+ * the CU, so save the old UE's CellGroup for the new UE */
+ UE->CellGroup->spCellConfig = NULL;
+ nr_mac_update_cellgroup(mac, dl_rrc->gNB_DU_ue_id, UE->CellGroup);
+ UE->reconfigCellGroup = oldUE->CellGroup;
+ UE->expect_reconfiguration = true;
+ oldUE->CellGroup = NULL;
+ mac_remove_nr_ue(mac, *dl_rrc->old_gNB_DU_ue_id);
+ pthread_mutex_unlock(&mac->sched_lock);
+ nr_rlc_remove_ue(dl_rrc->gNB_DU_ue_id);
+ nr_rlc_update_rnti(*dl_rrc->old_gNB_DU_ue_id, dl_rrc->gNB_DU_ue_id);
+ }
+
+ /* the DU ue id is the RNTI */
+ nr_rlc_srb_recv_sdu(dl_rrc->gNB_DU_ue_id, dl_rrc->srb_id, dl_rrc->rrc_container, dl_rrc->rrc_container_length);
}
diff --git a/openair2/LAYER2/NR_MAC_gNB/mac_rrc_dl_handler.h b/openair2/LAYER2/NR_MAC_gNB/mac_rrc_dl_handler.h
index 808277a7f4..859e128b4a 100644
--- a/openair2/LAYER2/NR_MAC_gNB/mac_rrc_dl_handler.h
+++ b/openair2/LAYER2/NR_MAC_gNB/mac_rrc_dl_handler.h
@@ -29,6 +29,6 @@ void ue_context_setup_request(const f1ap_ue_context_setup_t *req);
void ue_context_modification_request(const f1ap_ue_context_modif_req_t *req);
void ue_context_release_command(const f1ap_ue_context_release_cmd_t *cmd);
-int dl_rrc_message(module_id_t module_id, const f1ap_dl_rrc_message_t *dl_rrc);
+void dl_rrc_message_transfer(const f1ap_dl_rrc_message_t *dl_rrc);
#endif /* MAC_RRC_DL_HANDLER_H */
diff --git a/openair2/LAYER2/NR_MAC_gNB/mac_rrc_ul_direct.c b/openair2/LAYER2/NR_MAC_gNB/mac_rrc_ul_direct.c
index 6780fad873..a024abe6af 100644
--- a/openair2/LAYER2/NR_MAC_gNB/mac_rrc_ul_direct.c
+++ b/openair2/LAYER2/NR_MAC_gNB/mac_rrc_ul_direct.c
@@ -64,7 +64,6 @@ static void ue_context_modification_response_direct(const f1ap_ue_context_modif_
f1ap_msg->gNB_CU_ue_id = resp->gNB_CU_ue_id;
f1ap_msg->gNB_DU_ue_id = resp->gNB_DU_ue_id;
- f1ap_msg->rnti = resp->rnti;
f1ap_msg->mcc = resp->mcc;
f1ap_msg->mnc = resp->mnc;
f1ap_msg->mnc_digit_length = resp->mnc_digit_length;
diff --git a/openair2/LAYER2/NR_MAC_gNB/mac_rrc_ul_f1ap.c b/openair2/LAYER2/NR_MAC_gNB/mac_rrc_ul_f1ap.c
index f122a13c34..644decc21c 100644
--- a/openair2/LAYER2/NR_MAC_gNB/mac_rrc_ul_f1ap.c
+++ b/openair2/LAYER2/NR_MAC_gNB/mac_rrc_ul_f1ap.c
@@ -106,7 +106,7 @@ static void ue_context_release_request_f1ap(const f1ap_ue_context_release_req_t*
static void ue_context_release_complete_f1ap(const f1ap_ue_context_release_complete_t *complete)
{
- newGtpuDeleteAllTunnels(0, complete->rnti);
+ newGtpuDeleteAllTunnels(0, complete->gNB_DU_ue_id);
MessageDef *msg = itti_alloc_new_message(TASK_MAC_GNB, 0, F1AP_UE_CONTEXT_RELEASE_COMPLETE);
f1ap_ue_context_release_complete_t *f1ap_msg = &F1AP_UE_CONTEXT_RELEASE_COMPLETE(msg);
diff --git a/openair2/LAYER2/NR_MAC_gNB/main.c b/openair2/LAYER2/NR_MAC_gNB/main.c
index cdba0b676b..7fd559fdcd 100644
--- a/openair2/LAYER2/NR_MAC_gNB/main.c
+++ b/openair2/LAYER2/NR_MAC_gNB/main.c
@@ -40,6 +40,7 @@
#include "nr_rlc/nr_rlc_oai_api.h"
#include "RRC/NR/MESSAGES/asn1_msg.h"
//#include "RRC/L2_INTERFACE/openair_rrc_L2_interface.h"
+#include "openair2/F1AP/f1ap_ids.h"
#include "common/ran_context.h"
#include "executables/softmodem-common.h"
@@ -283,7 +284,7 @@ void mac_top_init_gNB(ngran_node_t node_type)
* will output the packets at a local interface, which is in line with
* the noS1 mode. Hence, below, we simply hardcode ENB_FLAG_NO */
// setup PDCP, RLC
- nr_pdcp_add_drbs(ENB_FLAG_NO, 0x1234, 0, rbconfig->drb_ToAddModList, 0, NULL, NULL, &rlc_bearer_list);
+ nr_pdcp_add_drbs(ENB_FLAG_NO, 0x1234, rbconfig->drb_ToAddModList, 0, NULL, NULL, &rlc_bearer_list);
nr_rlc_add_drb(0x1234, rbconfig->drb_ToAddModList->list.array[0]->drb_Identity, rlc_rbconfig);
// free memory
@@ -301,5 +302,7 @@ void mac_top_init_gNB(ngran_node_t node_type)
memset(&nrmac->UE_info, 0, sizeof(nrmac->UE_info));
}
+ du_init_f1_ue_data();
+
srand48(0);
}
diff --git a/openair2/LAYER2/NR_MAC_gNB/nr_mac_gNB.h b/openair2/LAYER2/NR_MAC_gNB/nr_mac_gNB.h
index 4e30c74a5c..457497679a 100644
--- a/openair2/LAYER2/NR_MAC_gNB/nr_mac_gNB.h
+++ b/openair2/LAYER2/NR_MAC_gNB/nr_mac_gNB.h
@@ -46,19 +46,19 @@
#define NR_SCHED_LOCK(lock) \
do { \
int rc = pthread_mutex_lock(lock); \
- AssertFatal(rc == 0, "error while locking scheduler mutex\n"); \
+ AssertFatal(rc == 0, "error while locking scheduler mutex, pthread_mutex_lock() returned %d\n", rc); \
} while (0)
#define NR_SCHED_UNLOCK(lock) \
do { \
int rc = pthread_mutex_unlock(lock); \
- AssertFatal(rc == 0, "error while locking scheduler mutex\n"); \
+ AssertFatal(rc == 0, "error while locking scheduler mutex, pthread_mutex_unlock() returned %d\n", rc); \
} while (0)
#define NR_SCHED_ENSURE_LOCKED(lock)\
do {\
int rc = pthread_mutex_trylock(lock); \
- AssertFatal(rc == EBUSY, "this function should be called with the scheduler mutex locked\n");\
+ AssertFatal(rc == EBUSY, "this function should be called with the scheduler mutex locked, pthread_mutex_trylock() returned %d\n", rc);\
} while (0)
/* Commmon */
@@ -675,7 +675,11 @@ typedef struct {
NR_UE_DL_BWP_t current_DL_BWP;
NR_UE_UL_BWP_t current_UL_BWP;
NR_mac_stats_t mac_stats;
+ /// currently active CellGroupConfig
NR_CellGroupConfig_t *CellGroup;
+ /// CellGroupConfig that is to be activated after the next reconfiguration
+ NR_CellGroupConfig_t *reconfigCellGroup;
+ bool expect_reconfiguration;
char cg_buf[32768]; /* arbitrary size */
asn_enc_rval_t enc_rval;
// UE selected beam index
diff --git a/openair2/LAYER2/nr_pdcp/nr_pdcp_e1_api.c b/openair2/LAYER2/nr_pdcp/nr_pdcp_e1_api.c
index d56c22f609..97370c5964 100644
--- a/openair2/LAYER2/nr_pdcp/nr_pdcp_e1_api.c
+++ b/openair2/LAYER2/nr_pdcp/nr_pdcp_e1_api.c
@@ -32,7 +32,7 @@ void e1_add_drb(int is_gnb,
unsigned char *ciphering_key,
unsigned char *integrity_key)
{
- add_drb_am(is_gnb, ue_id, 0, s, ciphering_algorithm, integrity_algorithm,
+ add_drb_am(is_gnb, ue_id, s, ciphering_algorithm, integrity_algorithm,
ciphering_key, integrity_key);
LOG_I(PDCP, "%s:%s:%d: added DRB for UE ID %ld\n", __FILE__, __FUNCTION__, __LINE__, ue_id);
}
diff --git a/openair2/LAYER2/nr_pdcp/nr_pdcp_e1_api.h b/openair2/LAYER2/nr_pdcp/nr_pdcp_e1_api.h
index f45f3f0458..3c16996126 100644
--- a/openair2/LAYER2/nr_pdcp/nr_pdcp_e1_api.h
+++ b/openair2/LAYER2/nr_pdcp/nr_pdcp_e1_api.h
@@ -45,7 +45,7 @@ void nr_pdcp_e1_add_drbs(eNB_flag_t enb_flag,
uint8_t *const kUPenc,
uint8_t *const kUPint);
-void add_drb_am(int is_gnb, ue_id_t rntiMaybeUEid, ue_id_t reestablish_ue_id, struct NR_DRB_ToAddMod *s,
+void add_drb_am(int is_gnb, ue_id_t rntiMaybeUEid, struct NR_DRB_ToAddMod *s,
int ciphering_algorithm,
int integrity_algorithm,
unsigned char *ciphering_key,
diff --git a/openair2/LAYER2/nr_pdcp/nr_pdcp_oai_api.c b/openair2/LAYER2/nr_pdcp/nr_pdcp_oai_api.c
index 7a798d7b81..be22753026 100644
--- a/openair2/LAYER2/nr_pdcp/nr_pdcp_oai_api.c
+++ b/openair2/LAYER2/nr_pdcp/nr_pdcp_oai_api.c
@@ -36,6 +36,7 @@
#include "oai_asn1.h"
#include "nr_pdcp_oai_api.h"
#include "LAYER2/nr_rlc/nr_rlc_oai_api.h"
+#include "openair2/F1AP/f1ap_ids.h"
#include
#include "openair2/SDAP/nr_sdap/nr_sdap.h"
#include "nr_pdcp_e1_api.h"
@@ -632,7 +633,9 @@ static void deliver_sdu_drb(void *_ue, nr_pdcp_entity_t *entity,
if (IS_SOFTMODEM_NOS1 || UE_NAS_USE_TUN) {
LOG_D(PDCP, "IP packet received with size %d, to be sent to SDAP interface, UE ID/RNTI: %ld\n", size, ue->rntiMaybeUEid);
- sdap_data_ind(entity->rb_id, entity->is_gnb, entity->has_sdap_rx, entity->pdusession_id, ue->rntiMaybeUEid, buf, size);
+ // in NoS1 mode: the SDAP should write() packets to an FD (TUN interface),
+ // so below, set is_gnb == 0 to do that
+ sdap_data_ind(entity->rb_id, 0, entity->has_sdap_rx, entity->pdusession_id, ue->rntiMaybeUEid, buf, size);
}
else{
for (i = 0; i < MAX_DRBS_PER_UE; i++) {
@@ -653,11 +656,24 @@ static void deliver_sdu_drb(void *_ue, nr_pdcp_entity_t *entity,
}
}
-static void deliver_pdu_drb(void *deliver_pdu_data, ue_id_t ue_id, int rb_id,
- char *buf, int size, int sdu_id)
+static void deliver_pdu_drb_ue(void *deliver_pdu_data, ue_id_t ue_id, int rb_id,
+ char *buf, int size, int sdu_id)
{
DevAssert(deliver_pdu_data == NULL);
- protocol_ctxt_t ctxt = { .enb_flag = 1, .rntiMaybeUEid = ue_id };
+ protocol_ctxt_t ctxt = { .enb_flag = 0, .rntiMaybeUEid = ue_id };
+
+ mem_block_t *memblock = get_free_mem_block(size, __FUNCTION__);
+ memcpy(memblock->data, buf, size);
+ LOG_D(PDCP, "%s(): (drb %d) calling rlc_data_req size %d UE %ld/%04lx\n", __func__, rb_id, size, ctxt.rntiMaybeUEid, ctxt.rntiMaybeUEid);
+ enqueue_rlc_data_req(&ctxt, 0, MBMS_FLAG_NO, rb_id, sdu_id, 0, size, memblock);
+}
+
+static void deliver_pdu_drb_gnb(void *deliver_pdu_data, ue_id_t ue_id, int rb_id,
+ char *buf, int size, int sdu_id)
+{
+ DevAssert(deliver_pdu_data == NULL);
+ f1_ue_data_t ue_data = cu_get_f1_ue_data(ue_id);
+ protocol_ctxt_t ctxt = { .enb_flag = 1, .rntiMaybeUEid = ue_data.secondary_ue };
if (NODE_IS_CU(node_type)) {
MessageDef *message_p = itti_alloc_new_message_sized(TASK_PDCP_ENB, 0,
@@ -668,12 +684,11 @@ static void deliver_pdu_drb(void *deliver_pdu_data, ue_id_t ue_id, int rb_id,
AssertFatal(message_p != NULL, "OUT OF MEMORY");
gtpv1u_tunnel_data_req_t *req=>PV1U_TUNNEL_DATA_REQ(message_p);
uint8_t *gtpu_buffer_p = (uint8_t*)(req+1);
- memcpy(gtpu_buffer_p+GTPU_HEADER_OVERHEAD_MAX,
- buf, size);
+ memcpy(gtpu_buffer_p + GTPU_HEADER_OVERHEAD_MAX, buf, size);
req->buffer = gtpu_buffer_p;
req->length = size;
req->offset = GTPU_HEADER_OVERHEAD_MAX;
- req->ue_id = ue_id;
+ req->ue_id = ue_id; // use CU UE ID as GTP will use that to look up TEID
req->bearer_id = rb_id;
LOG_D(PDCP, "%s() (drb %d) sending message to gtp size %d\n", __func__, rb_id, size);
extern instance_t CUuniqInstance;
@@ -682,8 +697,6 @@ static void deliver_pdu_drb(void *deliver_pdu_data, ue_id_t ue_id, int rb_id,
mem_block_t *memblock = get_free_mem_block(size, __FUNCTION__);
memcpy(memblock->data, buf, size);
LOG_D(PDCP, "%s(): (drb %d) calling rlc_data_req size %d\n", __func__, rb_id, size);
- //for (i = 0; i < size; i++) printf(" %2.2x", (unsigned char)memblock->data[i]);
- //printf("\n");
enqueue_rlc_data_req(&ctxt, 0, MBMS_FLAG_NO, rb_id, sdu_id, 0, size, memblock);
}
}
@@ -710,7 +723,11 @@ srb_found:
MessageDef *message_p = itti_alloc_new_message(TASK_PDCP_GNB, 0, F1AP_UL_RRC_MESSAGE);
AssertFatal(message_p != NULL, "OUT OF MEMORY\n");
f1ap_ul_rrc_message_t *ul_rrc = &F1AP_UL_RRC_MESSAGE(message_p);
- ul_rrc->rnti = ue->rntiMaybeUEid;
+ ul_rrc->gNB_CU_ue_id = ue->rntiMaybeUEid;
+ /* look up the correct secondary UE ID to provide complete information to
+ * RRC, the RLC-PDCP interface does not transport this information */
+ f1_ue_data_t ue_data = cu_get_f1_ue_data(ue->rntiMaybeUEid);
+ ul_rrc->gNB_DU_ue_id = ue_data.secondary_ue;
ul_rrc->srb_id = srb_id;
ul_rrc->rrc_container = malloc(size);
AssertFatal(ul_rrc->rrc_container != NULL, "OUT OF MEMORY\n");
@@ -740,19 +757,6 @@ void deliver_pdu_srb_rlc(void *deliver_pdu_data, ue_id_t ue_id, int srb_id,
enqueue_rlc_data_req(&ctxt, 1, MBMS_FLAG_NO, srb_id, sdu_id, 0, size, memblock);
}
-void deliver_pdu_srb_f1(void *deliver_pdu_data, ue_id_t ue_id, int srb_id,
- char *buf, int size, int sdu_id)
-{
- DevAssert(deliver_pdu_data != NULL);
- gNB_RRC_INST *rrc = deliver_pdu_data;
- f1ap_dl_rrc_message_t dl_rrc = {.old_gNB_DU_ue_id = 0xFFFFFF,
- .rrc_container = (uint8_t *)buf,
- .rrc_container_length = size,
- .rnti = ue_id,
- .srb_id = srb_id};
- rrc->mac_rrc.dl_rrc_message_transfer(0, &dl_rrc);
-}
-
static void add_srb(int is_gnb, ue_id_t rntiMaybeUEid, struct NR_SRB_ToAddMod *s, int ciphering_algorithm, int integrity_algorithm, unsigned char *ciphering_key, unsigned char *integrity_key)
{
nr_pdcp_entity_t *pdcp_srb;
@@ -784,7 +788,7 @@ static void add_srb(int is_gnb, ue_id_t rntiMaybeUEid, struct NR_SRB_ToAddMod *s
nr_pdcp_manager_unlock(nr_pdcp_ue_manager);
}
-void add_drb_am(int is_gnb, ue_id_t rntiMaybeUEid, ue_id_t reestablish_ue_id, struct NR_DRB_ToAddMod *s, int ciphering_algorithm, int integrity_algorithm, unsigned char *ciphering_key, unsigned char *integrity_key)
+void add_drb_am(int is_gnb, ue_id_t rntiMaybeUEid, struct NR_DRB_ToAddMod *s, int ciphering_algorithm, int integrity_algorithm, unsigned char *ciphering_key, unsigned char *integrity_key)
{
nr_pdcp_entity_t *pdcp_drb;
nr_pdcp_ue_t *ue;
@@ -860,8 +864,10 @@ void add_drb_am(int is_gnb, ue_id_t rntiMaybeUEid, ue_id_t reestablish_ue_id, st
LOG_W(PDCP, "%s:%d:%s: warning DRB %d already exist for UE ID/RNTI %ld, do nothing\n", __FILE__, __LINE__, __FUNCTION__, drb_id, rntiMaybeUEid);
} else {
pdcp_drb = new_nr_pdcp_entity(NR_PDCP_DRB_AM, is_gnb, drb_id, pdusession_id,
- has_sdap_rx, has_sdap_tx,
- deliver_sdu_drb, ue, deliver_pdu_drb, ue,
+ has_sdap_rx, has_sdap_tx, deliver_sdu_drb, ue,
+ is_gnb ?
+ deliver_pdu_drb_gnb : deliver_pdu_drb_ue,
+ ue,
sn_size_dl, t_reordering, discard_timer,
has_ciphering ? ciphering_algorithm : 0,
has_integrity ? integrity_algorithm : 0,
@@ -869,14 +875,6 @@ void add_drb_am(int is_gnb, ue_id_t rntiMaybeUEid, ue_id_t reestablish_ue_id, st
has_integrity ? integrity_key : NULL);
nr_pdcp_ue_add_drb_pdcp_entity(ue, drb_id, pdcp_drb);
- if (reestablish_ue_id > 0) {
- nr_pdcp_ue_t *reestablish_ue = nr_pdcp_manager_get_ue(nr_pdcp_ue_manager, reestablish_ue_id);
- if (reestablish_ue != NULL) {
- pdcp_drb->tx_next = reestablish_ue->drb[drb_id - 1]->tx_next;
- LOG_I(PDCP, "Applying tx_next %d in DRB %d from old UEid %lx to new UEid %lx\n", reestablish_ue->drb[drb_id - 1]->tx_next, drb_id, reestablish_ue_id, rntiMaybeUEid);
- }
- }
-
LOG_D(PDCP, "%s:%d:%s: added drb %d to UE ID/RNTI %ld\n", __FILE__, __LINE__, __FUNCTION__, drb_id, rntiMaybeUEid);
new_nr_sdap_entity(is_gnb, has_sdap_rx, has_sdap_tx, rntiMaybeUEid, pdusession_id, is_sdap_DefaultDRB, drb_id, mappedQFIs2Add, mappedQFIs2AddCount);
@@ -886,7 +884,6 @@ void add_drb_am(int is_gnb, ue_id_t rntiMaybeUEid, ue_id_t reestablish_ue_id, st
static void add_drb(int is_gnb,
ue_id_t rntiMaybeUEid,
- ue_id_t reestablish_ue_id,
struct NR_DRB_ToAddMod *s,
NR_RLC_Config_t *rlc_Config,
int ciphering_algorithm,
@@ -896,12 +893,12 @@ static void add_drb(int is_gnb,
{
switch (rlc_Config->present) {
case NR_RLC_Config_PR_am:
- add_drb_am(is_gnb, rntiMaybeUEid, reestablish_ue_id, s, ciphering_algorithm, integrity_algorithm, ciphering_key, integrity_key);
+ add_drb_am(is_gnb, rntiMaybeUEid, s, ciphering_algorithm, integrity_algorithm, ciphering_key, integrity_key);
break;
case NR_RLC_Config_PR_um_Bi_Directional:
// add_drb_um(rntiMaybeUEid, s);
/* hack */
- add_drb_am(is_gnb, rntiMaybeUEid, reestablish_ue_id, s, ciphering_algorithm, integrity_algorithm, ciphering_key, integrity_key);
+ add_drb_am(is_gnb, rntiMaybeUEid, s, ciphering_algorithm, integrity_algorithm, ciphering_key, integrity_key);
break;
default:
LOG_E(PDCP, "%s:%d:%s: fatal: unhandled DRB type\n",
@@ -923,7 +920,6 @@ void nr_pdcp_add_srbs(eNB_flag_t enb_flag, ue_id_t rntiMaybeUEid, NR_SRB_ToAddMo
void nr_pdcp_add_drbs(eNB_flag_t enb_flag,
ue_id_t rntiMaybeUEid,
- ue_id_t reestablish_ue_id,
NR_DRB_ToAddModList_t *const drb2add_list,
const uint8_t security_modeP,
uint8_t *const kUPenc,
@@ -932,7 +928,7 @@ void nr_pdcp_add_drbs(eNB_flag_t enb_flag,
{
if (drb2add_list != NULL) {
for (int i = 0; i < drb2add_list->list.count; i++) {
- add_drb(enb_flag, rntiMaybeUEid, reestablish_ue_id, drb2add_list->list.array[i], rlc_bearer2add_list->list.array[i]->rlc_Config, security_modeP & 0x0f, (security_modeP >> 4) & 0x0f, kUPenc, kUPint);
+ add_drb(enb_flag, rntiMaybeUEid, drb2add_list->list.array[i], rlc_bearer2add_list->list.array[i]->rlc_Config, security_modeP & 0x0f, (security_modeP >> 4) & 0x0f, kUPenc, kUPint);
}
} else
LOG_W(PDCP, "nr_pdcp_add_drbs() with void list\n");
@@ -1065,6 +1061,39 @@ bool nr_pdcp_data_req_srb(ue_id_t ue_id,
return 1;
}
+void nr_pdcp_reestablishment(ue_id_t ue_id)
+{
+ // TODO implement this on a per RB basis following TS 38.323 Sec 5.1.2
+ nr_pdcp_manager_lock(nr_pdcp_ue_manager);
+ nr_pdcp_ue_t *ue = nr_pdcp_manager_get_ue(nr_pdcp_ue_manager, ue_id);
+ if (ue == NULL) {
+ LOG_E(PDCP, "Cannot find PDCP entity for UE %lx\n", ue_id);
+ nr_pdcp_manager_unlock(nr_pdcp_ue_manager);
+ return;
+ }
+
+ for (int i = 0; i < 3; i++) {
+ nr_pdcp_entity_t *srb = ue->srb[i];
+ if (srb != NULL) {
+ srb->tx_next = 0;
+ srb->rx_next = 0;
+ srb->rx_deliv = 0;
+ srb->rx_reord = 0;
+ }
+ }
+
+ for (int i = 0; i < MAX_DRBS_PER_UE; i++) {
+ nr_pdcp_entity_t *drb = ue->drb[i];
+ if (drb != NULL) {
+ // drb->tx_next = 0; // Should continue from the previous value
+ drb->rx_next = 0;
+ //drb->rx_deliv = 0; // should continue from the previous value
+ drb->rx_reord = 0;
+ }
+ }
+ nr_pdcp_manager_unlock(nr_pdcp_ue_manager);
+}
+
bool nr_pdcp_data_req_drb(protocol_ctxt_t *ctxt_pP,
const srb_flag_t srb_flagP,
const rb_id_t rb_id,
diff --git a/openair2/LAYER2/nr_pdcp/nr_pdcp_oai_api.h b/openair2/LAYER2/nr_pdcp/nr_pdcp_oai_api.h
index 0fd23d2f6b..f00ab98422 100644
--- a/openair2/LAYER2/nr_pdcp/nr_pdcp_oai_api.h
+++ b/openair2/LAYER2/nr_pdcp/nr_pdcp_oai_api.h
@@ -48,7 +48,6 @@ bool pdcp_data_ind(const protocol_ctxt_t *const ctxt_pP,
void nr_pdcp_add_drbs(eNB_flag_t enb_flag,
ue_id_t rntiMaybeUEid,
- ue_id_t reestablish_ue_id,
NR_DRB_ToAddModList_t *const drb2add_list,
const uint8_t security_modeP,
uint8_t *const kUPenc,
@@ -58,6 +57,7 @@ void nr_pdcp_add_drbs(eNB_flag_t enb_flag,
void nr_DRB_preconfiguration(ue_id_t crntiMaybeUEid);
bool nr_pdcp_remove_UE(ue_id_t ue_id);
+void nr_pdcp_reestablishment(ue_id_t ue_id);
void nr_pdcp_config_set_security(ue_id_t ue_id,
const rb_id_t rb_id,
@@ -80,10 +80,7 @@ bool cu_f1u_data_req(protocol_ctxt_t *ctxt_pP,
typedef void (*deliver_pdu)(void *data, ue_id_t ue_id, int srb_id,
char *buf, int size, int sdu_id);
/* default implementation of deliver_pdu */
-void deliver_pdu_srb_rlc(void *data, ue_id_t ue_id, int srb_id, char *buf,
- int size, int sdu_id);
-void deliver_pdu_srb_f1(void *data, ue_id_t ue_id, int srb_id, char *buf,
- int size, int sdu_id);
+void deliver_pdu_srb_rlc(void *data, ue_id_t ue_id, int srb_id, char *buf, int size, int sdu_id);
bool nr_pdcp_data_req_srb(ue_id_t ue_id,
const rb_id_t rb_id,
const mui_t muiP,
diff --git a/openair2/LAYER2/nr_rlc/nr_rlc_oai_api.c b/openair2/LAYER2/nr_rlc/nr_rlc_oai_api.c
index f4097d721b..7d17829e4f 100644
--- a/openair2/LAYER2/nr_rlc/nr_rlc_oai_api.c
+++ b/openair2/LAYER2/nr_rlc/nr_rlc_oai_api.c
@@ -39,6 +39,7 @@
#include "NR_UL-CCCH-Message.h"
#include "openair2/F1AP/f1ap_du_rrc_message_transfer.h"
+#include "openair2/F1AP/f1ap_ids.h"
extern RAN_CONTEXT_t RC;
@@ -425,11 +426,18 @@ rb_found:
ctx.eNB_index = 0;
ctx.brOption = 0;
+ is_enb = nr_rlc_manager_get_enb_flag(nr_rlc_ue_manager);
+
/* used fields? */
ctx.module_id = 0;
+ /* CU (PDCP, RRC, SDAP) use a different ID than RNTI, so below set the CU UE
+ * ID if in gNB, else use RNTI normally */
ctx.rntiMaybeUEid = ue->rnti;
+ if (is_enb) {
+ f1_ue_data_t ue_data = du_get_f1_ue_data(ue->rnti);
+ ctx.rntiMaybeUEid = ue_data.secondary_ue;
+ }
- is_enb = nr_rlc_manager_get_enb_flag(nr_rlc_ue_manager);
ctx.enb_flag = is_enb;
if (is_enb) {
@@ -453,7 +461,8 @@ rb_found:
msg = itti_alloc_new_message(TASK_RLC_ENB, 0, F1AP_UL_RRC_MESSAGE);
uint8_t *message_buffer = itti_malloc (TASK_RLC_ENB, TASK_DU_F1, size);
memcpy (message_buffer, buf, size);
- F1AP_UL_RRC_MESSAGE(msg).rnti = ue->rnti;
+ F1AP_UL_RRC_MESSAGE(msg).gNB_CU_ue_id = ctx.rntiMaybeUEid;
+ F1AP_UL_RRC_MESSAGE(msg).gNB_DU_ue_id = ue->rnti;
F1AP_UL_RRC_MESSAGE(msg).srb_id = rb_id;
F1AP_UL_RRC_MESSAGE(msg).rrc_container = message_buffer;
F1AP_UL_RRC_MESSAGE(msg).rrc_container_length = size;
@@ -467,7 +476,7 @@ rb_found:
memcpy(req->buffer,buf,size);
req->length=size;
req->offset=0;
- req->ue_id=ue->rnti;
+ req->ue_id=ue->rnti; // use RNTI here, which GTP will use to look up TEID
req->bearer_id=rb_id;
LOG_D(RLC, "Received uplink user-plane traffic at RLC-DU to be sent to the CU, size %d \n", size);
extern instance_t DUuniqInstance;
@@ -477,6 +486,7 @@ rb_found:
}
}
+ /* UE or monolithic gNB */
memblock = get_free_mem_block(size, __func__);
if (memblock == NULL) {
LOG_E(RLC, "%s:%d:%s: ERROR: get_free_mem_block failed\n", __FILE__, __LINE__, __FUNCTION__);
@@ -1000,6 +1010,45 @@ rlc_op_status_t rrc_rlc_remove_ue (const protocol_ctxt_t* const x)
return RLC_OP_STATUS_OK;
}
+bool nr_rlc_update_rnti(int from_rnti, int to_rnti)
+{
+ nr_rlc_manager_lock(nr_rlc_ue_manager);
+ nr_rlc_ue_t *ue = nr_rlc_manager_get_ue(nr_rlc_ue_manager, from_rnti);
+ if (ue == NULL) {
+ nr_rlc_manager_unlock(nr_rlc_ue_manager);
+ LOG_E(RLC, "Cannot find RLC entity for UE %04x\n", from_rnti);
+ return false;
+ }
+ ue->rnti = to_rnti;
+ LOG_I(RLC, "Update old UE RNTI %04x context to RNTI %04x\n", from_rnti, to_rnti);
+ for (int i = 0; i < sizeof(ue->srb) / sizeof(ue->srb[0]); ++i)
+ if (ue->srb[i])
+ ue->srb[i]->reestablishment(ue->srb[i]);
+ for (int i = 0; i < sizeof(ue->drb) / sizeof(ue->drb[0]); ++i)
+ if (ue->drb[i])
+ ue->drb[i]->reestablishment(ue->drb[i]);
+ nr_rlc_manager_unlock(nr_rlc_ue_manager);
+ return true;
+}
+
+/* This function is for testing purposes. At least on a COTS UE, it will
+ * trigger a reestablishment. */
+void nr_rlc_test_trigger_reestablishment(int rnti)
+{
+ nr_rlc_manager_lock(nr_rlc_ue_manager);
+ nr_rlc_ue_t *ue = nr_rlc_manager_get_ue(nr_rlc_ue_manager, rnti);
+ if (ue == NULL) {
+ nr_rlc_manager_unlock(nr_rlc_ue_manager);
+ LOG_E(RLC, "Cannot find RLC entity for UE %04x\n", rnti);
+ return;
+ }
+ /* we simply assume the SRB exists, because the scheduler creates it as soon
+ * as the UE context is created. */
+ nr_rlc_entity_t *ent = ue->srb[0];
+ ent->reestablishment(ent);
+ nr_rlc_manager_unlock(nr_rlc_ue_manager);
+}
+
void nr_rlc_tick(int frame, int subframe)
{
if (frame != nr_rlc_current_time_last_frame ||
diff --git a/openair2/LAYER2/nr_rlc/nr_rlc_oai_api.h b/openair2/LAYER2/nr_rlc/nr_rlc_oai_api.h
index 3b4bce7176..15fe286435 100644
--- a/openair2/LAYER2/nr_rlc/nr_rlc_oai_api.h
+++ b/openair2/LAYER2/nr_rlc/nr_rlc_oai_api.h
@@ -43,6 +43,10 @@ void nr_rlc_add_srb(int rnti, int srb_id, const NR_RLC_BearerConfig_t *rlc_Beare
void nr_rlc_add_drb(int rnti, int drb_id, const NR_RLC_BearerConfig_t *rlc_BearerConfig);
void nr_rlc_remove_ue(int rnti);
+bool nr_rlc_update_rnti(int from_rnti, int to_rnti);
+
+/* test function for CI to trigger reestablishments */
+void nr_rlc_test_trigger_reestablishment(int rnti);
int nr_rlc_get_available_tx_space(
const rnti_t rntiP,
diff --git a/openair2/RRC/NR/L2_nr_interface.c b/openair2/RRC/NR/L2_nr_interface.c
index 0f524a0241..3334842616 100644
--- a/openair2/RRC/NR/L2_nr_interface.c
+++ b/openair2/RRC/NR/L2_nr_interface.c
@@ -52,16 +52,6 @@
extern RAN_CONTEXT_t RC;
-void nr_rrc_mac_remove_ue(rnti_t rntiMaybeUEid)
-{
- nr_rlc_remove_ue(rntiMaybeUEid);
-
- gNB_MAC_INST *nrmac = RC.nrmac[0];
- NR_SCHED_LOCK(&nrmac->sched_lock);
- mac_remove_nr_ue(nrmac, rntiMaybeUEid);
- NR_SCHED_UNLOCK(&nrmac->sched_lock);
-}
-
void nr_rrc_mac_update_cellgroup(rnti_t rntiMaybeUEid, NR_CellGroupConfig_t *cgc)
{
gNB_MAC_INST *nrmac = RC.nrmac[0];
diff --git a/openair2/RRC/NR/MESSAGES/asn1_msg.c b/openair2/RRC/NR/MESSAGES/asn1_msg.c
index 75446708a9..3935c18bfe 100644
--- a/openair2/RRC/NR/MESSAGES/asn1_msg.c
+++ b/openair2/RRC/NR/MESSAGES/asn1_msg.c
@@ -783,7 +783,7 @@ int16_t do_RRCReconfiguration(
}
if(cellGroupConfig!=NULL){
- update_cellGroupConfig(cellGroupConfig, ue_context_pP->ue_context.gNB_ue_ngap_id, ue_context_pP ? ue_context_pP->ue_context.UE_Capability_nr : NULL, configuration);
+ update_cellGroupConfig(cellGroupConfig, ue_context_pP->ue_context.rrc_ue_id, ue_context_pP ? ue_context_pP->ue_context.UE_Capability_nr : NULL, configuration);
enc_rval = uper_encode_to_buffer(&asn_DEF_NR_CellGroupConfig,
NULL,
@@ -1100,8 +1100,7 @@ uint8_t do_RRCReestablishmentRequest(uint8_t Mod_id, uint8_t *buffer, uint16_t c
}
//------------------------------------------------------------------------------
-int do_RRCReestablishment(const protocol_ctxt_t *const ctxt_pP,
- rrc_gNB_ue_context_t *const ue_context_pP,
+int do_RRCReestablishment(rrc_gNB_ue_context_t *const ue_context_pP,
int CC_id,
uint8_t *const buffer,
size_t buffer_size,
@@ -1126,7 +1125,8 @@ int do_RRCReestablishment(const protocol_ctxt_t *const ctxt_pP,
rrcReestablishment->criticalExtensions.present = NR_RRCReestablishment__criticalExtensions_PR_rrcReestablishment;
rrcReestablishment->criticalExtensions.choice.rrcReestablishment = CALLOC(1, sizeof(NR_RRCReestablishment_IEs_t));
- uint16_t pci = RC.nrrrc[ctxt_pP->module_id]->carrier.physCellId;
+ int module_id = 0;
+ uint16_t pci = RC.nrrrc[module_id]->carrier.physCellId;
uint32_t nr_arfcn_dl = (uint64_t)*scc->downlinkConfigCommon->frequencyInfoDL->absoluteFrequencySSB;
LOG_I(NR_RRC, "Reestablishment update key pci=%d, earfcn_dl=%u\n", pci, nr_arfcn_dl);
diff --git a/openair2/RRC/NR/MESSAGES/asn1_msg.h b/openair2/RRC/NR/MESSAGES/asn1_msg.h
index 27782d8a97..5e9a9fa756 100644
--- a/openair2/RRC/NR/MESSAGES/asn1_msg.h
+++ b/openair2/RRC/NR/MESSAGES/asn1_msg.h
@@ -172,8 +172,7 @@ uint8_t do_NR_ULInformationTransfer(uint8_t **buffer,
uint8_t do_RRCReestablishmentRequest(uint8_t Mod_id, uint8_t *buffer, uint16_t c_rnti);
-int do_RRCReestablishment(const protocol_ctxt_t *const ctxt_pP,
- rrc_gNB_ue_context_t *const ue_context_pP,
+int do_RRCReestablishment(rrc_gNB_ue_context_t *const ue_context_pP,
int CC_id,
uint8_t *const buffer,
size_t buffer_size,
diff --git a/openair2/RRC/NR/cucp_cuup_direct.c b/openair2/RRC/NR/cucp_cuup_direct.c
index 9c4e6462a4..9dccef4286 100644
--- a/openair2/RRC/NR/cucp_cuup_direct.c
+++ b/openair2/RRC/NR/cucp_cuup_direct.c
@@ -61,7 +61,7 @@ void fill_e1ap_bearer_setup_resp(e1ap_bearer_setup_resp_t *resp,
drbSetup->numUpParam = 1;
drbSetup->UpParamList[0].tlAddress = my_addr;
drbSetup->UpParamList[0].teId = newGtpuCreateTunnel(gtpInst,
- (ue_id & 0xFFFF),
+ ue_id,
drb2Setup->id,
drb2Setup->id,
0xFFFF, // We will set the right value from DU answer
@@ -117,7 +117,7 @@ static int drb_config_gtpu_create(const protocol_ctxt_t *const ctxt_p,
create_tunnel_req.outgoing_teid[i] = pdu->param.gtp_teid;
}
create_tunnel_req.num_tunnels = UE->nb_of_pdusessions;
- create_tunnel_req.ue_id = UE->rnti;
+ create_tunnel_req.ue_id = UE->rrc_ue_id;
int ret = gtpv1u_create_ngu_tunnel(getCxtE1(instance)->gtpInstN3,
&create_tunnel_req,
&create_tunnel_resp,
@@ -150,8 +150,7 @@ static int drb_config_gtpu_create(const protocol_ctxt_t *const ctxt_p,
LOG_D(NR_RRC, "Configuring PDCP DRBs for UE %x\n", UE->rnti);
nr_pdcp_add_drbs(ctxt_p->enb_flag,
- ctxt_p->rntiMaybeUEid,
- 0,
+ UE->rrc_ue_id,
DRB_configList,
(UE->integrity_algorithm << 4) | UE->ciphering_algorithm,
kUPenc,
@@ -163,10 +162,10 @@ static int drb_config_gtpu_create(const protocol_ctxt_t *const ctxt_p,
static void cucp_cuup_bearer_context_setup_direct(e1ap_bearer_setup_req_t *const req, instance_t instance)
{
- rrc_gNB_ue_context_t *ue_context_p = rrc_gNB_get_ue_context_by_rnti(RC.nrrrc[instance], req->rnti);
+ rrc_gNB_ue_context_t *ue_context_p = rrc_gNB_get_ue_context(RC.nrrrc[instance], req->gNB_cu_cp_ue_id);
gNB_RRC_UE_t *UE = &ue_context_p->ue_context;
protocol_ctxt_t ctxt = {0};
- PROTOCOL_CTXT_SET_BY_MODULE_ID(&ctxt, 0, GNB_FLAG_YES, UE->rnti, 0, 0, 0);
+ PROTOCOL_CTXT_SET_BY_MODULE_ID(&ctxt, 0, GNB_FLAG_YES, UE->rrc_ue_id, 0, 0, 0);
e1ap_bearer_setup_resp_t resp = {0};
resp.numPDUSessions = req->numPDUSessions;
@@ -198,7 +197,7 @@ static void cucp_cuup_bearer_context_setup_direct(e1ap_bearer_setup_req_t *const
in_addr_t my_addr = inet_addr(RC.nrrrc[ctxt.module_id]->eth_params_s.my_addr);
instance_t gtpInst = getCxt(CUtype, instance)->gtpInst;
// GTP tunnel for DL
- fill_e1ap_bearer_setup_resp(&resp, req, gtpInst, UE->rnti, remote_port, my_addr);
+ fill_e1ap_bearer_setup_resp(&resp, req, gtpInst, UE->rrc_ue_id, remote_port, my_addr);
}
// actually, we should receive the corresponding context setup response
// message at the RRC and always react to this one. So in the following, we
@@ -212,7 +211,7 @@ static void cucp_cuup_bearer_context_mod_direct(e1ap_bearer_setup_req_t *const r
if (!NODE_IS_CU(RC.nrrrc[0]->node_type))
return;
instance_t gtpInst = getCxt(CUtype, instance)->gtpInst;
- CU_update_UP_DL_tunnel(req, gtpInst, req->rnti);
+ CU_update_UP_DL_tunnel(req, gtpInst, req->gNB_cu_cp_ue_id);
}
void cucp_cuup_message_transfer_direct_init(gNB_RRC_INST *rrc) {
diff --git a/openair2/RRC/NR/mac_rrc_dl.h b/openair2/RRC/NR/mac_rrc_dl.h
index 2728174603..94920f6f64 100644
--- a/openair2/RRC/NR/mac_rrc_dl.h
+++ b/openair2/RRC/NR/mac_rrc_dl.h
@@ -29,7 +29,7 @@ typedef void (*ue_context_setup_request_func_t)(const f1ap_ue_context_setup_t *r
typedef void (*ue_context_modification_request_func_t)(const f1ap_ue_context_modif_req_t *req);
typedef void (*ue_context_release_command_func_t)(const f1ap_ue_context_release_cmd_t *cmd);
-typedef void (*dl_rrc_message_transfer_func_t)(module_id_t module_id, const f1ap_dl_rrc_message_t *dl_rrc);
+typedef void (*dl_rrc_message_transfer_func_t)(const f1ap_dl_rrc_message_t *dl_rrc);
struct nr_mac_rrc_dl_if_s;
void mac_rrc_dl_direct_init(struct nr_mac_rrc_dl_if_s *mac_rrc);
diff --git a/openair2/RRC/NR/mac_rrc_dl_direct.c b/openair2/RRC/NR/mac_rrc_dl_direct.c
index 2d436c19e3..eeec72e132 100644
--- a/openair2/RRC/NR/mac_rrc_dl_direct.c
+++ b/openair2/RRC/NR/mac_rrc_dl_direct.c
@@ -24,17 +24,10 @@
#include "mac_rrc_dl.h"
#include "openair2/LAYER2/NR_MAC_gNB/mac_rrc_dl_handler.h"
-static void dl_rrc_message_transfer_direct(module_id_t module_id, const f1ap_dl_rrc_message_t *dl_rrc)
-{
- /* TODO how to manage inter-thread communication? */
-
- dl_rrc_message(module_id, dl_rrc);
-}
-
void mac_rrc_dl_direct_init(nr_mac_rrc_dl_if_t *mac_rrc)
{
mac_rrc->ue_context_setup_request = ue_context_setup_request;
mac_rrc->ue_context_modification_request = ue_context_modification_request;
mac_rrc->ue_context_release_command = ue_context_release_command;
- mac_rrc->dl_rrc_message_transfer = dl_rrc_message_transfer_direct;
+ mac_rrc->dl_rrc_message_transfer = dl_rrc_message_transfer;
}
diff --git a/openair2/RRC/NR/mac_rrc_dl_f1ap.c b/openair2/RRC/NR/mac_rrc_dl_f1ap.c
index 5bfeda2dc8..3f3b0f800f 100644
--- a/openair2/RRC/NR/mac_rrc_dl_f1ap.c
+++ b/openair2/RRC/NR/mac_rrc_dl_f1ap.c
@@ -76,23 +76,34 @@ static void ue_context_release_command_f1ap(const f1ap_ue_context_release_cmd_t
MessageDef *message_p = itti_alloc_new_message (TASK_RRC_GNB, 0, F1AP_UE_CONTEXT_RELEASE_CMD);
f1ap_ue_context_release_cmd_t *msg = &F1AP_UE_CONTEXT_RELEASE_CMD(message_p);
*msg = *cmd;
+ if (cmd->rrc_container_length > 0) {
+ msg->rrc_container = calloc(cmd->rrc_container_length, sizeof(*msg->rrc_container));
+ AssertFatal(msg->rrc_container != NULL, "out of memory\n");
+ msg->rrc_container_length = cmd->rrc_container_length;
+ memcpy(msg->rrc_container, cmd->rrc_container, cmd->rrc_container_length);
+ }
itti_send_msg_to_task (TASK_CU_F1, 0, message_p);
}
-static void dl_rrc_message_transfer_f1ap(module_id_t module_id, const f1ap_dl_rrc_message_t *dl_rrc)
+static void dl_rrc_message_transfer_f1ap(const f1ap_dl_rrc_message_t *dl_rrc)
{
/* TODO call F1AP function directly? no real-time constraint here */
MessageDef *message_p = itti_alloc_new_message (TASK_RRC_GNB, 0, F1AP_DL_RRC_MESSAGE);
f1ap_dl_rrc_message_t *msg = &F1AP_DL_RRC_MESSAGE(message_p);
*msg = *dl_rrc;
+ if (dl_rrc->old_gNB_DU_ue_id) {
+ msg->old_gNB_DU_ue_id = malloc(sizeof(*msg->old_gNB_DU_ue_id));
+ AssertFatal(msg->old_gNB_DU_ue_id != NULL, "out of memory\n");
+ *msg->old_gNB_DU_ue_id = *dl_rrc->old_gNB_DU_ue_id;
+ }
if (dl_rrc->rrc_container) {
msg->rrc_container = malloc(dl_rrc->rrc_container_length);
AssertFatal(msg->rrc_container != NULL, "out of memory\n");
msg->rrc_container_length = dl_rrc->rrc_container_length;
memcpy(msg->rrc_container, dl_rrc->rrc_container, dl_rrc->rrc_container_length);
}
- itti_send_msg_to_task (TASK_CU_F1, module_id, message_p);
+ itti_send_msg_to_task (TASK_CU_F1, 0, message_p);
}
void mac_rrc_dl_f1ap_init(nr_mac_rrc_dl_if_t *mac_rrc)
diff --git a/openair2/RRC/NR/nr_rrc_defs.h b/openair2/RRC/NR/nr_rrc_defs.h
index 51ef9d0f8d..f9c821736c 100644
--- a/openair2/RRC/NR/nr_rrc_defs.h
+++ b/openair2/RRC/NR/nr_rrc_defs.h
@@ -235,7 +235,6 @@ typedef enum {
} rrc_action_t;
typedef struct gNB_RRC_UE_s {
- uint8_t primaryCC_id;
drb_t established_drbs[MAX_DRBS_PER_UE];
uint8_t DRB_active[MAX_DRBS_PER_UE];
@@ -255,9 +254,6 @@ typedef struct gNB_RRC_UE_s {
NR_RRCReconfiguration_t *reconfig;
NR_RadioBearerConfig_t *rb_config;
- /* Pointer to save spCellConfig during RRC Reestablishment procedures */
- NR_SpCellConfig_t *spCellConfigReestablishment;
-
ImsiMobileIdentity_t imsi;
/* KgNB as derived from KASME received from EPC */
@@ -283,12 +279,7 @@ typedef struct gNB_RRC_UE_s {
/* Information from UE RRCReestablishmentRequest */
NR_ReestablishmentCause_t reestablishment_cause;
- /* UE id for initial connection to S1AP */
- uint16_t ue_initial_id;
-
- /* Information from S1AP initial_context_setup_req */
- uint32_t gNB_ue_s1ap_id :24;
- uint32_t gNB_ue_ngap_id;
+ uint32_t rrc_ue_id;
uint64_t amf_ue_ngap_id;
nr_rrc_guami_t ue_guami;
@@ -383,11 +374,6 @@ typedef struct cucp_cuup_if_s {
cucp_cuup_bearer_context_setup_func_t bearer_context_mod;
} cucp_cuup_if_t;
-typedef struct nr_reestablish_rnti_map_s {
- ue_id_t ue_id;
- rnti_t c_rnti;
-} nr_reestablish_rnti_map_t;
-
//---NR---(completely change)---------------------
typedef struct gNB_RRC_INST_s {
@@ -435,8 +421,6 @@ typedef struct gNB_RRC_INST_s {
// security configuration (preferred algorithms)
nr_security_configuration_t security;
- nr_reestablish_rnti_map_t nr_reestablish_rnti_map[MAX_MOBILES_PER_GNB];
-
nr_mac_rrc_dl_if_t mac_rrc;
cucp_cuup_if_t cucp_cuup;
diff --git a/openair2/RRC/NR/nr_rrc_proto.h b/openair2/RRC/NR/nr_rrc_proto.h
index fd9f38a3fb..7502662da3 100644
--- a/openair2/RRC/NR/nr_rrc_proto.h
+++ b/openair2/RRC/NR/nr_rrc_proto.h
@@ -119,7 +119,6 @@ void *rrc_gnb_task(void *args_p);
\ *reOffset Pointer to RE Offset Value */
void rrc_config_dl_ptrs_params(NR_BWP_Downlink_t *bwp, long *ptrsNrb, long *ptrsMcs, long *epre_Ratio, long *reOffset);
-void nr_rrc_mac_remove_ue(rnti_t rntiP);
void nr_rrc_mac_update_cellgroup(rnti_t rntiMaybeUEid, NR_CellGroupConfig_t *cgc);
int8_t nr_mac_rrc_bwp_switch_req(const module_id_t module_idP,
@@ -164,7 +163,6 @@ void nr_pdcp_add_srbs(eNB_flag_t enb_flag, ue_id_t rntiMaybeUEid, NR_SRB_ToAddMo
void nr_pdcp_add_drbs(eNB_flag_t enb_flag,
ue_id_t rntiMaybeUEid,
- ue_id_t reestablish_ue_id,
NR_DRB_ToAddModList_t *const drb2add_list,
const uint8_t security_modeP,
uint8_t *const kUPenc,
@@ -172,4 +170,7 @@ void nr_pdcp_add_drbs(eNB_flag_t enb_flag,
struct NR_CellGroupConfig__rlc_BearerToAddModList *rlc_bearer2add_list);
int rrc_gNB_generate_pcch_msg(uint32_t tmsi, uint8_t paging_drx, instance_t instance, uint8_t CC_id);
+
+void nr_rrc_transfer_protected_rrc_message(const gNB_RRC_INST *rrc, const gNB_RRC_UE_t *ue_p, uint8_t srb_id, const uint8_t* buffer, int size);
+
#endif
diff --git a/openair2/RRC/NR/rrc_gNB.c b/openair2/RRC/NR/rrc_gNB.c
index f731ed0fbe..1fa458a309 100644
--- a/openair2/RRC/NR/rrc_gNB.c
+++ b/openair2/RRC/NR/rrc_gNB.c
@@ -97,6 +97,7 @@
#include
#include "openair2/LAYER2/nr_pdcp/nr_pdcp_e1_api.h"
#include "openair2/F1AP/f1ap_common.h"
+#include "openair2/F1AP/f1ap_ids.h"
#include "openair2/SDAP/nr_sdap/nr_sdap_entity.h"
#include "cucp_cuup_if.h"
@@ -186,26 +187,6 @@ static void freeDRBlist(NR_DRB_ToAddModList_t *list)
//ASN_STRUCT_FREE(asn_DEF_NR_DRB_ToAddModList, list);
return;
}
-static void nr_rrc_addmod_srbs(int rnti,
- const NR_SRB_INFO_TABLE_ENTRY *srb_list,
- const int nb_srb,
- const struct NR_CellGroupConfig__rlc_BearerToAddModList *bearer_list)
-{
- if (srb_list == NULL || bearer_list == NULL)
- return;
-
- for (int i = 0; i < nb_srb; i++) {
- if (srb_list[i].Active)
- for (int j = 0; j < bearer_list->list.count; j++) {
- const NR_RLC_BearerConfig_t *bearer = bearer_list->list.array[j];
- if (bearer->servedRadioBearer != NULL
- && bearer->servedRadioBearer->present == NR_RLC_BearerConfig__servedRadioBearer_PR_srb_Identity
- && i == bearer->servedRadioBearer->choice.srb_Identity) {
- nr_rlc_add_srb(rnti, i, bearer);
- }
- }
- }
-}
static void nr_rrc_addmod_drbs(int rnti,
const NR_DRB_ToAddModList_t *drb_list,
@@ -227,6 +208,29 @@ static void nr_rrc_addmod_drbs(int rnti,
}
}
+typedef struct deliver_dl_rrc_message_data_s {
+ const gNB_RRC_INST *rrc;
+ f1ap_dl_rrc_message_t *dl_rrc;
+} deliver_dl_rrc_message_data_t;
+static void rrc_deliver_dl_rrc_message(void *deliver_pdu_data, ue_id_t ue_id, int srb_id, char *buf, int size, int sdu_id)
+{
+ DevAssert(deliver_pdu_data != NULL);
+ deliver_dl_rrc_message_data_t *data = (deliver_dl_rrc_message_data_t *)deliver_pdu_data;
+ data->dl_rrc->rrc_container = (uint8_t *)buf;
+ data->dl_rrc->rrc_container_length = size;
+ DevAssert(data->dl_rrc->srb_id == srb_id);
+ data->rrc->mac_rrc.dl_rrc_message_transfer(data->dl_rrc);
+}
+
+
+void nr_rrc_transfer_protected_rrc_message(const gNB_RRC_INST *rrc, const gNB_RRC_UE_t *ue_p, uint8_t srb_id, const uint8_t* buffer, int size)
+{
+ DevAssert(size > 0);
+ f1_ue_data_t ue_data = cu_get_f1_ue_data(ue_p->rrc_ue_id);
+ f1ap_dl_rrc_message_t dl_rrc = {.gNB_CU_ue_id = ue_p->rrc_ue_id, .gNB_DU_ue_id = ue_data.secondary_ue, .srb_id = srb_id};
+ deliver_dl_rrc_message_data_t data = {.rrc = rrc, .dl_rrc = &dl_rrc};
+ nr_pdcp_data_req_srb(ue_p->rrc_ue_id, srb_id, rrc_gNB_mui++, size, (unsigned char *const)buffer, rrc_deliver_dl_rrc_message, &data);
+}
///---------------------------------------------------------------------------------------------------------------///
///---------------------------------------------------------------------------------------------------------------///
@@ -310,6 +314,7 @@ static void rrc_gNB_CU_DU_init(gNB_RRC_INST *rrc)
AssertFatal(0 == 1, "Unknown node type %d\n", rrc->node_type);
break;
}
+ cu_init_f1_ue_data();
}
static void openair_rrc_gNB_configuration(const module_id_t gnb_mod_idP, gNB_RrcConfigurationReq *configuration)
@@ -422,25 +427,6 @@ static void freeSRBlist(NR_SRB_ToAddModList_t *l)
LOG_E(NR_RRC, "Call free SRB list on NULL pointer\n");
}
-static void apply_macrlc_config(gNB_RRC_INST *rrc, rrc_gNB_ue_context_t *const ue_context_pP, const protocol_ctxt_t *const ctxt_pP)
-{
- NR_CellGroupConfig_t *cgc = get_softmodem_params()->sa ? ue_context_pP->ue_context.masterCellGroup : NULL;
- gNB_RRC_UE_t *ue_p = &ue_context_pP->ue_context;
- nr_rrc_mac_update_cellgroup(ue_p->rnti, cgc);
- nr_rrc_addmod_srbs(ctxt_pP->rntiMaybeUEid, ue_p->Srb, maxSRBs, cgc->rlc_BearerToAddModList);
- NR_DRB_ToAddModList_t *DRBs = fill_DRB_configList(ue_p);
- nr_rrc_addmod_drbs(ctxt_pP->rntiMaybeUEid, DRBs, cgc->rlc_BearerToAddModList);
- freeDRBlist(DRBs);
-}
-
-void apply_macrlc_config_reest(gNB_RRC_INST *rrc, rrc_gNB_ue_context_t *const ue_context_pP, const protocol_ctxt_t *const ctxt_pP, ue_id_t ue_id)
-{
- gNB_RRC_UE_t *ue_p = &ue_context_pP->ue_context;
- nr_rrc_mac_update_cellgroup(ue_id, ue_p->masterCellGroup);
-
- nr_rrc_addmod_srbs(ctxt_pP->rntiMaybeUEid, ue_p->Srb, maxSRBs, ue_p->masterCellGroup->rlc_BearerToAddModList);
-}
-
//-----------------------------------------------------------------------------
static void rrc_gNB_generate_RRCSetup(instance_t instance,
rnti_t rnti,
@@ -466,74 +452,18 @@ static void rrc_gNB_generate_RRCSetup(instance_t instance,
(char *)buf,
size,
"[MSG] RRC Setup\n");
- nr_pdcp_add_srbs(true, rnti, SRBs, 0, NULL, NULL);
+ nr_pdcp_add_srbs(true, ue_p->rrc_ue_id, SRBs, 0, NULL, NULL);
freeSRBlist(SRBs);
+ f1_ue_data_t ue_data = cu_get_f1_ue_data(ue_p->rrc_ue_id);
f1ap_dl_rrc_message_t dl_rrc = {
- .old_gNB_DU_ue_id = 0xFFFFFF,
+ .gNB_CU_ue_id = ue_p->rrc_ue_id,
+ .gNB_DU_ue_id = ue_data.secondary_ue,
.rrc_container = buf,
.rrc_container_length = size,
- .rnti = ue_p->rnti,
.srb_id = CCCH
};
- rrc->mac_rrc.dl_rrc_message_transfer(instance, &dl_rrc);
-}
-
-//-----------------------------------------------------------------------------
-static int rrc_gNB_generate_RRCSetup_for_RRCReestablishmentRequest(module_id_t module_id, rnti_t rnti, const int CC_id)
-//-----------------------------------------------------------------------------
-{
- LOG_I(NR_RRC, "generate RRCSetup for RRCReestablishmentRequest \n");
- rrc_gNB_ue_context_t *ue_context_pP = NULL;
- gNB_RRC_INST *rrc_instance_p = RC.nrrrc[module_id];
-
- ue_context_pP = rrc_gNB_create_ue_context(rnti, rrc_instance_p, 0);
-
- gNB_RRC_UE_t *ue_p = &ue_context_pP->ue_context;
- unsigned char buf[1024];
- uint8_t xid = rrc_gNB_get_next_transaction_identifier(module_id);
- ue_p->xids[xid] = RRC_SETUP_FOR_REESTABLISHMENT;
- NR_SRB_ToAddModList_t *SRBs = createSRBlist(ue_p, true);
-
- int size = do_RRCSetup(ue_context_pP, buf, xid, NULL, 0, &rrc_instance_p->configuration, SRBs);
- AssertFatal(size > 0, "do_RRCSetup failed\n");
- AssertFatal(size <= 1024, "memory corruption\n");
-
- AssertFatal(size>0,"Error generating RRCSetup for RRCReestablishmentRequest\n");
-
- LOG_DUMPMSG(NR_RRC, DEBUG_RRC,
- (char *)buf,
- size,
- "[MSG] RRC Setup\n");
-
- LOG_D(NR_RRC, "RRC_gNB --- MAC_CONFIG_REQ (SRB1) ---> MAC_gNB for rnti %04x\n", rnti);
- freeSRBlist(SRBs);
-
- // update SCC and MIB/SIB (two calls)
- nr_mac_config_scc(RC.nrmac[rrc_instance_p->module_id],
- rrc_instance_p->configuration.pdsch_AntennaPorts,
- rrc_instance_p->configuration.pusch_AntennaPorts,
- rrc_instance_p->configuration.sib1_tda,
- rrc_instance_p->configuration.minRXTXTIME,
- rrc_instance_p->carrier.servingcellconfigcommon);
- nr_mac_config_mib(RC.nrmac[rrc_instance_p->module_id], rrc_instance_p->carrier.mib);
- nr_mac_config_sib1(RC.nrmac[rrc_instance_p->module_id], rrc_instance_p->carrier.siblock1);
-
- LOG_I(NR_RRC, " [RAPROC] rnti: %04x Logical Channel DL-CCCH, Generating RRCSetup (bytes %d)\n", rnti, size);
- // configure MAC
- protocol_ctxt_t ctxt = {0};
- PROTOCOL_CTXT_SET_BY_INSTANCE(&ctxt, 0, GNB_FLAG_YES, rnti, 0, 0);
- apply_macrlc_config(rrc_instance_p, ue_context_pP, &ctxt);
-
- f1ap_dl_rrc_message_t dl_rrc = {
- .old_gNB_DU_ue_id = 0xFFFFFF,
- .rrc_container = buf,
- .rrc_container_length = size,
- .rnti = ue_p->rnti,
- .srb_id = CCCH
- };
- rrc_instance_p->mac_rrc.dl_rrc_message_transfer(module_id, &dl_rrc);
- return xid;
+ rrc->mac_rrc.dl_rrc_message_transfer(&dl_rrc);
}
static void rrc_gNB_generate_RRCReject(module_id_t module_id, rrc_gNB_ue_context_t *const ue_context_pP)
@@ -554,18 +484,17 @@ static void rrc_gNB_generate_RRCReject(module_id_t module_id, rrc_gNB_ue_context
"[MSG] RRCReject \n");
LOG_I(NR_RRC, " [RAPROC] ue %04x Logical Channel DL-CCCH, Generating NR_RRCReject (bytes %d)\n", ue_p->rnti, size);
+ f1_ue_data_t ue_data = cu_get_f1_ue_data(ue_p->rrc_ue_id);
f1ap_dl_rrc_message_t dl_rrc = {
- .gNB_CU_ue_id = 0,
- .gNB_DU_ue_id = 0,
- .old_gNB_DU_ue_id = 0xFFFFFF,
+ .gNB_CU_ue_id = ue_p->rrc_ue_id,
+ .gNB_DU_ue_id = ue_data.secondary_ue,
.rrc_container = buf,
.rrc_container_length = size,
- .rnti = ue_p->rnti,
.srb_id = CCCH,
.execute_duplication = 1,
.RAT_frequency_priority_information.en_dc = 0
};
- rrc->mac_rrc.dl_rrc_message_transfer(module_id, &dl_rrc);
+ rrc->mac_rrc.dl_rrc_message_transfer(&dl_rrc);
}
//-----------------------------------------------------------------------------
@@ -580,6 +509,7 @@ static void rrc_gNB_process_RRCSetupComplete(const protocol_ctxt_t *const ctxt_p
ue_context_pP->ue_context.Srb[1].Active = 1;
ue_context_pP->ue_context.Srb[2].Active = 0;
ue_context_pP->ue_context.StatusRrc = NR_RRC_CONNECTED;
+ AssertFatal(ctxt_pP->rntiMaybeUEid == ue_context_pP->ue_context.rrc_ue_id, "logic bug: inconsistent IDs, must use CU UE ID!\n");
if (get_softmodem_params()->sa) {
rrc_gNB_send_NGAP_NAS_FIRST_REQ(ctxt_pP, ue_context_pP, rrcSetupComplete);
@@ -668,7 +598,7 @@ static void rrc_gNB_generate_defaultRRCReconfiguration(const protocol_ctxt_t *co
ue_context_pP->ue_context.rnti);
AssertFatal(!NODE_IS_DU(rrc->node_type), "illegal node type DU!\n");
- nr_pdcp_data_req_srb(ctxt_pP->rntiMaybeUEid, DCCH, rrc_gNB_mui++, size, buffer, deliver_pdu_srb_f1, rrc);
+ nr_rrc_transfer_protected_rrc_message(rrc, ue_p, DCCH, buffer, size);
if (NODE_IS_DU(rrc->node_type) || NODE_IS_MONOLITHIC(rrc->node_type)) {
gNB_RRC_UE_t *ue_p = &ue_context_pP->ue_context;
@@ -775,7 +705,7 @@ void rrc_gNB_generate_dedicatedRRCReconfiguration(const protocol_ctxt_t *const c
ctxt_pP->module_id,
DCCH);
- nr_pdcp_data_req_srb(ctxt_pP->rntiMaybeUEid, DCCH, rrc_gNB_mui++, size, buffer, deliver_pdu_srb_f1, rrc);
+ nr_rrc_transfer_protected_rrc_message(rrc, ue_p, DCCH, buffer, size);
if (NODE_IS_DU(rrc->node_type) || NODE_IS_MONOLITHIC(rrc->node_type)) {
nr_rrc_mac_update_cellgroup(ue_context_pP->ue_context.rnti, ue_context_pP->ue_context.masterCellGroup);
@@ -928,7 +858,7 @@ rrc_gNB_modify_dedicatedRRCReconfiguration(
DCCH);
gNB_RRC_INST *rrc = RC.nrrrc[ctxt_pP->module_id];
- nr_pdcp_data_req_srb(ctxt_pP->rntiMaybeUEid, DCCH, rrc_gNB_mui++, size, buffer, deliver_pdu_srb_f1, rrc);
+ nr_rrc_transfer_protected_rrc_message(rrc, ue_p, DCCH, buffer, size);
if (NODE_IS_DU(rrc->node_type) || NODE_IS_MONOLITHIC(rrc->node_type)) {
uint32_t delay_ms = ue_p->masterCellGroup && ue_p->masterCellGroup->spCellConfig && ue_p->masterCellGroup->spCellConfig->spCellConfigDedicated
@@ -1009,7 +939,7 @@ rrc_gNB_generate_dedicatedRRCReconfiguration_release(
DCCH);
gNB_RRC_INST *rrc = RC.nrrrc[ctxt_pP->module_id];
- nr_pdcp_data_req_srb(ctxt_pP->rntiMaybeUEid, DCCH, rrc_gNB_mui++, size, buffer, deliver_pdu_srb_f1, rrc);
+ nr_rrc_transfer_protected_rrc_message(rrc, ue_p, DCCH, buffer, size);
if (NODE_IS_DU(rrc->node_type) || NODE_IS_MONOLITHIC(rrc->node_type)) {
uint32_t delay_ms = ue_p->masterCellGroup && ue_p->masterCellGroup->spCellConfig && ue_p->masterCellGroup->spCellConfig->spCellConfigDedicated
@@ -1046,35 +976,18 @@ static void rrc_gNB_process_RRCReconfigurationComplete(const protocol_ctxt_t *co
/* Refresh SRBs/DRBs */
LOG_D(NR_RRC, "Configuring PDCP DRBs/SRBs for UE %04x\n", ue_p->rnti);
- ue_id_t reestablish_ue_id = 0;
- for (int i = 0; i < MAX_MOBILES_PER_GNB; i++) {
- nr_reestablish_rnti_map_t *nr_reestablish_rnti_map = &(RC.nrrrc[ctxt_pP->module_id])->nr_reestablish_rnti_map[i];
- if (nr_reestablish_rnti_map->ue_id == ctxt_pP->rntiMaybeUEid) {
- ue_context_pP->ue_context.ue_reconfiguration_after_reestablishment_counter++;
- reestablish_ue_id = nr_reestablish_rnti_map[i].c_rnti;
- LOG_D(NR_RRC,
- "Removing reestablish_rnti_map[%d] UEid %lx, RNTI %04x\n",
- i,
- nr_reestablish_rnti_map->ue_id,
- nr_reestablish_rnti_map->c_rnti);
- // clear current C-RNTI from map
- nr_reestablish_rnti_map->ue_id = 0;
- nr_reestablish_rnti_map->c_rnti = 0;
- break;
- }
- }
- NR_SRB_ToAddModList_t *SRBs = createSRBlist(ue_p, false);
+ ue_context_pP->ue_context.ue_reconfiguration_after_reestablishment_counter++;
+ NR_SRB_ToAddModList_t *SRBs = createSRBlist(ue_p, false);
nr_pdcp_add_srbs(ctxt_pP->enb_flag,
- ctxt_pP->rntiMaybeUEid,
+ ue_p->rrc_ue_id,
SRBs,
(ue_p->integrity_algorithm << 4) | ue_p->ciphering_algorithm,
kRRCenc,
kRRCint);
freeSRBlist(SRBs);
nr_pdcp_add_drbs(ctxt_pP->enb_flag,
- ctxt_pP->rntiMaybeUEid,
- reestablish_ue_id,
+ ue_p->rrc_ue_id,
DRB_configList,
(ue_p->integrity_algorithm << 4) | ue_p->ciphering_algorithm,
kUPenc,
@@ -1145,34 +1058,23 @@ static void rrc_gNB_process_RRCReconfigurationComplete(const protocol_ctxt_t *co
}
//-----------------------------------------------------------------------------
-void rrc_gNB_generate_RRCReestablishment(const protocol_ctxt_t *ctxt_pP,
- rrc_gNB_ue_context_t *ue_context_pP,
- const uint8_t *masterCellGroup_from_DU,
- NR_ServingCellConfigCommon_t *scc,
- const int CC_id)
+static void rrc_gNB_generate_RRCReestablishment(rrc_gNB_ue_context_t *ue_context_pP,
+ const uint8_t *masterCellGroup_from_DU,
+ NR_ServingCellConfigCommon_t *scc,
+ const rnti_t old_rnti)
//-----------------------------------------------------------------------------
{
- // int UE_id = -1;
- // NR_LogicalChannelConfig_t *SRB1_logicalChannelConfig = NULL;
- // NR_SRB_ToAddMod_t *SRB1_config = NULL;
- // rrc_gNB_carrier_data_t *carrier = NULL;
- module_id_t module_id = ctxt_pP->module_id;
- gNB_RRC_INST *rrc = RC.nrrrc[ctxt_pP->module_id];
+ module_id_t module_id = 0;
+ gNB_RRC_INST *rrc = RC.nrrrc[module_id];
int enable_ciphering = 0;
gNB_RRC_UE_t *ue_p = &ue_context_pP->ue_context;
- // Need to drop spCellConfig when there is a RRCReestablishment
- // Save spCellConfig in spCellConfigReestablishment to recover after Reestablishment is completed
- ue_p->spCellConfigReestablishment = ue_p->masterCellGroup->spCellConfig;
- ue_p->masterCellGroup->spCellConfig = NULL;
-
uint8_t buffer[RRC_BUF_SIZE] = {0};
uint8_t xid = rrc_gNB_get_next_transaction_identifier(module_id);
ue_p->xids[xid] = RRC_REESTABLISH;
NR_SRB_ToAddModList_t *SRBs = createSRBlist(ue_p, true);
- int size = do_RRCReestablishment(ctxt_pP,
- ue_context_pP,
- CC_id,
+ int size = do_RRCReestablishment(ue_context_pP,
+ 0 /* CC_id */,
buffer,
RRC_BUF_SIZE,
xid,
@@ -1192,101 +1094,27 @@ void rrc_gNB_generate_RRCReestablishment(const protocol_ctxt_t *ctxt_pP,
nr_derive_key(RRC_ENC_ALG, ue_p->ciphering_algorithm, ue_p->kgnb, kRRCenc);
nr_derive_key(RRC_INT_ALG, ue_p->integrity_algorithm, ue_p->kgnb, kRRCint);
-
- /* Configure SRB1 for UE */
- nr_pdcp_add_srbs(ctxt_pP->enb_flag, ctxt_pP->rntiMaybeUEid, SRBs, 0, NULL, NULL);
- LOG_D(NR_RRC, "UE %04x --- MAC_CONFIG_REQ (SRB1) ---> MAC_gNB\n", ue_p->rnti);
freeSRBlist(SRBs);
- LOG_I(NR_RRC, "Set PDCP security RNTI %04lx nca %ld nia %d in RRCReestablishment\n", ctxt_pP->rntiMaybeUEid, ue_p->ciphering_algorithm, ue_p->integrity_algorithm);
+ LOG_I(NR_RRC, "Set PDCP security UE %d RNTI %04x nca %ld nia %d in RRCReestablishment\n", ue_p->rrc_ue_id, ue_p->rnti, ue_p->ciphering_algorithm, ue_p->integrity_algorithm);
uint8_t security_mode =
enable_ciphering ? ue_p->ciphering_algorithm | (ue_p->integrity_algorithm << 4) : 0 | (ue_p->integrity_algorithm << 4);
- nr_pdcp_config_set_security(ctxt_pP->rntiMaybeUEid,
+ nr_pdcp_config_set_security(ue_p->rrc_ue_id,
DCCH,
security_mode,
kRRCenc,
kRRCint,
kUPenc);
+ nr_pdcp_reestablishment(ue_p->rrc_ue_id);
- if (!NODE_IS_CU(rrc->node_type)) {
- apply_macrlc_config_reest(rrc, ue_context_pP, ctxt_pP, ctxt_pP->rntiMaybeUEid);
- }
-
- nr_pdcp_data_req_srb(ctxt_pP->rntiMaybeUEid, DCCH, rrc_gNB_mui++, size, buffer, deliver_pdu_srb_f1, rrc);
-}
-
-/// @brief Function used in RRCReestablishmentComplete procedure to update the NGU Tunnels.
-/// @param reestablish_rnti is the old C-RNTI
-void RRCReestablishmentComplete_update_ngu_tunnel(const protocol_ctxt_t *const ctxt_pP,
- rrc_gNB_ue_context_t *ue_context_pP,
- const rnti_t reestablish_rnti)
-{
- gNB_RRC_UE_t *ue_p = &ue_context_pP->ue_context;
- int i = 0;
- int j = 0;
- int ret = 0;
-
- if (get_softmodem_params()->sa) {
- LOG_W(NR_RRC, "RRC Reestablishment - Rework identity mapping need to be done properly!\n");
- gtpv1u_gnb_create_tunnel_req_t create_tunnel_req = {0};
- /* Save e RAB information for later */
-
- for (j = 0, i = 0; i < NB_RB_MAX; i++) {
- if (ue_p->pduSession[i].status == PDU_SESSION_STATUS_ESTABLISHED || ue_p->pduSession[i].status == PDU_SESSION_STATUS_DONE) {
- create_tunnel_req.pdusession_id[j] = ue_p->pduSession[i].param.pdusession_id;
- create_tunnel_req.incoming_rb_id[j] = i + 1;
- create_tunnel_req.outgoing_teid[j] = ue_p->pduSession[i].param.gtp_teid;
- // to be developped, use the first QFI only
- create_tunnel_req.outgoing_qfi[j] = ue_p->pduSession[i].param.qos[0].qfi;
- memcpy(create_tunnel_req.dst_addr[j].buffer, ue_p->pduSession[i].param.upf_addr.buffer, sizeof(uint8_t) * 20);
- create_tunnel_req.dst_addr[j].length = ue_p->pduSession[i].param.upf_addr.length;
- j++;
- }
- }
-
- create_tunnel_req.ue_id = ctxt_pP->rntiMaybeUEid; // warning put zero above
- create_tunnel_req.num_tunnels = j;
- ret = gtpv1u_update_ngu_tunnel(ctxt_pP->instance, &create_tunnel_req, reestablish_rnti);
-
- if (ret != 0) {
- LOG_E(NR_RRC, "RRC Reestablishment - gtpv1u_update_ngu_tunnel failed,start to release UE %x\n", reestablish_rnti);
- AssertFatal(false, "not implemented\n");
- return;
- }
- }
-}
-
-/// @brief Function used in RRCReestablishmentComplete procedure to update the NAS PDUSessions and the xid.
-/// @param old_xid Refers to the old transaction identifier passed to rrc_gNB_process_RRCReestablishmentComplete as xid.
-/// @todo parameters yet to process inside the for loop.
-/// @todo should test if pdu session are Ok before! inside the for loop.
-void RRCReestablishmentComplete_nas_pdu_update(rrc_gNB_ue_context_t *ue_context_pP, const uint8_t old_xid)
-{
- gNB_RRC_UE_t *ue_p = &ue_context_pP->ue_context;
- /* Add all NAS PDUs to the list */
- for (int i = 0; i < ue_p->nb_of_pdusessions; i++) {
- ue_p->pduSession[i].status = PDU_SESSION_STATUS_DONE;
- ue_p->pduSession[i].xid = old_xid;
- LOG_D(NR_RRC,
- "RRC Reestablishment - setting the status for the default DRB (index %d) to (%d,%s)\n",
- i,
- ue_p->pduSession[i].status,
- "PDU_SESSION_STATUS_DONE");
- }
-}
-
-/// @brief Function used in RRCReestablishmentComplete procedure to Free all the NAS PDU buffers.
-void RRCReestablishmentComplete_nas_pdu_free(rrc_gNB_ue_context_t *ue_context_pP)
-{
- gNB_RRC_UE_t *ue_p = &ue_context_pP->ue_context;
- /* Free all NAS PDUs */
- for (int i = 0; i < ue_p->nb_of_pdusessions; i++) {
- if (ue_p->pduSession[i].param.nas_pdu.buffer != NULL) {
- /* Free the NAS PDU buffer and invalidate it */
- free(ue_p->pduSession[i].param.nas_pdu.buffer);
- ue_p->pduSession[i].param.nas_pdu.buffer = NULL;
- }
- }
+ f1_ue_data_t ue_data = cu_get_f1_ue_data(ue_p->rrc_ue_id);
+ uint32_t old_gNB_DU_ue_id = old_rnti;
+ f1ap_dl_rrc_message_t dl_rrc = {.gNB_CU_ue_id = ue_p->rrc_ue_id,
+ .gNB_DU_ue_id = ue_data.secondary_ue,
+ .srb_id = DCCH,
+ .old_gNB_DU_ue_id = &old_gNB_DU_ue_id};
+ deliver_dl_rrc_message_data_t data = {.rrc = rrc, .dl_rrc = &dl_rrc};
+ nr_pdcp_data_req_srb(ue_p->rrc_ue_id, DCCH, rrc_gNB_mui++, size, (unsigned char *const)buffer, rrc_deliver_dl_rrc_message, &data);
}
/// @brief Function tha processes RRCReestablishmentComplete message sent by the UE, after RRCReestasblishment request.
@@ -1294,10 +1122,9 @@ void RRCReestablishmentComplete_nas_pdu_free(rrc_gNB_ue_context_t *ue_context_pP
/// @param reestablish_rnti is the old C-RNTI
/// @param ue_context_pP UE context container information regarding the UE
/// @param xid Transaction Identifier used in RRC messages
-void rrc_gNB_process_RRCReestablishmentComplete(const protocol_ctxt_t *const ctxt_pP,
- const rnti_t reestablish_rnti,
- rrc_gNB_ue_context_t *ue_context_pP,
- const uint8_t xid)
+static void rrc_gNB_process_RRCReestablishmentComplete(const protocol_ctxt_t *const ctxt_pP,
+ rrc_gNB_ue_context_t *ue_context_pP,
+ const uint8_t xid)
{
gNB_RRC_UE_t *ue_p = &ue_context_pP->ue_context;
LOG_I(NR_RRC,
@@ -1316,19 +1143,10 @@ void rrc_gNB_process_RRCReestablishmentComplete(const protocol_ctxt_t *const ctx
nr_rrc_pdcp_config_security(ctxt_pP, ue_context_pP, send_security_mode_command);
LOG_D(NR_RRC, "RRC Reestablishment - set security successfully \n");
}
- RRCReestablishmentComplete_update_ngu_tunnel(ctxt_pP, ue_context_pP, reestablish_rnti);
- RRCReestablishmentComplete_nas_pdu_update(ue_context_pP, xid);
-
- /* Update RNTI in ue_context */
- LOG_I(NR_RRC, "RRC Reestablishment - Updating UEid from %04x to %lx\n", ue_p->rnti, ctxt_pP->rntiMaybeUEid);
- rrc_gNB_update_ue_context_rnti(ctxt_pP->rntiMaybeUEid, RC.nrrrc[ctxt_pP->module_id], ue_p->gNB_ue_ngap_id);
gNB_RRC_INST *rrc = RC.nrrrc[ctxt_pP->module_id];
NR_CellGroupConfig_t *cellGroupConfig = calloc(1, sizeof(NR_CellGroupConfig_t));
- // Revert spCellConfig stored in spCellConfigReestablishment before had been dropped during RRC Reestablishment
- ue_p->masterCellGroup->spCellConfig = ue_p->spCellConfigReestablishment;
- ue_p->spCellConfigReestablishment = NULL;
cellGroupConfig->spCellConfig = ue_p->masterCellGroup->spCellConfig;
cellGroupConfig->mac_CellGroupConfig = ue_p->masterCellGroup->mac_CellGroupConfig;
cellGroupConfig->physicalCellGroupConfig = ue_p->masterCellGroup->physicalCellGroupConfig;
@@ -1371,32 +1189,13 @@ void rrc_gNB_process_RRCReestablishmentComplete(const protocol_ctxt_t *const ctx
freeDRBlist(DRBs);
LOG_DUMPMSG(NR_RRC, DEBUG_RRC, (char *)buffer, size, "[MSG] RRC Reconfiguration\n");
- RRCReestablishmentComplete_nas_pdu_free(ue_context_pP);
-
- if (size < 0) {
- LOG_E(NR_RRC, "RRC decode err!!! do_RRCReconfiguration\n");
- return;
- } else {
- LOG_I(NR_RRC,
- "[gNB %d] Frame %d, Logical Channel DL-DCCH, Generate NR_RRCReconfiguration (bytes %d, UE id %04x)\n",
- ctxt_pP->module_id,
- ctxt_pP->frame,
- size,
- ue_p->rnti);
- LOG_D(NR_RRC,
- "[FRAME %05d][RRC_gNB][MOD %u][][--- PDCP_DATA_REQ/%d Bytes (RRCReconfiguration to UE %04x MUI %d) --->][PDCP][MOD "
- "%u][RB %u]\n",
- ctxt_pP->frame,
- ctxt_pP->module_id,
- size,
- ue_p->rnti,
- rrc_gNB_mui,
- ctxt_pP->module_id,
- DCCH);
-
- nr_rrc_mac_update_cellgroup(ue_context_pP->ue_context.rnti, cellGroupConfig);
- nr_pdcp_data_req_srb(ctxt_pP->rntiMaybeUEid, DCCH, rrc_gNB_mui++, size, buffer, deliver_pdu_srb_f1, rrc);
- }
+ AssertFatal(size > 0, "cannot encode RRC Reconfiguration\n");
+ LOG_I(NR_RRC,
+ "UE %d RNTI %04x: Generate NR_RRCReconfiguration after reestablishment complete (bytes %d)\n",
+ ue_p->rrc_ue_id,
+ ue_p->rnti,
+ size);
+ nr_rrc_transfer_protected_rrc_message(rrc, ue_p, DCCH, buffer, size);
if (NODE_IS_DU(RC.nrrrc[ctxt_pP->module_id]->node_type) || NODE_IS_MONOLITHIC(RC.nrrrc[ctxt_pP->module_id]->node_type)) {
uint32_t delay_ms = ue_p->masterCellGroup && ue_p->masterCellGroup->spCellConfig
@@ -1451,7 +1250,7 @@ int nr_rrc_reconfiguration_req(rrc_gNB_ue_context_t *const ue_context_pP
nr_rrc_mac_update_cellgroup(ue_context_pP->ue_context.rnti, masterCellGroup);
gNB_RRC_INST *rrc = RC.nrrrc[ctxt_pP->module_id];
- nr_pdcp_data_req_srb(ctxt_pP->rntiMaybeUEid, DCCH, rrc_gNB_mui++, size, buffer, deliver_pdu_srb_f1, rrc);
+ nr_rrc_transfer_protected_rrc_message(rrc, ue_p, DCCH, buffer, size);
if (NODE_IS_DU(rrc->node_type) || NODE_IS_MONOLITHIC(rrc->node_type)) {
uint32_t delay_ms = ue_p->masterCellGroup && ue_p->masterCellGroup->spCellConfig && ue_p->masterCellGroup->spCellConfig->spCellConfigDedicated
@@ -1466,17 +1265,18 @@ int nr_rrc_reconfiguration_req(rrc_gNB_ue_context_t *const ue_context_pP
}
/*------------------------------------------------------------------------------*/
-static int nr_rrc_gNB_decode_ccch(module_id_t module_id, rnti_t rnti, const uint8_t *buffer, int buffer_length, const uint8_t *du_to_cu_rrc_container, int du_to_cu_rrc_container_len)
+static int nr_rrc_gNB_decode_ccch(module_id_t module_id, const f1ap_initial_ul_rrc_message_t *msg)
{
- module_id_t Idx;
asn_dec_rval_t dec_rval;
NR_UL_CCCH_Message_t *ul_ccch_msg = NULL;
gNB_RRC_INST *gnb_rrc_inst = RC.nrrrc[module_id];
NR_RRCSetupRequest_IEs_t *rrcSetupRequest = NULL;
NR_RRCReestablishmentRequest_IEs_t rrcReestablishmentRequest;
+ rnti_t rnti = msg->crnti;
- LOG_I(NR_RRC, "Decoding CCCH: RNTI %04x, payload_size %d\n", rnti, buffer_length);
- dec_rval = uper_decode(NULL, &asn_DEF_NR_UL_CCCH_Message, (void **) &ul_ccch_msg, buffer, buffer_length, 0, 0);
+ LOG_I(NR_RRC, "Decoding CCCH: RNTI %04x, payload_size %d\n", rnti, msg->rrc_container_length);
+ dec_rval =
+ uper_decode(NULL, &asn_DEF_NR_UL_CCCH_Message, (void **)&ul_ccch_msg, msg->rrc_container, msg->rrc_container_length, 0, 0);
if (dec_rval.code != RC_OK || dec_rval.consumed == 0) {
LOG_E(NR_RRC, " FATAL Error in receiving CCCH\n");
@@ -1492,12 +1292,9 @@ static int nr_rrc_gNB_decode_ccch(module_id_t module_id, rnti_t rnti, const uint
case NR_UL_CCCH_MessageType__c1_PR_rrcSetupRequest:
LOG_D(NR_RRC, "Received RRCSetupRequest on UL-CCCH-Message (UE rnti %04x)\n", rnti);
- rrc_gNB_ue_context_t *ue_context_p = rrc_gNB_get_ue_context_by_rnti(gnb_rrc_inst, rnti);
- if (ue_context_p != NULL) {
- LOG_W(NR_RRC, "Got RRC setup request for a already registered RNTI %x, dropping the old one and give up this rrcSetupRequest\n", ue_context_p->ue_context.rnti);
- rrc_gNB_remove_ue_context(gnb_rrc_inst, ue_context_p);
- } else {
+ {
rrcSetupRequest = &ul_ccch_msg->message.choice.c1->choice.rrcSetupRequest->rrcSetupRequest;
+ rrc_gNB_ue_context_t *ue_context_p = NULL;
if (NR_InitialUE_Identity_PR_randomValue == rrcSetupRequest->ue_Identity.present) {
/* randomValue BIT STRING (SIZE (39)) */
if (rrcSetupRequest->ue_Identity.choice.randomValue.size != 5) { // 39-bit random value
@@ -1515,7 +1312,7 @@ static int nr_rrc_gNB_decode_ccch(module_id_t module_id, rnti_t rnti, const uint
AssertFatal(false, "not implemented\n");
}
- ue_context_p = rrc_gNB_create_ue_context(rnti, gnb_rrc_inst, random_value);
+ ue_context_p = rrc_gNB_create_ue_context(rnti, gnb_rrc_inst, random_value, msg->gNB_DU_ue_id);
} else if (NR_InitialUE_Identity_PR_ng_5G_S_TMSI_Part1 == rrcSetupRequest->ue_Identity.present) {
/* TODO */
/* <5G-S-TMSI> = <5G-TMSI> 48-bit */
@@ -1534,20 +1331,14 @@ static int nr_rrc_gNB_decode_ccch(module_id_t module_id, rnti_t rnti, const uint
if ((ue_context_p = rrc_gNB_ue_context_5g_s_tmsi_exist(gnb_rrc_inst, s_tmsi_part1))) {
gNB_RRC_UE_t *UE = &ue_context_p->ue_context;
LOG_I(NR_RRC, " 5G-S-TMSI-Part1 exists, old rnti %04x => %04x\n", UE->rnti, rnti);
-
- // TODO: MAC structures should not be accessed directly from the RRC! An implementation using the F1 interface should be developed.
- if (!NODE_IS_CU(RC.nrrrc[0]->node_type)) {
- nr_rrc_mac_remove_ue(ue_context_p->ue_context.rnti);
- } else {
- AssertFatal(false, "not implemented: need to switch RNTI in MAC via DL RRC Message Transfer\n");
- }
+ AssertFatal(false, "not implemented\n");
/* replace rnti in the context */
UE->rnti = rnti;
} else {
LOG_I(NR_RRC, "UE %04x 5G-S-TMSI-Part1 doesn't exist, setting ng_5G_S_TMSI_Part1 => %ld\n", rnti, s_tmsi_part1);
- ue_context_p = rrc_gNB_create_ue_context(rnti, gnb_rrc_inst, s_tmsi_part1);
+ ue_context_p = rrc_gNB_create_ue_context(rnti, gnb_rrc_inst, s_tmsi_part1, msg->gNB_DU_ue_id);
if (ue_context_p == NULL) {
LOG_E(NR_RRC, "rrc_gNB_get_next_free_ue_context returned NULL\n");
return -1;
@@ -1561,7 +1352,7 @@ static int nr_rrc_gNB_decode_ccch(module_id_t module_id, rnti_t rnti, const uint
uint64_t random_value = 0;
memcpy(((uint8_t *)&random_value) + 3, rrcSetupRequest->ue_Identity.choice.randomValue.buf, rrcSetupRequest->ue_Identity.choice.randomValue.size);
- ue_context_p = rrc_gNB_create_ue_context(rnti, gnb_rrc_inst, random_value);
+ ue_context_p = rrc_gNB_create_ue_context(rnti, gnb_rrc_inst, random_value, msg->gNB_DU_ue_id);
LOG_E(NR_RRC, "RRCSetupRequest without random UE identity or S-TMSI not supported, let's reject the UE %04x\n", rnti);
rrc_gNB_generate_RRCReject(module_id, ue_context_p);
break;
@@ -1572,9 +1363,9 @@ static int nr_rrc_gNB_decode_ccch(module_id_t module_id, rnti_t rnti, const uint
UE->Srb[1].Active = 1;
rrc_gNB_generate_RRCSetup(module_id,
rnti,
- rrc_gNB_get_ue_context_by_rnti(gnb_rrc_inst, rnti),
- du_to_cu_rrc_container,
- du_to_cu_rrc_container_len);
+ ue_context_p,
+ msg->du2cu_rrc_container,
+ msg->du2cu_rrc_container_length);
}
break;
@@ -1583,86 +1374,81 @@ static int nr_rrc_gNB_decode_ccch(module_id_t module_id, rnti_t rnti, const uint
break;
case NR_UL_CCCH_MessageType__c1_PR_rrcReestablishmentRequest: {
- LOG_DUMPMSG(NR_RRC, DEBUG_RRC, (char *)(buffer), buffer_length, "[MSG] RRC Reestablishment Request\n");
+ LOG_DUMPMSG(NR_RRC,
+ DEBUG_RRC,
+ (char *)(msg->rrc_container),
+ msg->rrc_container_length,
+ "[MSG] RRC Reestablishment Request\n");
rrcReestablishmentRequest = ul_ccch_msg->message.choice.c1->choice.rrcReestablishmentRequest->rrcReestablishmentRequest;
const NR_ReestablishmentCause_t cause = rrcReestablishmentRequest.reestablishmentCause;
const long physCellId = rrcReestablishmentRequest.ue_Identity.physCellId;
LOG_I(NR_RRC,
- "UE %04x NR_RRCReestablishmentRequest cause %s\n",
+ "UE %04x physCellId %ld NR_RRCReestablishmentRequest cause %s\n",
rnti,
- ((cause == NR_ReestablishmentCause_otherFailure) ? "Other Failure"
- : (cause == NR_ReestablishmentCause_handoverFailure) ? "Handover Failure"
- : "reconfigurationFailure"));
- uint8_t xid = -1;
+ physCellId,
+ cause == NR_ReestablishmentCause_otherFailure
+ ? "Other Failure"
+ : (cause == NR_ReestablishmentCause_handoverFailure ? "Handover Failure" : "reconfigurationFailure"));
if (physCellId != gnb_rrc_inst->carrier.physCellId) {
/* UE was moving from previous cell so quickly that RRCReestablishment for previous cell was received in this cell */
LOG_E(NR_RRC,
" NR_RRCReestablishmentRequest ue_Identity.physCellId(%ld) is not equal to current physCellId(%ld), fallback to RRC establishment\n",
physCellId,
gnb_rrc_inst->carrier.physCellId);
- xid = rrc_gNB_generate_RRCSetup_for_RRCReestablishmentRequest(module_id, rnti, 0);
+ /* 38.401 8.7: "If the UE accessed from a gNB-DU other than the
+ * original one, the gNB-CU should trigger the UE Context Setup
+ * procedure" we did not implement this yet; TBD for Multi-DU */
+ AssertFatal(false, "not implemented\n");
break;
}
- LOG_I(NR_RRC, "physCellId: %ld\n", physCellId);
-
for (int i = 0; i < rrcReestablishmentRequest.ue_Identity.shortMAC_I.size; i++) {
LOG_D(NR_RRC, "rrcReestablishmentRequest.ue_Identity.shortMAC_I.buf[%d] = %x\n", i, rrcReestablishmentRequest.ue_Identity.shortMAC_I.buf[i]);
}
- // 3GPP TS 38.321 version 15.13.0 Section 7.1 Table 7.1-1: RNTI values
- if (rrcReestablishmentRequest.ue_Identity.c_RNTI < 0x1 || rrcReestablishmentRequest.ue_Identity.c_RNTI > 0xffef) {
- /* c_RNTI range error should not happen */
- LOG_E(NR_RRC, "NR_RRCReestablishmentRequest c_RNTI range error, fallback to RRC establishment\n");
- xid = rrc_gNB_generate_RRCSetup_for_RRCReestablishmentRequest(module_id, rnti, 0);
+ rnti_t old_rnti = rrcReestablishmentRequest.ue_Identity.c_RNTI;
+ // TODO: we need to check within a specific DU!
+ rrc_gNB_ue_context_t *ue_context_p = rrc_gNB_get_ue_context_by_rnti(gnb_rrc_inst, old_rnti);
+ gNB_RRC_UE_t *UE = &ue_context_p->ue_context;
+ /* in case we need to do RRC Setup, give the UE a new random identity */
+ uint64_t random_value;
+ fill_random(&random_value, sizeof(random_value));
+ random_value = random_value & 0x7fffffffff; /* random value is 39 bits */
+ if (ue_context_p == NULL) {
+ LOG_E(NR_RRC, "NR_RRCReestablishmentRequest without UE context, fallback to RRC setup\n");
+ ue_context_p = rrc_gNB_create_ue_context(rnti, gnb_rrc_inst, random_value, msg->gNB_DU_ue_id);
+ ue_context_p->ue_context.Srb[1].Active = 1;
+ rrc_gNB_generate_RRCSetup(module_id, rnti, ue_context_p, msg->du2cu_rrc_container, msg->du2cu_rrc_container_length);
break;
}
- rnti_t c_rnti = rrcReestablishmentRequest.ue_Identity.c_RNTI;
- LOG_I(NR_RRC, "c_RNTI: %04x\n", c_rnti);
- rrc_gNB_ue_context_t *ue_context_p = rrc_gNB_get_ue_context_by_rnti(gnb_rrc_inst, c_rnti);
- gNB_RRC_UE_t *UE = &ue_context_p->ue_context;
- if (ue_context_p == NULL) {
- LOG_E(NR_RRC, "NR_RRCReestablishmentRequest without UE context, fallback to RRC establishment\n");
- xid = rrc_gNB_generate_RRCSetup_for_RRCReestablishmentRequest(module_id, c_rnti, 0);
- break;
- }
- // c-plane not end
- if ((UE->StatusRrc != NR_RRC_RECONFIGURED) && (UE->reestablishment_cause == NR_ReestablishmentCause_spare1)) {
- LOG_E(NR_RRC, "NR_RRCReestablishmentRequest (UE %x c-plane is not end), RRC establishment failed\n", c_rnti);
- /* TODO RRC Release ? */
+ // 3GPP TS 38.321 version 15.13.0 Section 7.1 Table 7.1-1: RNTI values
+ if (rrcReestablishmentRequest.ue_Identity.c_RNTI < 0x1 || rrcReestablishmentRequest.ue_Identity.c_RNTI > 0xffef) {
+ /* c_RNTI range error should not happen */
+ LOG_E(NR_RRC,
+ "NR_RRCReestablishmentRequest c_RNTI %04lx range error, fallback to RRC setup\n",
+ rrcReestablishmentRequest.ue_Identity.c_RNTI);
+ ue_context_p = rrc_gNB_create_ue_context(rnti, gnb_rrc_inst, random_value, msg->gNB_DU_ue_id);
+ ue_context_p->ue_context.Srb[1].Active = 1;
+ rrc_gNB_generate_RRCSetup(module_id, rnti, ue_context_p, msg->du2cu_rrc_container, msg->du2cu_rrc_container_length);
break;
}
/* TODO: start timer in ITTI and drop UE if it does not come back */
- (void) xid; /* xid currently not used */
- // Insert C-RNTI to map
- for (int i = 0; i < MAX_MOBILES_PER_GNB; i++) {
- nr_reestablish_rnti_map_t *nr_reestablish_rnti_map = &gnb_rrc_inst->nr_reestablish_rnti_map[i];
- LOG_I(NR_RRC, "Insert nr_reestablish_rnti_map[%d] UEid: %lx, RNTI: %04x\n", i, nr_reestablish_rnti_map->ue_id, nr_reestablish_rnti_map->c_rnti);
- if (nr_reestablish_rnti_map->ue_id == 0) {
- nr_reestablish_rnti_map->ue_id = rnti;
- nr_reestablish_rnti_map->c_rnti = c_rnti;
- LOG_W(NR_RRC, "Insert nr_reestablish_rnti_map[%d] UEid: %lx, RNTI: %04x bug in UEid to fix \n", i, nr_reestablish_rnti_map->ue_id, nr_reestablish_rnti_map->c_rnti);
- break;
- }
- }
+ // update with new RNTI, and update secondary UE association
+ UE->rnti = rnti;
+ cu_remove_f1_ue_data(UE->rrc_ue_id);
+ f1_ue_data_t ue_data = {.secondary_ue = rnti};
+ cu_add_f1_ue_data(UE->rrc_ue_id, &ue_data);
UE->reestablishment_cause = cause;
LOG_D(NR_RRC, "Accept RRCReestablishmentRequest from UE physCellId %ld cause %ld\n", physCellId, cause);
- UE->primaryCC_id = 0;
- // LG COMMENT Idx = (ue_mod_idP * NB_RB_MAX) + DCCH;
- Idx = DCCH;
- // SRB1
- UE->Srb[1].Active = 1;
- // SRB2: set it to go through SRB1 with id 1 (DCCH)
- UE->Srb[2].Active = 1;
- protocol_ctxt_t ctxt = {.rntiMaybeUEid = rnti, .module_id = module_id, .instance = module_id, .enb_flag = 1, .eNB_index = module_id};
- rrc_gNB_generate_RRCReestablishment(&ctxt, ue_context_p, du_to_cu_rrc_container, gnb_rrc_inst->carrier.servingcellconfigcommon, 0);
-
- LOG_I(NR_RRC, "CALLING RLC CONFIG SRB1 (rbid %d)\n", Idx);
+ rrc_gNB_generate_RRCReestablishment(ue_context_p,
+ msg->du2cu_rrc_container,
+ gnb_rrc_inst->carrier.servingcellconfigcommon,
+ old_rnti);
} break;
case NR_UL_CCCH_MessageType__c1_PR_rrcSystemInfoRequest:
@@ -1721,48 +1507,18 @@ static void rrc_gNB_process_MeasurementReport(rrc_gNB_ue_context_t *ue_context,
}
static int handle_rrcReestablishmentComplete(const protocol_ctxt_t *const ctxt_pP,
+ rrc_gNB_ue_context_t *ue_context_p,
const NR_RRCReestablishmentComplete_t *reestablishment_complete)
{
- rnti_t reestablish_rnti = 0;
- gNB_RRC_INST *gnb_rrc_inst = RC.nrrrc[ctxt_pP->module_id];
- rrc_gNB_ue_context_t *ue_context_p = NULL;
- gNB_RRC_UE_t *UE = NULL;
- // Select C-RNTI from map
- for (int i = 0; i < MAX_MOBILES_PER_GNB; i++) {
- nr_reestablish_rnti_map_t *nr_reestablish_rnti_map = &gnb_rrc_inst->nr_reestablish_rnti_map[i];
- LOG_I(NR_RRC,
- "nr_reestablish_rnti_map[%d] UEid %lx, RNTI %04x, ctxt_pP->rntiMaybeUEid: %lx\n",
- i,
- nr_reestablish_rnti_map->ue_id,
- nr_reestablish_rnti_map->c_rnti,
- ctxt_pP->rntiMaybeUEid);
- if (nr_reestablish_rnti_map->ue_id == ctxt_pP->rntiMaybeUEid) {
- LOG_I(NR_RRC,
- "Removing nr_reestablish_rnti_map[%d] UEid %lx, RNTI %04x\n",
- i,
- nr_reestablish_rnti_map->ue_id,
- nr_reestablish_rnti_map->c_rnti);
- reestablish_rnti = nr_reestablish_rnti_map->c_rnti;
- ue_context_p = rrc_gNB_get_ue_context_by_rnti(gnb_rrc_inst, reestablish_rnti);
- UE = &ue_context_p->ue_context;
- break;
- }
- }
-
- if (ue_context_p == NULL || UE == NULL) {
- LOG_E(RRC, "no UE found for reestablishment. ERROR: should send reply\n");
- return -1;
- }
+ DevAssert(ue_context_p != NULL);
+ gNB_RRC_UE_t *UE = &ue_context_p->ue_context;
DevAssert(reestablishment_complete->criticalExtensions.present
== NR_RRCReestablishmentComplete__criticalExtensions_PR_rrcReestablishmentComplete);
rrc_gNB_process_RRCReestablishmentComplete(ctxt_pP,
- reestablish_rnti,
ue_context_p,
reestablishment_complete->rrc_TransactionIdentifier);
- nr_rrc_mac_remove_ue(reestablish_rnti);
-
UE->ue_reestablishment_counter++;
return 0;
}
@@ -1954,18 +1710,21 @@ static void handle_rrcReconfigurationComplete(const protocol_ctxt_t *const ctxt_
case RRC_DEFAULT_RECONF:
rrc_gNB_send_NGAP_INITIAL_CONTEXT_SETUP_RESP(ctxt_pP, ue_context_p);
break;
+ case RRC_REESTABLISH_COMPLETE:
+ /* do nothing */
+ break;
default:
- LOG_E(RRC, "Received unexpected xid: %d\n", xid);
+ LOG_E(RRC, "Received unexpected transaction type %d for xid %d\n", UE->xids[xid], xid);
successful_reconfig = false;
break;
}
}
gNB_RRC_INST *rrc = RC.nrrrc[0];
+ f1_ue_data_t ue_data = cu_get_f1_ue_data(UE->rrc_ue_id);
f1ap_ue_context_modif_req_t ue_context_modif_req = {
- .gNB_CU_ue_id = 0xffffffff, /* filled by F1 for the moment */
- .gNB_DU_ue_id = 0xffffffff, /* filled by F1 for the moment */
- .rnti = UE->rnti,
+ .gNB_CU_ue_id = UE->rrc_ue_id,
+ .gNB_DU_ue_id = ue_data.secondary_ue,
.mcc = rrc->configuration.mcc[0],
.mnc = rrc->configuration.mnc[0],
.mnc_digit_length = rrc->configuration.mnc_digit_length[0],
@@ -1984,6 +1743,13 @@ int rrc_gNB_decode_dcch(const protocol_ctxt_t *const ctxt_pP,
{
gNB_RRC_INST *gnb_rrc_inst = RC.nrrrc[ctxt_pP->module_id];
+ /* we look up by CU UE ID! Do NOT change back to RNTI! */
+ rrc_gNB_ue_context_t *ue_context_p = rrc_gNB_get_ue_context(gnb_rrc_inst, ctxt_pP->rntiMaybeUEid);
+ if (!ue_context_p) {
+ LOG_E(RRC, "could not find UE context for CU UE ID %lu, aborting transaction\n", ctxt_pP->rntiMaybeUEid);
+ return -1;
+ }
+
if ((Srb_id != 1) && (Srb_id != 2)) {
LOG_E(NR_RRC, "Received message on SRB%ld, should not have ...\n", Srb_id);
} else {
@@ -2011,8 +1777,6 @@ int rrc_gNB_decode_dcch(const protocol_ctxt_t *const ctxt_pP,
xer_fprint(stdout, &asn_DEF_NR_UL_DCCH_Message, (void *)ul_dcch_msg);
}
- rrc_gNB_ue_context_t *ue_context_p = rrc_gNB_get_ue_context_by_rnti(gnb_rrc_inst, ctxt_pP->rntiMaybeUEid);
-
if (ul_dcch_msg->message.present == NR_UL_DCCH_MessageType_PR_c1) {
switch (ul_dcch_msg->message.choice.c1->present) {
case NR_UL_DCCH_MessageType__c1_PR_NOTHING:
@@ -2104,7 +1868,7 @@ int rrc_gNB_decode_dcch(const protocol_ctxt_t *const ctxt_pP,
break;
case NR_UL_DCCH_MessageType__c1_PR_rrcReestablishmentComplete:
- if (handle_rrcReestablishmentComplete(ctxt_pP, ul_dcch_msg->message.choice.c1->choice.rrcReestablishmentComplete)
+ if (handle_rrcReestablishmentComplete(ctxt_pP, ue_context_p, ul_dcch_msg->message.choice.c1->choice.rrcReestablishmentComplete)
== -1)
return -1;
break;
@@ -2222,7 +1986,7 @@ void rrc_gNB_process_initial_ul_rrc_message(const f1ap_initial_ul_rrc_message_t
i = 0;
LOG_W(RRC, "initial UL RRC message nr_cellid %ld does not match RRC's %ld\n", ul_rrc->nr_cellid, RC.nrrrc[0]->nr_cellid);
}
- nr_rrc_gNB_decode_ccch(i, ul_rrc->crnti, ul_rrc->rrc_container, ul_rrc->rrc_container_length, ul_rrc->du2cu_rrc_container, ul_rrc->du2cu_rrc_container_length);
+ nr_rrc_gNB_decode_ccch(i, ul_rrc);
if (ul_rrc->rrc_container)
free(ul_rrc->rrc_container);
@@ -2246,7 +2010,11 @@ static void rrc_CU_process_ue_context_setup_response(MessageDef *msg_p, instance
{
f1ap_ue_context_setup_t *resp = &F1AP_UE_CONTEXT_SETUP_RESP(msg_p);
gNB_RRC_INST *rrc = RC.nrrrc[instance];
- rrc_gNB_ue_context_t *ue_context_p = rrc_gNB_get_ue_context_by_rnti(rrc, resp->rnti);
+ rrc_gNB_ue_context_t *ue_context_p = rrc_gNB_get_ue_context(rrc, resp->gNB_CU_ue_id);
+ if (!ue_context_p) {
+ LOG_E(RRC, "could not find UE context for CU UE ID %u, aborting transaction\n", resp->gNB_CU_ue_id);
+ return;
+ }
gNB_RRC_UE_t *UE = &ue_context_p->ue_context;
NR_CellGroupConfig_t *cellGroupConfig = NULL;
@@ -2275,10 +2043,14 @@ static void rrc_CU_process_ue_context_release_request(MessageDef *msg_p)
const int instance = 0;
f1ap_ue_context_release_req_t *req = &F1AP_UE_CONTEXT_RELEASE_REQ(msg_p);
gNB_RRC_INST *rrc = RC.nrrrc[instance];
- rrc_gNB_ue_context_t *ue_context_p = rrc_gNB_get_ue_context_by_rnti(rrc, req->rnti);
+ rrc_gNB_ue_context_t *ue_context_p = rrc_gNB_get_ue_context(rrc, req->gNB_CU_ue_id);
+ if (!ue_context_p) {
+ LOG_E(RRC, "could not find UE context for CU UE ID %u, aborting transaction\n", req->gNB_CU_ue_id);
+ return;
+ }
/* TODO: marshall types correctly */
- LOG_I(NR_RRC, "received UE Context Release Request for UE %04x, forwarding to AMF\n", req->rnti);
+ LOG_I(NR_RRC, "received UE Context Release Request for UE %u, forwarding to AMF\n", req->gNB_CU_ue_id);
rrc_gNB_send_NGAP_UE_CONTEXT_RELEASE_REQ(instance,
ue_context_p,
NGAP_CAUSE_RADIO_NETWORK,
@@ -2290,29 +2062,37 @@ static void rrc_CU_process_ue_context_release_complete(MessageDef *msg_p)
const int instance = 0;
f1ap_ue_context_release_complete_t *complete = &F1AP_UE_CONTEXT_RELEASE_COMPLETE(msg_p);
gNB_RRC_INST *rrc = RC.nrrrc[instance];
- rrc_gNB_ue_context_t *ue_context_p = rrc_gNB_get_ue_context_by_rnti(rrc, complete->rnti);
+ rrc_gNB_ue_context_t *ue_context_p = rrc_gNB_get_ue_context(rrc, complete->gNB_CU_ue_id);
+ if (!ue_context_p) {
+ LOG_E(RRC, "could not find UE context for CU UE ID %u, aborting transaction\n", complete->gNB_CU_ue_id);
+ return;
+ }
gNB_RRC_UE_t *UE = &ue_context_p->ue_context;
- nr_pdcp_remove_UE(UE->rnti);
- newGtpuDeleteAllTunnels(instance, UE->rnti);
- rrc_gNB_send_NGAP_UE_CONTEXT_RELEASE_COMPLETE(instance, UE->gNB_ue_ngap_id);
- LOG_I(NR_RRC, "removed UE %04x \n", UE->rnti);
+ nr_pdcp_remove_UE(UE->rrc_ue_id);
+ newGtpuDeleteAllTunnels(instance, UE->rrc_ue_id);
+ rrc_gNB_send_NGAP_UE_CONTEXT_RELEASE_COMPLETE(instance, UE->rrc_ue_id);
+ LOG_I(NR_RRC, "removed UE CU UE ID %u/RNTI %04x \n", UE->rrc_ue_id, UE->rnti);
rrc_gNB_remove_ue_context(rrc, ue_context_p);
}
static void rrc_CU_process_ue_context_modification_response(MessageDef *msg_p, instance_t instance)
{
f1ap_ue_context_modif_resp_t *resp = &F1AP_UE_CONTEXT_MODIFICATION_RESP(msg_p);
- protocol_ctxt_t ctxt = {.rntiMaybeUEid = resp->rnti, .module_id = instance, .instance = instance, .enb_flag = 1, .eNB_index = instance};
+ protocol_ctxt_t ctxt = {.rntiMaybeUEid = resp->gNB_CU_ue_id, .module_id = instance, .instance = instance, .enb_flag = 1, .eNB_index = instance};
gNB_RRC_INST *rrc = RC.nrrrc[ctxt.module_id];
- rrc_gNB_ue_context_t *ue_context_p = rrc_gNB_get_ue_context_by_rnti(rrc, resp->rnti);
+ rrc_gNB_ue_context_t *ue_context_p = rrc_gNB_get_ue_context(rrc, resp->gNB_CU_ue_id);
+ if (!ue_context_p) {
+ LOG_E(RRC, "could not find UE context for CU UE ID %u, aborting transaction\n", resp->gNB_CU_ue_id);
+ return;
+ }
gNB_RRC_UE_t *UE = &ue_context_p->ue_context;
if (resp->drbs_to_be_setup_length > 0) {
e1ap_bearer_setup_req_t req = {0};
req.numPDUSessionsMod = UE->nb_of_pdusessions;
- req.gNB_cu_cp_ue_id = UE->gNB_ue_ngap_id;
- req.rnti = UE->rnti;
+ req.gNB_cu_cp_ue_id = UE->rrc_ue_id;
+ req.gNB_cu_up_ue_id = UE->rrc_ue_id;
for (int i = 0; i < req.numPDUSessionsMod; i++) {
req.pduSessionMod[i].numDRB2Modify = resp->drbs_to_be_setup_length;
for (int j = 0; j < resp->drbs_to_be_setup_length; j++) {
@@ -2561,10 +2341,10 @@ void prepare_and_send_ue_context_modification_f1(rrc_gNB_ue_context_t *ue_contex
srbs[0].lcid = 2;
}
+ f1_ue_data_t ue_data = cu_get_f1_ue_data(UE->rrc_ue_id);
f1ap_ue_context_modif_req_t ue_context_modif_req = {
- .gNB_CU_ue_id = 0xffffffff, /* filled by F1 for the moment */
- .gNB_DU_ue_id = 0xffffffff, /* filled by F1 for the moment */
- .rnti = UE->rnti,
+ .gNB_CU_ue_id = UE->rrc_ue_id,
+ .gNB_DU_ue_id = ue_data.secondary_ue,
.mcc = rrc->configuration.mcc[0],
.mnc = rrc->configuration.mnc[0],
.mnc_digit_length = rrc->configuration.mnc_digit_length[0],
@@ -2582,9 +2362,16 @@ void rrc_gNB_process_e1_bearer_context_setup_resp(e1ap_bearer_setup_resp_t *resp
// Find the UE context from UE ID and send ITTI message to F1AP to send UE context modification message to DU
rrc_gNB_ue_context_t *ue_context_p = rrc_gNB_get_ue_context(RC.nrrrc[instance], resp->gNB_cu_cp_ue_id);
- gNB_RRC_UE_t *UE = &ue_context_p->ue_context;
+ AssertFatal(ue_context_p != NULL, "did not find UE with CU UE ID %d\n", resp->gNB_cu_cp_ue_id);
protocol_ctxt_t ctxt = {0};
- PROTOCOL_CTXT_SET_BY_MODULE_ID(&ctxt, 0, GNB_FLAG_YES, UE->rnti, 0, 0, 0);
+ PROTOCOL_CTXT_SET_BY_MODULE_ID(&ctxt, 0, GNB_FLAG_YES, resp->gNB_cu_cp_ue_id, 0, 0, 0);
+
+ // currently: we don't have "infrastructure" to save the CU-UP UE ID, so we
+ // assume (and below check) that CU-UP UE ID == CU-CP UE ID
+ AssertFatal(resp->gNB_cu_cp_ue_id == resp->gNB_cu_up_ue_id,
+ "cannot handle CU-UP UE ID different from CU-CP UE ID (%d vs %d)\n",
+ resp->gNB_cu_cp_ue_id,
+ resp->gNB_cu_up_ue_id);
gtpv1u_gnb_create_tunnel_resp_t create_tunnel_resp={0};
create_tunnel_resp.num_tunnels = resp->numPDUSessions;
@@ -2624,6 +2411,36 @@ static void print_rrc_meas(FILE *f, const NR_MeasResults_t *measresults)
}
}
+static const char *get_rrc_connection_status_text(NR_UE_STATE_t state)
+{
+ switch (state) {
+ case NR_RRC_INACTIVE: return "inactive";
+ case NR_RRC_IDLE: return "idle";
+ case NR_RRC_SI_RECEIVED: return "SI-received";
+ case NR_RRC_CONNECTED: return "connected";
+ case NR_RRC_RECONFIGURED: return "reconfigured";
+ case NR_RRC_HO_EXECUTION: return "HO-execution";
+ default: AssertFatal(false, "illegal RRC state %d\n", state); return "illegal";
+ }
+ return "illegal";
+}
+
+static const char *get_pdusession_status_text(pdu_session_status_t status)
+{
+ switch (status) {
+ case PDU_SESSION_STATUS_NEW: return "new";
+ case PDU_SESSION_STATUS_DONE: return "done";
+ case PDU_SESSION_STATUS_ESTABLISHED: return "established";
+ case PDU_SESSION_STATUS_REESTABLISHED: return "reestablished";
+ case PDU_SESSION_STATUS_TOMODIFY: return "to-modify";
+ case PDU_SESSION_STATUS_FAILED: return "failed";
+ case PDU_SESSION_STATUS_TORELEASE: return "to-release";
+ case PDU_SESSION_STATUS_RELEASED: return "released";
+ default: AssertFatal(false, "illegal PDU status code %d\n", status); return "illegal";
+ }
+ return "illegal";
+}
+
static void write_rrc_stats(const gNB_RRC_INST *rrc)
{
const char *filename = "nrRRC_stats.log";
@@ -2633,19 +2450,33 @@ static void write_rrc_stats(const gNB_RRC_INST *rrc)
return;
}
+ int i = 0;
rrc_gNB_ue_context_t *ue_context_p = NULL;
/* cast is necessary to eliminate warning "discards ‘const’ qualifier" */
RB_FOREACH(ue_context_p, rrc_nr_ue_tree_s, &((gNB_RRC_INST *)rrc)->rrc_ue_head)
{
const gNB_RRC_UE_t *ue_ctxt = &ue_context_p->ue_context;
- const rnti_t rnti = ue_ctxt->rnti;
-
- fprintf(f, "NR RRC UE rnti %04x:", rnti);
+ f1_ue_data_t ue_data = cu_get_f1_ue_data(ue_ctxt->rrc_ue_id);
+ fprintf(f,
+ "UE %d CU UE ID %d DU UE ID %d RNTI %04x random identity %016lx",
+ i,
+ ue_ctxt->rrc_ue_id,
+ ue_data.secondary_ue,
+ ue_ctxt->rnti,
+ ue_ctxt->random_ue_identity);
if (ue_ctxt->Initialue_identity_5g_s_TMSI.presence)
fprintf(f, " S-TMSI %x", ue_ctxt->Initialue_identity_5g_s_TMSI.fiveg_tmsi);
+ fprintf(f, ":\n");
- fprintf(f, "\n");
+ fprintf(f, " RRC status %s\n", get_rrc_connection_status_text(ue_ctxt->StatusRrc));
+
+ if (ue_ctxt->nb_of_pdusessions == 0)
+ fprintf(f, " (no PDU sessions)\n");
+ for (int nb_pdu = 0; nb_pdu < ue_ctxt->nb_of_pdusessions; ++nb_pdu) {
+ const rrc_pdu_session_param_t *pdu = &ue_ctxt->pduSession[nb_pdu];
+ fprintf(f, " PDU session %d ID %d status %s\n", nb_pdu, pdu->param.pdusession_id, get_pdusession_status_text(pdu->status));
+ }
if (ue_ctxt->UE_Capability_nr) {
fprintf(f,
@@ -2659,6 +2490,7 @@ static void write_rrc_stats(const gNB_RRC_INST *rrc)
if (ue_ctxt->measResults)
print_rrc_meas(f, ue_ctxt->measResults);
+ ++i;
}
fclose(f);
@@ -2714,7 +2546,7 @@ void *rrc_gnb_task(void *args_p) {
PROTOCOL_CTXT_SET_BY_INSTANCE(&ctxt,
instance,
GNB_FLAG_YES,
- F1AP_UL_RRC_MESSAGE(msg_p).rnti,
+ F1AP_UL_RRC_MESSAGE(msg_p).gNB_CU_ue_id,
0,
0);
LOG_D(NR_RRC,
@@ -2827,25 +2659,17 @@ void *rrc_gnb_task(void *args_p) {
}
}
+typedef struct deliver_ue_ctxt_setup_data_t {
+ gNB_RRC_INST *rrc;
+ f1ap_ue_context_setup_t *setup_req;
+} deliver_ue_ctxt_setup_data_t;
static void rrc_deliver_ue_ctxt_setup_req(void *deliver_pdu_data, ue_id_t ue_id, int srb_id, char *buf, int size, int sdu_id)
{
DevAssert(deliver_pdu_data != NULL);
- gNB_RRC_INST *rrc = deliver_pdu_data;
- f1ap_ue_context_setup_t ue_context_setup_req = {
- .gNB_CU_ue_id = 0xffffffff, /* filled by F1 for the moment */
- .gNB_DU_ue_id = 0xffffffff, /* filled by F1 for the moment */
- .rnti = ue_id,
- .mcc = rrc->configuration.mcc[0],
- .mnc = rrc->configuration.mnc[0],
- .mnc_digit_length = rrc->configuration.mnc_digit_length[0],
- .nr_cellid = rrc->nr_cellid,
- .servCellId = 0, /* TODO: correct value? */
- .srbs_to_be_setup = 0, /* no new SRBs */
- .drbs_to_be_setup = 0, /* no new DRBs */
- .rrc_container = (uint8_t*) buf, /* security mode command */
- .rrc_container_length = size,
- };
- rrc->mac_rrc.ue_context_setup_request(&ue_context_setup_req);
+ deliver_ue_ctxt_setup_data_t *data = deliver_pdu_data;
+ data->setup_req->rrc_container = (uint8_t*)buf;
+ data->setup_req->rrc_container_length = size;
+ data->rrc->mac_rrc.ue_context_setup_request(data->setup_req);
}
//-----------------------------------------------------------------------------
@@ -2870,7 +2694,20 @@ rrc_gNB_generate_SecurityModeCommand(
AssertFatal(!NODE_IS_DU(rrc->node_type), "illegal node type DU!\n");
/* the callback will fill the UE context setup request and forward it */
- nr_pdcp_data_req_srb(ctxt_pP->rntiMaybeUEid, DCCH, rrc_gNB_mui++, size, buffer, rrc_deliver_ue_ctxt_setup_req, rrc);
+ f1_ue_data_t ue_data = cu_get_f1_ue_data(ue_p->rrc_ue_id);
+ f1ap_ue_context_setup_t ue_context_setup_req = {
+ .gNB_CU_ue_id = ue_p->rrc_ue_id,
+ .gNB_DU_ue_id = ue_data.secondary_ue,
+ .mcc = rrc->configuration.mcc[0],
+ .mnc = rrc->configuration.mnc[0],
+ .mnc_digit_length = rrc->configuration.mnc_digit_length[0],
+ .nr_cellid = rrc->nr_cellid,
+ .servCellId = 0, /* TODO: correct value? */
+ .srbs_to_be_setup = 0, /* no new SRBs */
+ .drbs_to_be_setup = 0, /* no new DRBs */
+ };
+ deliver_ue_ctxt_setup_data_t data = {.rrc = rrc, .setup_req = &ue_context_setup_req};
+ nr_pdcp_data_req_srb(ctxt_pP->rntiMaybeUEid, DCCH, rrc_gNB_mui++, size, buffer, rrc_deliver_ue_ctxt_setup_req, &data);
}
void
@@ -2896,25 +2733,21 @@ rrc_gNB_generate_UECapabilityEnquiry(
gNB_RRC_INST *rrc = RC.nrrrc[ctxt_pP->module_id];
AssertFatal(!NODE_IS_DU(rrc->node_type), "illegal node type DU!\n");
- nr_pdcp_data_req_srb(ctxt_pP->rntiMaybeUEid, DCCH, rrc_gNB_mui++, size, buffer, deliver_pdu_srb_f1, rrc);
+ const gNB_RRC_UE_t *ue = &ue_context_pP->ue_context;
+ nr_rrc_transfer_protected_rrc_message(rrc, ue, DCCH, buffer, size);
}
+typedef struct deliver_ue_ctxt_release_data_t {
+ gNB_RRC_INST *rrc;
+ f1ap_ue_context_release_cmd_t *release_cmd;
+} deliver_ue_ctxt_release_data_t;
static void rrc_deliver_ue_ctxt_release_cmd(void *deliver_pdu_data, ue_id_t ue_id, int srb_id, char *buf, int size, int sdu_id)
{
DevAssert(deliver_pdu_data != NULL);
- gNB_RRC_INST *rrc = deliver_pdu_data;
- uint8_t *rrc_container = malloc(size);
- AssertFatal(rrc_container != NULL, "out of memory\n");
- memcpy(rrc_container, buf, size);
- f1ap_ue_context_release_cmd_t ue_context_release_cmd = {
- .rnti = ue_id, /* TODO: proper IDs! */
- .cause = F1AP_CAUSE_RADIO_NETWORK,
- .cause_value = 10, // 10 = F1AP_CauseRadioNetwork_normal_release
- .srb_id = srb_id,
- .rrc_container = rrc_container,
- .rrc_container_length = size,
- };
- rrc->mac_rrc.ue_context_release_command(&ue_context_release_cmd);
+ deliver_ue_ctxt_release_data_t *data = deliver_pdu_data;
+ data->release_cmd->rrc_container = (uint8_t*) buf;
+ data->release_cmd->rrc_container_length = size;
+ data->rrc->mac_rrc.ue_context_release_command(data->release_cmd);
}
//-----------------------------------------------------------------------------
@@ -2938,7 +2771,17 @@ rrc_gNB_generate_RRCRelease(
size);
gNB_RRC_INST *rrc = RC.nrrrc[ctxt_pP->module_id];
- nr_pdcp_data_req_srb(ctxt_pP->rntiMaybeUEid, DCCH, rrc_gNB_mui++, size, buffer, rrc_deliver_ue_ctxt_release_cmd, rrc);
+ const gNB_RRC_UE_t *UE = &ue_context_pP->ue_context;
+ f1_ue_data_t ue_data = cu_get_f1_ue_data(UE->rrc_ue_id);
+ f1ap_ue_context_release_cmd_t ue_context_release_cmd = {
+ .gNB_CU_ue_id = UE->rrc_ue_id,
+ .gNB_DU_ue_id = ue_data.secondary_ue,
+ .cause = F1AP_CAUSE_RADIO_NETWORK,
+ .cause_value = 10, // 10 = F1AP_CauseRadioNetwork_normal_release
+ .srb_id = DCCH,
+ };
+ deliver_ue_ctxt_release_data_t data = {.rrc = rrc, .release_cmd = &ue_context_release_cmd};
+ nr_pdcp_data_req_srb(ctxt_pP->rntiMaybeUEid, DCCH, rrc_gNB_mui++, size, buffer, rrc_deliver_ue_ctxt_release_cmd, &data);
/* UE will be freed after UE context release complete */
}
diff --git a/openair2/RRC/NR/rrc_gNB_GTPV1U.c b/openair2/RRC/NR/rrc_gNB_GTPV1U.c
index e7bbe5835e..3ef3e62d51 100644
--- a/openair2/RRC/NR/rrc_gNB_GTPV1U.c
+++ b/openair2/RRC/NR/rrc_gNB_GTPV1U.c
@@ -52,7 +52,8 @@ int rrc_gNB_process_GTPV1U_CREATE_TUNNEL_RESP(const protocol_ctxt_t *const ctxt_
}
LOG_D(RRC, PROTOCOL_RRC_CTXT_UE_FMT " RX CREATE_TUNNEL_RESP num tunnels %u \n", PROTOCOL_RRC_CTXT_UE_ARGS(ctxt_pP), create_tunnel_resp_pP->num_tunnels);
- rrc_gNB_ue_context_t *ue_context_p = rrc_gNB_get_ue_context_by_rnti(RC.nrrrc[ctxt_pP->module_id], ctxt_pP->rntiMaybeUEid);
+ /* we look up by CU UE ID! Do NOT change back to RNTI! */
+ rrc_gNB_ue_context_t *ue_context_p = rrc_gNB_get_ue_context(RC.nrrrc[ctxt_pP->module_id], ctxt_pP->rntiMaybeUEid);
if (!ue_context_p) {
LOG_E(NR_RRC, "UE table error\n");
return -1;
@@ -83,7 +84,8 @@ int nr_rrc_gNB_process_GTPV1U_CREATE_TUNNEL_RESP(const protocol_ctxt_t *const ct
}
LOG_D(NR_RRC, PROTOCOL_NR_RRC_CTXT_UE_FMT " RX CREATE_TUNNEL_RESP num tunnels %u \n", PROTOCOL_NR_RRC_CTXT_UE_ARGS(ctxt_pP), create_tunnel_resp_pP->num_tunnels);
- rrc_gNB_ue_context_t *ue_context_p = rrc_gNB_get_ue_context_by_rnti(RC.nrrrc[ctxt_pP->module_id], ctxt_pP->rntiMaybeUEid);
+ /* we look up by CU UE ID! Do NOT change back to RNTI! */
+ rrc_gNB_ue_context_t *ue_context_p = rrc_gNB_get_ue_context(RC.nrrrc[ctxt_pP->module_id], ctxt_pP->rntiMaybeUEid);
if (!ue_context_p) {
LOG_E(NR_RRC, "UE table error\n");
return -1;
diff --git a/openair2/RRC/NR/rrc_gNB_NGAP.c b/openair2/RRC/NR/rrc_gNB_NGAP.c
index f0a7f3b90f..8a9a08abd7 100644
--- a/openair2/RRC/NR/rrc_gNB_NGAP.c
+++ b/openair2/RRC/NR/rrc_gNB_NGAP.c
@@ -58,6 +58,7 @@
#include "NR_UE-CapabilityRAT-ContainerList.h"
#include "NGAP_CauseRadioNetwork.h"
#include "f1ap_messages_types.h"
+#include "openair2/F1AP/f1ap_ids.h"
#include "openair2/E1AP/e1ap_asnc.h"
#include "NGAP_asn_constant.h"
#include "NGAP_PDUSessionResourceSetupRequestTransfer.h"
@@ -182,7 +183,7 @@ rrc_gNB_send_NGAP_NAS_FIRST_REQ(
ngap_nas_first_req_t *req = &NGAP_NAS_FIRST_REQ(message_p);
memset(req, 0, sizeof(*req));
- req->gNB_ue_ngap_id = UE->gNB_ue_ngap_id;
+ req->gNB_ue_ngap_id = UE->rrc_ue_id;
/* Assume that cause is coded in the same way in RRC and NGap, just check that the value is in NGap range */
AssertFatal(UE->establishment_cause < NGAP_RRC_CAUSE_LAST, "Establishment cause invalid (%jd/%d) for gNB %d!", UE->establishment_cause, NGAP_RRC_CAUSE_LAST, ctxt_pP->module_id);
@@ -370,7 +371,7 @@ int rrc_gNB_process_NGAP_INITIAL_CONTEXT_SETUP_REQ(MessageDef *msg_p, instance_t
itti_send_msg_to_task(TASK_NGAP, instance, msg_fail_p);
return (-1);
}
- PROTOCOL_CTXT_SET_BY_INSTANCE(&ctxt, instance, GNB_FLAG_YES, UE->rnti, 0, 0);
+ PROTOCOL_CTXT_SET_BY_INSTANCE(&ctxt, instance, GNB_FLAG_YES, UE->rrc_ue_id, 0, 0);
UE->amf_ue_ngap_id = req->amf_ue_ngap_id;
uint8_t nb_pdusessions_tosetup = req->nb_of_pdusessions;
if (nb_pdusessions_tosetup) {
@@ -391,7 +392,7 @@ int rrc_gNB_process_NGAP_INITIAL_CONTEXT_SETUP_REQ(MessageDef *msg_p, instance_t
memcpy(create_tunnel_req.dst_addr[i].buffer, req->pdusession_param[i].upf_addr.buffer, sizeof(create_tunnel_req.dst_addr[i].buffer));
LOG_I(NR_RRC, "PDUSESSION SETUP: local index %d teid %u, pdusession id %d \n", i, create_tunnel_req.outgoing_teid[i], create_tunnel_req.pdusession_id[i]);
}
- create_tunnel_req.ue_id = UE->rnti;
+ create_tunnel_req.ue_id = UE->rrc_ue_id;
gtpv1u_gnb_create_tunnel_resp_t create_tunnel_resp = {0};
int ret = gtpv1u_create_ngu_tunnel(instance, &create_tunnel_req, &create_tunnel_resp, nr_pdcp_data_req_drb, sdap_data_req);
if (ret != 0) {
@@ -436,7 +437,7 @@ void rrc_gNB_send_NGAP_INITIAL_CONTEXT_SETUP_RESP(const protocol_ctxt_t *const c
ngap_initial_context_setup_resp_t *resp = &NGAP_INITIAL_CONTEXT_SETUP_RESP(msg_p);
gNB_RRC_UE_t *UE = &ue_context_pP->ue_context;
- resp->gNB_ue_ngap_id = UE->gNB_ue_ngap_id;
+ resp->gNB_ue_ngap_id = UE->rrc_ue_id;
for (int pdusession = 0; pdusession < UE->nb_of_pdusessions; pdusession++) {
rrc_pdu_session_param_t *session = &UE->pduSession[pdusession];
@@ -607,7 +608,7 @@ int rrc_gNB_process_NGAP_DOWNLINK_NAS(MessageDef *msg_p, instance_t instance, mu
}
gNB_RRC_UE_t *UE = &ue_context_p->ue_context;
- PROTOCOL_CTXT_SET_BY_INSTANCE(&ctxt, instance, GNB_FLAG_YES, UE->rnti, 0, 0);
+ PROTOCOL_CTXT_SET_BY_INSTANCE(&ctxt, instance, GNB_FLAG_YES, UE->rrc_ue_id, 0, 0);
/* Create message for PDCP (DLInformationTransfer_t) */
length = do_NR_DLInformationTransfer(instance, &buffer, rrc_gNB_get_next_transaction_identifier(instance), req->nas_pdu.length, req->nas_pdu.buffer);
@@ -618,7 +619,7 @@ int rrc_gNB_process_NGAP_DOWNLINK_NAS(MessageDef *msg_p, instance_t instance, mu
AssertFatal(!NODE_IS_DU(RC.nrrrc[ctxt.module_id]->node_type), "illegal node type DU: receiving NGAP messages at this node\n");
/* Transfer data to PDCP */
rb_id_t srb_id = UE->Srb[2].Active ? DCCH1 : DCCH;
- nr_pdcp_data_req_srb(ctxt.rntiMaybeUEid, srb_id, (*rrc_gNB_mui)++, length, buffer, deliver_pdu_srb_f1, RC.nrrrc[instance]);
+ nr_rrc_transfer_protected_rrc_message(RC.nrrrc[instance], UE, srb_id, buffer, length);
return 0;
}
@@ -641,7 +642,7 @@ rrc_gNB_send_NGAP_UPLINK_NAS(
pdu_length = ulInformationTransfer->criticalExtensions.choice.ulInformationTransfer->dedicatedNAS_Message->size;
pdu_buffer = ulInformationTransfer->criticalExtensions.choice.ulInformationTransfer->dedicatedNAS_Message->buf;
msg_p = itti_alloc_new_message (TASK_RRC_GNB, 0, NGAP_UPLINK_NAS);
- NGAP_UPLINK_NAS(msg_p).gNB_ue_ngap_id = UE->gNB_ue_ngap_id;
+ NGAP_UPLINK_NAS(msg_p).gNB_ue_ngap_id = UE->rrc_ue_id;
NGAP_UPLINK_NAS (msg_p).nas_pdu.length = pdu_length;
NGAP_UPLINK_NAS (msg_p).nas_pdu.buffer = pdu_buffer;
// extract_imsi(NGAP_UPLINK_NAS (msg_p).nas_pdu.buffer,
@@ -668,7 +669,7 @@ rrc_gNB_send_NGAP_PDUSESSION_SETUP_RESP(
msg_p = itti_alloc_new_message (TASK_RRC_GNB, 0, NGAP_PDUSESSION_SETUP_RESP);
ngap_pdusession_setup_resp_t *resp = &NGAP_PDUSESSION_SETUP_RESP(msg_p);
gNB_RRC_UE_t *UE = &ue_context_pP->ue_context;
- resp->gNB_ue_ngap_id = UE->gNB_ue_ngap_id;
+ resp->gNB_ue_ngap_id = UE->rrc_ue_id;
for (int pdusession = 0; pdusession < UE->nb_of_pdusessions; pdusession++) {
rrc_pdu_session_param_t *session = &UE->pduSession[pdusession];
@@ -745,7 +746,7 @@ void rrc_gNB_process_NGAP_PDUSESSION_SETUP_REQ(MessageDef *msg_p, instance_t ins
return ;
}
- UE->gNB_ue_ngap_id = msg->gNB_ue_ngap_id;
+ UE->rrc_ue_id = msg->gNB_ue_ngap_id;
UE->amf_ue_ngap_id = msg->amf_ue_ngap_id;
e1ap_bearer_setup_req_t bearer_req = {0};
@@ -759,7 +760,6 @@ void rrc_gNB_process_NGAP_PDUSESSION_SETUP_REQ(MessageDef *msg_p, instance_t ins
session->pdusessionTransfer = msg->pdusession_setup_params[i].pdusessionTransfer;
decodePDUSessionResourceSetup(session);
bearer_req.gNB_cu_cp_ue_id = msg->gNB_ue_ngap_id;
- bearer_req.rnti = UE->rnti;
bearer_req.cipheringAlgorithm = UE->ciphering_algorithm;
bearer_req.integrityProtectionAlgorithm = UE->integrity_algorithm;
nr_derive_key(UP_ENC_ALG, UE->ciphering_algorithm, UE->kgnb, (uint8_t *)bearer_req.encryptionKey);
@@ -925,7 +925,7 @@ int rrc_gNB_process_NGAP_PDUSESSION_MODIFY_REQ(MessageDef *msg_p, instance_t ins
return (-1);
}
gNB_RRC_UE_t *UE = &ue_context_p->ue_context;
- PROTOCOL_CTXT_SET_BY_INSTANCE(&ctxt, instance, GNB_FLAG_YES, UE->rnti, 0, 0);
+ PROTOCOL_CTXT_SET_BY_INSTANCE(&ctxt, instance, GNB_FLAG_YES, UE->rrc_ue_id, 0, 0);
ctxt.eNB_index = 0;
bool all_failed = true;
for (int i = 0; i < req->nb_pdusessions_tomodify; i++) {
@@ -1009,7 +1009,7 @@ rrc_gNB_send_NGAP_PDUSESSION_MODIFY_RESP(
ngap_pdusession_modify_resp_t *resp = &NGAP_PDUSESSION_MODIFY_RESP(msg_p);
LOG_I(NR_RRC, "send message NGAP_PDUSESSION_MODIFY_RESP \n");
- resp->gNB_ue_ngap_id = UE->gNB_ue_ngap_id;
+ resp->gNB_ue_ngap_id = UE->rrc_ue_id;
for (int i = 0; i < UE->nb_of_pdusessions; i++) {
if (xid != UE->pduSession[i].xid) {
@@ -1087,7 +1087,7 @@ void rrc_gNB_send_NGAP_UE_CONTEXT_RELEASE_REQ(const module_id_t gnb_mod_idP, con
MessageDef *msg = itti_alloc_new_message(TASK_RRC_GNB, 0, NGAP_UE_CONTEXT_RELEASE_REQ);
ngap_ue_release_req_t *req = &NGAP_UE_CONTEXT_RELEASE_REQ(msg);
memset(req, 0, sizeof(*req));
- req->gNB_ue_ngap_id = UE->gNB_ue_ngap_id;
+ req->gNB_ue_ngap_id = UE->rrc_ue_id;
req->cause = causeP;
req->cause_value = cause_valueP;
for (int i = 0; i < UE->nb_of_pdusessions; i++) {
@@ -1152,7 +1152,7 @@ int rrc_gNB_process_NGAP_UE_CONTEXT_RELEASE_COMMAND(MessageDef *msg_p, instance_
}
gNB_RRC_UE_t *UE = &ue_context_p->ue_context;
- PROTOCOL_CTXT_SET_BY_INSTANCE(&ctxt, instance, GNB_FLAG_YES, UE->rnti, 0, 0);
+ PROTOCOL_CTXT_SET_BY_INSTANCE(&ctxt, instance, GNB_FLAG_YES, UE->rrc_ue_id, 0, 0);
ctxt.eNB_index = 0;
rrc_gNB_generate_RRCRelease(&ctxt, ue_context_p);
return 0;
@@ -1202,7 +1202,7 @@ void rrc_gNB_send_NGAP_UE_CAPABILITIES_IND(const protocol_ctxt_t *const ctxt_pP,
msg_p = itti_alloc_new_message (TASK_RRC_GNB, 0, NGAP_UE_CAPABILITIES_IND);
ngap_ue_cap_info_ind_t *ind = &NGAP_UE_CAPABILITIES_IND(msg_p);
memset(ind, 0, sizeof(*ind));
- ind->gNB_ue_ngap_id = UE->gNB_ue_ngap_id;
+ ind->gNB_ue_ngap_id = UE->rrc_ue_id;
ind->ue_radio_cap.length = encoded;
ind->ue_radio_cap.buffer = buf2;
itti_send_msg_to_task (TASK_NGAP, ctxt_pP->instance, msg_p);
@@ -1224,7 +1224,7 @@ rrc_gNB_send_NGAP_PDUSESSION_RELEASE_RESPONSE(
msg_p = itti_alloc_new_message (TASK_RRC_GNB, 0, NGAP_PDUSESSION_RELEASE_RESPONSE);
ngap_pdusession_release_resp_t *resp = &NGAP_PDUSESSION_RELEASE_RESPONSE(msg_p);
memset(resp, 0, sizeof(*resp));
- resp->gNB_ue_ngap_id = UE->gNB_ue_ngap_id;
+ resp->gNB_ue_ngap_id = UE->rrc_ue_id;
for (int i = 0; i < UE->nb_of_pdusessions; i++) {
if (xid == UE->pduSession[i].xid) {
@@ -1239,7 +1239,7 @@ rrc_gNB_send_NGAP_PDUSESSION_RELEASE_RESPONSE(
resp->nb_of_pdusessions_released = pdu_sessions_released;
resp->nb_of_pdusessions_failed = 0;
- LOG_I(NR_RRC, "NGAP PDUSESSION RELEASE RESPONSE: GNB_UE_NGAP_ID %u release_pdu_sessions %d\n", resp->gNB_ue_ngap_id, pdu_sessions_released);
+ LOG_I(NR_RRC, "NGAP PDUSESSION RELEASE RESPONSE: rrc_ue_id %u release_pdu_sessions %d\n", resp->gNB_ue_ngap_id, pdu_sessions_released);
itti_send_msg_to_task (TASK_NGAP, ctxt_pP->instance, msg_p);
}
@@ -1264,9 +1264,9 @@ int rrc_gNB_process_NGAP_PDUSESSION_RELEASE_COMMAND(MessageDef *msg_p, instance_
LOG_I(NR_RRC, "[gNB %ld] gNB_ue_ngap_id %u \n", instance, gNB_ue_ngap_id);
gNB_RRC_UE_t *UE = &ue_context_p->ue_context;
- PROTOCOL_CTXT_SET_BY_INSTANCE(&ctxt, instance, GNB_FLAG_YES, UE->rnti, 0, 0);
+ PROTOCOL_CTXT_SET_BY_INSTANCE(&ctxt, instance, GNB_FLAG_YES, UE->rrc_ue_id, 0, 0);
LOG_I(
- NR_RRC, "PDU Session Release Command: AMF_UE_NGAP_ID %lu GNB_UE_NGAP_ID %u release_pdusessions %d \n", cmd->amf_ue_ngap_id, gNB_ue_ngap_id, cmd->nb_pdusessions_torelease);
+ NR_RRC, "PDU Session Release Command: AMF_UE_NGAP_ID %lu rrc_ue_id %u release_pdusessions %d \n", cmd->amf_ue_ngap_id, gNB_ue_ngap_id, cmd->nb_pdusessions_torelease);
bool found = false;
uint8_t xid = rrc_gNB_get_next_transaction_identifier(ctxt.module_id);
UE->xids[xid] = RRC_PDUSESSION_RELEASE;
diff --git a/openair2/RRC/NR/rrc_gNB_UE_context.c b/openair2/RRC/NR/rrc_gNB_UE_context.c
index 2d2742aa4a..8a8c0bdd2e 100644
--- a/openair2/RRC/NR/rrc_gNB_UE_context.c
+++ b/openair2/RRC/NR/rrc_gNB_UE_context.c
@@ -35,17 +35,18 @@
#include "common/utils/LOG/log.h"
#include "rrc_gNB_UE_context.h"
+#include "openair2/F1AP/f1ap_ids.h"
//------------------------------------------------------------------------------
int rrc_gNB_compare_ue_rnti_id(rrc_gNB_ue_context_t *c1_pP, rrc_gNB_ue_context_t *c2_pP)
//------------------------------------------------------------------------------
{
- if (c1_pP->ue_context.gNB_ue_ngap_id > c2_pP->ue_context.gNB_ue_ngap_id) {
+ if (c1_pP->ue_context.rrc_ue_id > c2_pP->ue_context.rrc_ue_id) {
return 1;
}
- if (c1_pP->ue_context.gNB_ue_ngap_id < c2_pP->ue_context.gNB_ue_ngap_id) {
+ if (c1_pP->ue_context.rrc_ue_id < c2_pP->ue_context.rrc_ue_id) {
return -1;
}
@@ -66,12 +67,12 @@ rrc_gNB_ue_context_t *rrc_gNB_allocate_new_ue_context(gNB_RRC_INST *rrc_instance
LOG_E(NR_RRC, "Cannot allocate new ue context\n");
return NULL;
}
- new_p->ue_context.gNB_ue_ngap_id = uid_linear_allocator_new(&rrc_instance_pP->uid_allocator);
+ new_p->ue_context.rrc_ue_id = uid_linear_allocator_new(&rrc_instance_pP->uid_allocator) + 1;
for(int i = 0; i < NB_RB_MAX; i++)
new_p->ue_context.pduSession[i].xid = -1;
- LOG_I(NR_RRC, "Returning new RRC UE context RRC ue id: %d\n", new_p->ue_context.gNB_ue_ngap_id);
+ LOG_I(NR_RRC, "Returning new RRC UE context RRC ue id: %d\n", new_p->ue_context.rrc_ue_id);
return(new_p);
}
@@ -82,7 +83,7 @@ rrc_gNB_ue_context_t *rrc_gNB_get_ue_context(gNB_RRC_INST *rrc_instance_pP, ue_i
{
rrc_gNB_ue_context_t temp;
/* gNB ue rrc id = 24 bits wide */
- temp.ue_context.gNB_ue_ngap_id = ue;
+ temp.ue_context.rrc_ue_id = ue;
return RB_FIND(rrc_nr_ue_tree_s, &rrc_instance_pP->rrc_ue_head, &temp);
}
@@ -120,7 +121,8 @@ void rrc_gNB_remove_ue_context(gNB_RRC_INST *rrc_instance_pP, rrc_gNB_ue_context
}
RB_REMOVE(rrc_nr_ue_tree_s, &rrc_instance_pP->rrc_ue_head, ue_context_pP);
- uid_linear_allocator_free(&rrc_instance_pP->uid_allocator, ue_context_pP->ue_context.gNB_ue_ngap_id);
+ uid_linear_allocator_free(&rrc_instance_pP->uid_allocator, ue_context_pP->ue_context.rrc_ue_id - 1);
+ cu_remove_f1_ue_data(ue_context_pP->ue_context.rrc_ue_id);
rrc_gNB_free_mem_ue_context(ue_context_pP);
LOG_I(NR_RRC, "Removed UE context\n");
}
@@ -153,35 +155,33 @@ rrc_gNB_ue_context_t *rrc_gNB_ue_context_5g_s_tmsi_exist(gNB_RRC_INST *rrc_insta
return NULL;
}
-void rrc_gNB_update_ue_context_rnti(rnti_t rnti, gNB_RRC_INST *rrc_instance_pP, uint32_t gNB_ue_ngap_id)
-{
- // rnti will need to be a fast access key, with indexing, today it is sequential search
- // This function will update the index when it will be made
- rrc_gNB_ue_context_t *ue_context_p = rrc_gNB_get_ue_context(rrc_instance_pP, gNB_ue_ngap_id);
- if (ue_context_p)
- ue_context_p->ue_context.rnti = rnti;
- else
- LOG_E(NR_RRC, "update rnti on a wrong UE id\n");
-}
//-----------------------------------------------------------------------------
// return a new ue context structure if ue_identityP, rnti not found in collection
-rrc_gNB_ue_context_t *rrc_gNB_create_ue_context(rnti_t rnti, gNB_RRC_INST *rrc_instance_pP, const uint64_t ue_identityP)
+rrc_gNB_ue_context_t *rrc_gNB_create_ue_context(rnti_t rnti,
+ gNB_RRC_INST *rrc_instance_pP,
+ const uint64_t ue_identityP,
+ uint32_t du_ue_id)
//-----------------------------------------------------------------------------
{
- rrc_gNB_ue_context_t *ue_context_p = rrc_gNB_get_ue_context_by_rnti(rrc_instance_pP, rnti);
-
- if (ue_context_p) {
- LOG_E(NR_RRC, "Cannot create new UE context, already exist rnti: %04x\n", rnti);
- return ue_context_p;
- }
-
- ue_context_p = rrc_gNB_allocate_new_ue_context(rrc_instance_pP);
+ rrc_gNB_ue_context_t *ue_context_p = rrc_gNB_allocate_new_ue_context(rrc_instance_pP);
if (ue_context_p == NULL)
return NULL;
- ue_context_p->ue_context.rnti = rnti;
- ue_context_p->ue_context.random_ue_identity = ue_identityP;
+ gNB_RRC_UE_t *ue = &ue_context_p->ue_context;
+ ue->rnti = rnti;
+ ue->random_ue_identity = ue_identityP;
+ f1_ue_data_t ue_data = {.secondary_ue = du_ue_id};
+ AssertFatal(!cu_exists_f1_ue_data(ue->rrc_ue_id),
+ "UE F1 Context for ID %d already exists, logic bug\n",
+ ue->rrc_ue_id);
+ cu_add_f1_ue_data(ue->rrc_ue_id, &ue_data);
+
RB_INSERT(rrc_nr_ue_tree_s, &rrc_instance_pP->rrc_ue_head, ue_context_p);
- LOG_W(NR_RRC, " Created new UE context rnti: %04x, random ue id %lx, RRC ue id %u\n", rnti, ue_identityP, ue_context_p->ue_context.gNB_ue_ngap_id);
+ LOG_I(NR_RRC,
+ "Created new UE context: CU UE ID %u DU UE ID %u (rnti: %04x, random ue id %lx)\n",
+ ue->rrc_ue_id,
+ du_ue_id,
+ ue->rnti,
+ ue->random_ue_identity);
return ue_context_p;
}
diff --git a/openair2/RRC/NR/rrc_gNB_UE_context.h b/openair2/RRC/NR/rrc_gNB_UE_context.h
index 9c1ec2c164..3ec0852af6 100644
--- a/openair2/RRC/NR/rrc_gNB_UE_context.h
+++ b/openair2/RRC/NR/rrc_gNB_UE_context.h
@@ -50,7 +50,9 @@ void rrc_gNB_remove_ue_context(gNB_RRC_INST* rrc_instance_pP, rrc_gNB_ue_context
rrc_gNB_ue_context_t* rrc_gNB_ue_context_random_exist(gNB_RRC_INST* rrc_instance_pP, const uint64_t ue_identityP);
rrc_gNB_ue_context_t* rrc_gNB_ue_context_5g_s_tmsi_exist(gNB_RRC_INST* rrc_instance_pP, const uint64_t s_TMSI);
-void rrc_gNB_update_ue_context_rnti(rnti_t rnti, gNB_RRC_INST* rrc_instance_pP, uint32_t gNB_ue_ngap_id);
-rrc_gNB_ue_context_t* rrc_gNB_create_ue_context(rnti_t rnti, gNB_RRC_INST* rrc_instance_pP, const uint64_t ue_identityP);
+rrc_gNB_ue_context_t* rrc_gNB_create_ue_context(rnti_t rnti,
+ gNB_RRC_INST* rrc_instance_pP,
+ const uint64_t ue_identityP,
+ uint32_t du_ue_id);
#endif
diff --git a/openair2/RRC/NR/rrc_gNB_nsa.c b/openair2/RRC/NR/rrc_gNB_nsa.c
index 656c7d0663..f0d89051df 100644
--- a/openair2/RRC/NR/rrc_gNB_nsa.c
+++ b/openair2/RRC/NR/rrc_gNB_nsa.c
@@ -41,6 +41,7 @@
#include "openair2/LAYER2/NR_MAC_gNB/mac_proto.h"
#include "openair2/LAYER2/nr_rlc/nr_rlc_oai_api.h"
#include "openair2/RRC/LTE/rrc_eNB_GTPV1U.h"
+#include "openair2/F1AP/f1ap_ids.h"
#include "executables/softmodem-common.h"
#include "executables/nr-softmodem.h"
#include
@@ -248,14 +249,11 @@ void rrc_add_nsa_user(gNB_RRC_INST *rrc, rrc_gNB_ue_context_t *ue_context_p, x2a
1,
1,
configuration,
- ue_context_p->ue_context.gNB_ue_ngap_id);
+ ue_context_p->ue_context.rrc_ue_id);
AssertFatal(UE->secondaryCellGroup != NULL, "out of memory\n");
xer_fprint(stdout, &asn_DEF_NR_CellGroupConfig, UE->secondaryCellGroup);
- fill_default_reconfig(carrier->servingcellconfigcommon, scc, reconfig_ies, UE->secondaryCellGroup, UE->UE_Capability_nr, configuration, ue_context_p->ue_context.gNB_ue_ngap_id);
- // the UE context is not yet inserted in the RRC UE manager
- // rrc_gNB_update_ue_context_rnti(UE->secondaryCellGroup->spCellConfig->reconfigurationWithSync->newUE_Identity, rrc,
- // UE->gNB_ue_ngap_id);
+ fill_default_reconfig(carrier->servingcellconfigcommon, scc, reconfig_ies, UE->secondaryCellGroup, UE->UE_Capability_nr, configuration, ue_context_p->ue_context.rrc_ue_id);
UE->rnti = UE->secondaryCellGroup->spCellConfig->reconfigurationWithSync->newUE_Identity;
NR_CG_Config_t *CG_Config = calloc(1,sizeof(*CG_Config));
memset((void *)CG_Config,0,sizeof(*CG_Config));
@@ -288,7 +286,7 @@ void rrc_add_nsa_user(gNB_RRC_INST *rrc, rrc_gNB_ue_context_t *ue_context_p, x2a
create_tunnel_req.sgw_S1u_teid[i]);
}
- create_tunnel_req.rnti = ue_context_p->ue_context.rnti;
+ create_tunnel_req.rnti = ue_context_p->ue_context.rrc_ue_id;
create_tunnel_req.num_tunnels = m->nb_e_rabs_tobeadded;
RB_INSERT(rrc_nr_ue_tree_s, &RC.nrrrc[rrc->module_id]->rrc_ue_head, ue_context_p);
PROTOCOL_CTXT_SET_BY_MODULE_ID(&ctxt, rrc->module_id, GNB_FLAG_YES, ue_context_p->ue_context.rnti, 0, 0, rrc->module_id);
@@ -343,20 +341,31 @@ void rrc_add_nsa_user(gNB_RRC_INST *rrc, rrc_gNB_ue_context_t *ue_context_p, x2a
itti_send_msg_to_task(TASK_X2AP, ENB_MODULE_ID_TO_INSTANCE(0), msg); //Check right id instead of hardcoding
}
+ // below we configure the stack. In SA, we fully adopted F1, meaning that
+ // layers use different IDs (MAC/RLC use RNTI as DU UE ID, above use NGAP ID
+ // as CU UE ID.
+ uint32_t du_ue_id = ue_context_p->ue_context.rnti;
+ static uint32_t rrc_ue_id = 0;
+ rrc_ue_id++;
+ f1_ue_data_t du_ue_data = {.secondary_ue = rrc_ue_id};
+ du_add_f1_ue_data(du_ue_id, &du_ue_data);
+ f1_ue_data_t cu_ue_data = {.secondary_ue = du_ue_id};
+ cu_add_f1_ue_data(rrc_ue_id, &cu_ue_data);
+ LOG_I(RRC, "Assign CU UE ID %d and DU UE ID %d to UE RNTI %04x\n", rrc_ue_id, du_ue_id, ue_context_p->ue_context.rnti);
+
// configure MAC and RLC
bool ret = false;
if (get_softmodem_params()->phy_test) {
// phytest mode: we don't set up RA, etc
- ret = nr_mac_add_test_ue(RC.nrmac[rrc->module_id] , ue_context_p->ue_context.rnti, ue_context_p->ue_context.secondaryCellGroup);
+ ret = nr_mac_add_test_ue(RC.nrmac[rrc->module_id], du_ue_id, ue_context_p->ue_context.secondaryCellGroup);
} else {
NR_SCHED_LOCK(&RC.nrmac[rrc->module_id]->sched_lock);
- ret = nr_mac_prepare_ra_ue(RC.nrmac[rrc->module_id], ue_context_p->ue_context.rnti, ue_context_p->ue_context.secondaryCellGroup);
+ ret = nr_mac_prepare_ra_ue(RC.nrmac[rrc->module_id], du_ue_id, ue_context_p->ue_context.secondaryCellGroup);
NR_SCHED_UNLOCK(&RC.nrmac[rrc->module_id]->sched_lock);
}
AssertFatal(ret, "cannot add NSA UE in MAC, aborting\n");
- PROTOCOL_CTXT_SET_BY_MODULE_ID(&ctxt, rrc->module_id, GNB_FLAG_YES, ue_context_p->ue_context.rnti, 0, 0, rrc->module_id);
- if (get_softmodem_params()->do_ra) ctxt.enb_flag = 0;
+ PROTOCOL_CTXT_SET_BY_MODULE_ID(&ctxt, rrc->module_id, GNB_FLAG_YES, rrc_ue_id, 0, 0, rrc->module_id);
LOG_W(RRC,
"Calling RRC PDCP/RLC ASN1 request functions for protocol context %p with module_id %d, rnti %lx, frame %d, subframe %d eNB_index %d \n",
&ctxt,
@@ -367,14 +376,14 @@ void rrc_add_nsa_user(gNB_RRC_INST *rrc, rrc_gNB_ue_context_t *ue_context_p, x2a
ctxt.eNB_index);
nr_pdcp_add_drbs(ctxt.enb_flag,
- ctxt.rntiMaybeUEid,
- 0,
+ rrc_ue_id,
ue_context_p->ue_context.rb_config->drb_ToAddModList,
(ue_context_p->ue_context.integrity_algorithm << 4) | ue_context_p->ue_context.ciphering_algorithm,
kUPenc,
kUPint,
ue_context_p->ue_context.secondaryCellGroup->rlc_BearerToAddModList);
+ ctxt.rntiMaybeUEid = du_ue_id;
// assume only a single bearer
const NR_DRB_ToAddModList_t *drb_list = ue_context_p->ue_context.rb_config->drb_ToAddModList;
DevAssert(drb_list->list.count == 1);
diff --git a/openair2/RRC/NR_UE/rrc_UE.c b/openair2/RRC/NR_UE/rrc_UE.c
index 01a0178b62..73c3fa1593 100644
--- a/openair2/RRC/NR_UE/rrc_UE.c
+++ b/openair2/RRC/NR_UE/rrc_UE.c
@@ -1675,7 +1675,6 @@ int32_t nr_rrc_ue_establish_drb(module_id_t ue_mod_idP,
// Refresh DRBs
nr_pdcp_add_drbs(ctxt_pP->enb_flag,
ctxt_pP->rntiMaybeUEid,
- 0,
radioBearerConfig->drb_ToAddModList,
ue_rrc->cipheringAlgorithm | (ue_rrc->integrityProtAlgorithm << 4),
kUPenc,
diff --git a/openair3/ocp-gtpu/gtp_itf.cpp b/openair3/ocp-gtpu/gtp_itf.cpp
index 5a75b8953a..d7cc496439 100644
--- a/openair3/ocp-gtpu/gtp_itf.cpp
+++ b/openair3/ocp-gtpu/gtp_itf.cpp
@@ -768,31 +768,31 @@ int gtpv1u_create_ngu_tunnel(const instance_t instance,
return !GTPNOK;
}
-int gtpv1u_update_ngu_tunnel(const instance_t instanceP, const gtpv1u_gnb_create_tunnel_req_t *const create_tunnel_req_pP, const ue_id_t prior_ue_id)
+int gtpv1u_update_ue_id(const instance_t instanceP, ue_id_t old_ue_id, ue_id_t new_ue_id)
{
- LOG_D(GTPU, "[%ld] Update tunnels from UEid %lx to UEid %lx\n", instanceP, prior_ue_id, create_tunnel_req_pP->ue_id);
-
pthread_mutex_lock(&globGtp.gtp_lock);
auto inst = &globGtp.instances[compatInst(instanceP)];
- auto it = inst->ue2te_mapping.find(prior_ue_id);
+ auto it = inst->ue2te_mapping.find(old_ue_id);
if (it == inst->ue2te_mapping.end()) {
- LOG_W(GTPU, "[%ld] Delete GTP tunnels for UEid: %lx, but no tunnel exits\n", instanceP, prior_ue_id);
+ LOG_W(GTPU, "[%ld] Update GTP tunnels for UEid: %lx, but no tunnel exits\n", instanceP, old_ue_id);
pthread_mutex_unlock(&globGtp.gtp_lock);
return GTPNOK;
}
- for (int i = 0; i < create_tunnel_req_pP->num_tunnels; i++) {
- teid_t incoming_teid = inst->ue2te_mapping[prior_ue_id].bearers[create_tunnel_req_pP->pdusession_id[i]].teid_incoming;
- if (globGtp.te2ue_mapping[incoming_teid].ue_id == prior_ue_id) {
- globGtp.te2ue_mapping[incoming_teid].ue_id = create_tunnel_req_pP->ue_id;
+ for (unsigned i = 0; i < it->second.bearers.size(); ++i) {
+ teid_t incoming_teid = inst->ue2te_mapping[old_ue_id].bearers[i].teid_incoming;
+ if (globGtp.te2ue_mapping[incoming_teid].ue_id == old_ue_id) {
+ globGtp.te2ue_mapping[incoming_teid].ue_id = new_ue_id;
}
}
- inst->ue2te_mapping[create_tunnel_req_pP->ue_id] = it->second;
+ inst->ue2te_mapping[new_ue_id] = it->second;
inst->ue2te_mapping.erase(it);
pthread_mutex_unlock(&globGtp.gtp_lock);
+
+ LOG_I(GTPU, "[%ld] Updated tunnels from UEid %lx to UEid %lx\n", instanceP, old_ue_id, new_ue_id);
return !GTPNOK;
}
diff --git a/openair3/ocp-gtpu/gtp_itf.h b/openair3/ocp-gtpu/gtp_itf.h
index 9592070ca9..f8228677fc 100644
--- a/openair3/ocp-gtpu/gtp_itf.h
+++ b/openair3/ocp-gtpu/gtp_itf.h
@@ -76,11 +76,8 @@ extern "C" {
int gtpv1u_delete_ngu_tunnel( const instance_t instance,
gtpv1u_gnb_delete_tunnel_req_t *req);
-
- int gtpv1u_update_ngu_tunnel( const instance_t instanceP,
- const gtpv1u_gnb_create_tunnel_req_t *const create_tunnel_req_pP,
- const ue_id_t prior_rnti
- );
+
+ int gtpv1u_update_ue_id(const instance_t instanceP, ue_id_t old_ue_id, ue_id_t new_ue_id);
// New API
teid_t newGtpuCreateTunnel(instance_t instance,