From 7877e38890c294dc7d551c0a1a31718a2cd6e409 Mon Sep 17 00:00:00 2001 From: Raghavendra Dinavahi Date: Mon, 12 May 2025 20:23:55 +0200 Subject: [PATCH] UE changes: Handle T430 expiry in RRC, MAC SPEC 38.331 section 5.2.2.6 Inform MAC that UL SYNC got lost because of T430 expiry - Send message NR_MAC_RRC_CONFIG_RESET with cause UL_SYNC_LOST_T430_EXPIRY to MAC Reacquire SIB19 after T430 expiry This is not checked in this commit - RACH needs to be performed through probably PDCCH order to reobtain UL-SYNC - system usecase involving Recovery from T430 expiry not tested yet as that requires changes on gNB side. --- openair2/LAYER2/NR_MAC_UE/config_ue.c | 5 +++++ openair2/LAYER2/NR_MAC_UE/mac_defs.h | 3 ++- openair2/LAYER2/NR_MAC_UE/mac_proto.h | 1 + openair2/LAYER2/NR_MAC_UE/nr_ue_scheduler.c | 21 +++++++++++++++++++ openair2/RRC/NR_UE/rrc_UE.c | 16 ++++++++++++++ openair2/RRC/NR_UE/rrc_proto.h | 1 + openair2/RRC/NR_UE/rrc_timers_and_constants.c | 4 ++-- 7 files changed, 48 insertions(+), 3 deletions(-) diff --git a/openair2/LAYER2/NR_MAC_UE/config_ue.c b/openair2/LAYER2/NR_MAC_UE/config_ue.c index 3a5d5e5640..e86599ef18 100644 --- a/openair2/LAYER2/NR_MAC_UE/config_ue.c +++ b/openair2/LAYER2/NR_MAC_UE/config_ue.c @@ -1718,6 +1718,11 @@ void nr_rrc_mac_config_req_reset(module_id_t module_id, NR_UE_MAC_reset_cause_t sync_req.ssb_bw_scan = false; nr_ue_send_synch_request(mac, module_id, 0, &sync_req); break; + case UL_SYNC_LOST_T430_EXPIRED: + // TS 38.331 Section 5.2.2.6, TS 38.321 Section 5.2a + // Flush all HARQ buffers and Stop UL transmissions + handle_ulsync_loss(mac); + break; default: AssertFatal(false, "Invalid MAC reset cause %d\n", cause); } diff --git a/openair2/LAYER2/NR_MAC_UE/mac_defs.h b/openair2/LAYER2/NR_MAC_UE/mac_defs.h index b3ca280f86..fcf770a2f4 100644 --- a/openair2/LAYER2/NR_MAC_UE/mac_defs.h +++ b/openair2/LAYER2/NR_MAC_UE/mac_defs.h @@ -196,7 +196,8 @@ typedef enum { GO_TO_IDLE, DETACH, T300_EXPIRY, - RE_ESTABLISHMENT + RE_ESTABLISHMENT, + UL_SYNC_LOST_T430_EXPIRED } NR_UE_MAC_reset_cause_t; typedef struct { diff --git a/openair2/LAYER2/NR_MAC_UE/mac_proto.h b/openair2/LAYER2/NR_MAC_UE/mac_proto.h index f5e36bd7d5..d12b006d90 100644 --- a/openair2/LAYER2/NR_MAC_UE/mac_proto.h +++ b/openair2/LAYER2/NR_MAC_UE/mac_proto.h @@ -323,6 +323,7 @@ void nr_Msg3_transmitted(NR_UE_MAC_INST_t *mac, uint8_t CC_id, frame_t frameP, s void trigger_MAC_UE_RA(NR_UE_MAC_INST_t *mac, dci_pdu_rel15_t *pdcch_order); void nr_get_Msg3_MsgA_PUSCH_payload(NR_UE_MAC_INST_t *mac, uint8_t *buf, int TBS_max); void handle_time_alignment_timer_expired(NR_UE_MAC_INST_t *mac); +void handle_ulsync_loss(NR_UE_MAC_INST_t *mac); int8_t nr_ue_process_dci_freq_dom_resource_assignment(nfapi_nr_ue_pusch_pdu_t *pusch_config_pdu, fapi_nr_dl_config_dlsch_pdu_rel15_t *dlsch_config_pdu, NR_PDSCH_Config_t *pdsch_Config, diff --git a/openair2/LAYER2/NR_MAC_UE/nr_ue_scheduler.c b/openair2/LAYER2/NR_MAC_UE/nr_ue_scheduler.c index 2c94de6e70..82f1669fa7 100644 --- a/openair2/LAYER2/NR_MAC_UE/nr_ue_scheduler.c +++ b/openair2/LAYER2/NR_MAC_UE/nr_ue_scheduler.c @@ -182,6 +182,27 @@ void handle_time_alignment_timer_expired(NR_UE_MAC_INST_t *mac) // TODO not sure what to do here } +void handle_ulsync_loss(NR_UE_MAC_INST_t *mac) +{ + // flush all HARQ buffers for all Serving Cells + for (int k = 0; k < NR_MAX_HARQ_PROCESSES; k++) { + memset(&mac->dl_harq_info[k], 0, sizeof(*mac->dl_harq_info)); + memset(&mac->ul_harq_info[k], 0, sizeof(*mac->ul_harq_info)); + mac->dl_harq_info[k].last_ndi = -1; // initialize to invalid value + mac->ul_harq_info[k].last_ndi = -1; // initialize to invalid value + } + // clear any configured downlink assignments and uplink grants; + if (mac->dl_config_request) + memset(mac->dl_config_request, 0, sizeof(*mac->dl_config_request)); + if (mac->ul_config_request) + clear_ul_config_request(mac); + + // Need to receive SIB19 again after loosing UL SYNC + mac->state = UE_RECEIVING_SIB; + // gNB needs to send PDCCH ORDER triggering RA after detecting ULSYNC LOSS + LOG_W(NR_MAC, "Wait for PDCCH ORDER, RACH needs to performed to obtain ULSYNC.\n"); +} + void update_mac_dl_timers(NR_UE_MAC_INST_t *mac) { bool ra_window_expired = nr_timer_tick(&mac->ra.response_window_timer); diff --git a/openair2/RRC/NR_UE/rrc_UE.c b/openair2/RRC/NR_UE/rrc_UE.c index 17eaca5e9c..668a008d15 100644 --- a/openair2/RRC/NR_UE/rrc_UE.c +++ b/openair2/RRC/NR_UE/rrc_UE.c @@ -2801,6 +2801,22 @@ void handle_t300_expiry(NR_UE_RRC_INST_t *rrc) // TODO inform upper layers about the failure to establish the RRC connection } +void handle_t430_expiry(NR_UE_RRC_INST_t *rrc) +{ + // SPEC 38.331 section 5.2.2.6 + // Reacquire SIB19 after T430 expiry + for (int i = 0; i < NB_CNX_UE; i++) { + rrcPerNB_t *nb = &rrc->perNB[i]; + NR_UE_RRC_SI_INFO *SI_info = &nb->SInfo; + SI_info->SInfo_r17.sib19_validity = false; + } + // Indicate MAC that UL SYNC is LOST + NR_UE_MAC_reset_cause_t cause = UL_SYNC_LOST_T430_EXPIRED; + MessageDef *msg = itti_alloc_new_message(TASK_RRC_NRUE, 0, NR_MAC_RRC_CONFIG_RESET); + NR_MAC_RRC_CONFIG_RESET(msg).cause = cause; + itti_send_msg_to_task(TASK_MAC_UE, rrc->ue_id, msg); +} + //This calls the sidelink preconf message after RRC, MAC instances are created. void start_sidelink(int instance) { diff --git a/openair2/RRC/NR_UE/rrc_proto.h b/openair2/RRC/NR_UE/rrc_proto.h index 9d599d6ab1..7c5f749fa0 100644 --- a/openair2/RRC/NR_UE/rrc_proto.h +++ b/openair2/RRC/NR_UE/rrc_proto.h @@ -80,6 +80,7 @@ void init_SI_timers(NR_UE_RRC_SI_INFO *SInfo); void nr_ue_rrc_timer_trigger(int module_id, int frame, int gnb_id); void handle_t300_expiry(NR_UE_RRC_INST_t *rrc); +void handle_t430_expiry(NR_UE_RRC_INST_t *rrc); void reset_rlf_timers_and_constants(NR_UE_Timers_Constants_t *tac); void set_default_timers_and_constants(NR_UE_Timers_Constants_t *tac); diff --git a/openair2/RRC/NR_UE/rrc_timers_and_constants.c b/openair2/RRC/NR_UE/rrc_timers_and_constants.c index 9f46fbb3cd..9286494f0b 100644 --- a/openair2/RRC/NR_UE/rrc_timers_and_constants.c +++ b/openair2/RRC/NR_UE/rrc_timers_and_constants.c @@ -172,10 +172,10 @@ void nr_rrc_handle_timers(NR_UE_RRC_INST_t *rrc) bool t430_expired = nr_timer_tick(&rrc->timers_and_constants.T430); if (t430_expired && rrc->nrRrcState == RRC_STATE_CONNECTED_NR && rrc->is_NTN_UE) { - LOG_W(NR_RRC, "Timer T430 expired! NTN UL SYNC FAILURE\n"); + LOG_W(NR_RRC, "Timer T430 expired! Indicate UL SYNC LOSS to MAC\n"); // Upon T430 expiry, the UE shall reacquire SIB19 and re-obtain UL-SYNC // Spec 38.331 Section 5.2.2.6 - AssertFatal(1 == 0, "UL-Sync Lost. Read SIB19, perform RACH and obtain UL-SYNC. NOT YET Implemented.\n"); + handle_t430_expiry(rrc); } }