From da70c0fdafd295f8d590339f5ecbb9ced4efc11c Mon Sep 17 00:00:00 2001 From: Francisco Paisana Date: Thu, 24 Sep 2020 19:53:26 +0200 Subject: [PATCH] fix cellsToAddModList handling. Now the eNB always adds PCell+SCells as measObjects in the RRC Reconfiguration messages. It may also further include cellsToAddModList if they are provided in the rr.conf file --- srsenb/hdr/stack/rrc/rrc.h | 3 - srsenb/hdr/stack/rrc/rrc_cell_cfg.h | 4 + srsenb/hdr/stack/rrc/rrc_mobility.h | 57 +++----- srsenb/src/stack/rrc/rrc.cc | 7 - srsenb/src/stack/rrc/rrc_cell_cfg.cc | 12 ++ srsenb/src/stack/rrc/rrc_mobility.cc | 189 +++++++++++++------------ srsenb/src/stack/rrc/rrc_ue.cc | 2 +- srsenb/test/upper/rrc_mobility_test.cc | 8 +- 8 files changed, 136 insertions(+), 146 deletions(-) diff --git a/srsenb/hdr/stack/rrc/rrc.h b/srsenb/hdr/stack/rrc/rrc.h index 0028bc946..cc8c74a41 100644 --- a/srsenb/hdr/stack/rrc/rrc.h +++ b/srsenb/hdr/stack/rrc/rrc.h @@ -182,9 +182,6 @@ private: uint32_t nof_si_messages = 0; asn1::rrc::sib_type7_s sib7; - class enb_mobility_handler; - std::unique_ptr enb_mobility_cfg; - void rem_user_thread(uint16_t rnti); std::mutex paging_mutex; diff --git a/srsenb/hdr/stack/rrc/rrc_cell_cfg.h b/srsenb/hdr/stack/rrc/rrc_cell_cfg.h index bb33b229d..80a51f05b 100644 --- a/srsenb/hdr/stack/rrc/rrc_cell_cfg.h +++ b/srsenb/hdr/stack/rrc/rrc_cell_cfg.h @@ -77,6 +77,8 @@ public: const cell_info_common* get_pci(uint32_t pci) const; size_t nof_cells() const { return cell_list.size(); } + std::vector get_potential_cells(uint32_t enb_cc_idx) const; + private: const rrc_cfg_t& cfg; std::vector > cell_list; @@ -101,6 +103,8 @@ struct cell_ctxt_dedicated { cell_ctxt_dedicated(cell_ctxt_dedicated&&) noexcept = default; cell_ctxt_dedicated& operator=(const cell_ctxt_dedicated&) = delete; cell_ctxt_dedicated& operator=(cell_ctxt_dedicated&&) noexcept = default; + + uint32_t get_dl_earfcn() const { return cell_common->cell_cfg.dl_earfcn; } }; /** Class used to handle the allocation of a UE's resources across its cells */ diff --git a/srsenb/hdr/stack/rrc/rrc_mobility.h b/srsenb/hdr/stack/rrc/rrc_mobility.h index ff4defb28..f52c075b4 100644 --- a/srsenb/hdr/stack/rrc/rrc_mobility.h +++ b/srsenb/hdr/stack/rrc/rrc_mobility.h @@ -42,8 +42,9 @@ public: using meas_obj_t = asn1::rrc::meas_obj_to_add_mod_s; using report_cfg_t = asn1::rrc::report_cfg_to_add_mod_s; - var_meas_cfg_t(uint32_t dl_earfcn_) : dl_earfcn(dl_earfcn_), rrc_log(srslte::logmap::get("RRC")) {} + var_meas_cfg_t(); std::tuple add_cell_cfg(const meas_cell_cfg_t& cellcfg); + std::pair add_meas_obj(uint32_t dl_earfcn); report_cfg_t* add_report_cfg(const asn1::rrc::report_cfg_eutra_s& reportcfg); meas_id_t* add_measid_cfg(uint8_t measobjid, uint8_t repid); asn1::rrc::quant_cfg_s* add_quant_cfg(const asn1::rrc::quant_cfg_eutra_s& quantcfg); @@ -64,40 +65,18 @@ public: asn1::rrc::meas_obj_to_add_mod_list_l& meas_objs() { return var_meas.meas_obj_list; } asn1::rrc::report_cfg_to_add_mod_list_l& rep_cfgs() { return var_meas.report_cfg_list; } asn1::rrc::meas_id_to_add_mod_list_l& meas_ids() { return var_meas.meas_id_list; } - uint32_t get_dl_earfcn() const { return dl_earfcn; } std::string to_string() const; - static var_meas_cfg_t make(uint32_t dl_earfcn, const asn1::rrc::meas_cfg_s& meas_cfg); + static var_meas_cfg_t make(const asn1::rrc::meas_cfg_s& meas_cfg); + static var_meas_cfg_t make(const rrc_cfg_t& cfg); private: - uint32_t dl_earfcn; asn1::rrc::var_meas_cfg_s var_meas; srslte::log_ref rrc_log; }; enum class ho_interface_t { S1, X2, intra_enb }; -class rrc::enb_mobility_handler -{ -public: - explicit enb_mobility_handler(rrc* rrc_); - - //! Variable used to store the MeasConfig expected for each cell. - // Note: Made const to forbid silent updates and enable comparison based on addr - std::vector cell_meas_cfg_list; - - rrc* get_rrc() { return rrc_ptr; } - const rrc* get_rrc() const { return rrc_ptr; } - - uint16_t start_ho_ue_resource_alloc(const asn1::s1ap::ho_request_s& msg, - const asn1::s1ap::sourceenb_to_targetenb_transparent_container_s& container); - -private: - // args - rrc* rrc_ptr = nullptr; - const rrc_cfg_t* cfg = nullptr; -}; - class rrc::ue::rrc_mobility : public srslte::fsm_t { public: @@ -109,7 +88,8 @@ public: struct ho_cancel_ev {}; explicit rrc_mobility(srsenb::rrc::ue* outer_ue); - bool fill_conn_recfg_msg(asn1::rrc::rrc_conn_recfg_r8_ies_s* conn_recfg); + + bool fill_conn_recfg_no_ho_cmd(asn1::rrc::rrc_conn_recfg_r8_ies_s* conn_recfg); void handle_ue_meas_report(const asn1::rrc::meas_report_s& msg); void handle_ho_preparation_complete(bool is_success, srslte::unique_byte_buffer_t container); bool is_ho_running() const { return not is_in_state(); } @@ -118,29 +98,30 @@ public: bool start_s1_tenb_ho(const asn1::s1ap::ho_request_s& msg, const asn1::s1ap::sourceenb_to_targetenb_transparent_container_s& container); + static uint16_t + start_ho_ue_resource_alloc(const asn1::s1ap::ho_request_s& msg, + const asn1::s1ap::sourceenb_to_targetenb_transparent_container_s& container); + private: + // helper methods + bool update_ue_var_meas_cfg(uint32_t src_earfcn, + std::vector target_cells, + asn1::rrc::meas_cfg_s* diff_meas_cfg); + // Handover from source cell bool start_ho_preparation(uint32_t target_eci, uint8_t measobj_id, bool fwd_direct_path_available); bool start_enb_status_transfer(); // Handover to target cell - bool update_ue_var_meas_cfg(const asn1::rrc::meas_cfg_s& source_meas_cfg, - uint32_t src_dl_earfcn, - uint32_t target_enb_cc_idx, - asn1::rrc::meas_cfg_s* diff_meas_cfg); - bool update_ue_var_meas_cfg(var_meas_cfg_t& source_var_meas_cfg, - uint32_t target_enb_cc_idx, - asn1::rrc::meas_cfg_s* diff_meas_cfg); void fill_mobility_reconf_common(asn1::rrc::dl_dcch_msg_s& msg, const cell_info_common& target_cell, uint32_t src_dl_earfcn); bool apply_ho_prep_cfg(const asn1::rrc::ho_prep_info_r8_ies_s& ho_prep, const asn1::s1ap::ho_request_s& ho_req_msg); - rrc::ue* rrc_ue = nullptr; - rrc* rrc_enb = nullptr; - rrc::enb_mobility_handler* cfg = nullptr; - srslte::byte_buffer_pool* pool = nullptr; - srslte::log_ref rrc_log; + rrc::ue* rrc_ue = nullptr; + rrc* rrc_enb = nullptr; + srslte::byte_buffer_pool* pool = nullptr; + srslte::log_ref rrc_log; // vars var_meas_cfg_t ue_var_meas; diff --git a/srsenb/src/stack/rrc/rrc.cc b/srsenb/src/stack/rrc/rrc.cc index 3aeb3461c..7f674a48b 100644 --- a/srsenb/src/stack/rrc/rrc.cc +++ b/srsenb/src/stack/rrc/rrc.cc @@ -75,7 +75,6 @@ void rrc::init(const rrc_cfg_t& cfg_, nof_si_messages = generate_sibs(); config_mac(); - enb_mobility_cfg.reset(new enb_mobility_handler(this)); // Check valid inactivity timeout config uint32_t t310 = cfg.sibs[1].sib2().ue_timers_and_consts.t310.to_number(); @@ -462,12 +461,6 @@ void rrc::ho_preparation_complete(uint16_t rnti, bool is_success, srslte::unique users.at(rnti)->mobility_handler->handle_ho_preparation_complete(is_success, std::move(rrc_container)); } -uint16_t rrc::start_ho_ue_resource_alloc(const asn1::s1ap::ho_request_s& msg, - const asn1::s1ap::sourceenb_to_targetenb_transparent_container_s& container) -{ - return enb_mobility_cfg->start_ho_ue_resource_alloc(msg, container); -} - void rrc::set_erab_status(uint16_t rnti, const asn1::s1ap::bearers_subject_to_status_transfer_list_l& erabs) { auto ue_it = users.find(rnti); diff --git a/srsenb/src/stack/rrc/rrc_cell_cfg.cc b/srsenb/src/stack/rrc/rrc_cell_cfg.cc index 6281aa677..ed10fb09d 100644 --- a/srsenb/src/stack/rrc/rrc_cell_cfg.cc +++ b/srsenb/src/stack/rrc/rrc_cell_cfg.cc @@ -95,6 +95,18 @@ const cell_info_common* cell_info_common_list::get_pci(uint32_t pci) const return it == cell_list.end() ? nullptr : it->get(); } +std::vector cell_info_common_list::get_potential_cells(uint32_t enb_cc_idx) const +{ + const cell_info_common* pcell = get_cc_idx(enb_cc_idx); + std::vector cells(pcell->cell_cfg.scell_list.size() + 1); + cells[0] = pcell; + for (uint32_t i = 0; i < pcell->cell_cfg.scell_list.size(); ++i) { + uint32_t cell_id = pcell->cell_cfg.scell_list[i].cell_id; + cells[i + 1] = get_cell_id(cell_id); + } + return cells; +} + /************************* * cell ctxt dedicated ************************/ diff --git a/srsenb/src/stack/rrc/rrc_mobility.cc b/srsenb/src/stack/rrc/rrc_mobility.cc index 0cae23861..7368d085a 100644 --- a/srsenb/src/stack/rrc/rrc_mobility.cc +++ b/srsenb/src/stack/rrc/rrc_mobility.cc @@ -187,6 +187,28 @@ meas_obj_to_add_mod_s* meascfg_add_meas_obj(meas_cfg_s* meas_cfg, const meas_obj * var_meas_cfg_t class ************************************************************************************************/ +var_meas_cfg_t::var_meas_cfg_t() : rrc_log(srslte::logmap::get("RRC")) {} + +//! Add EARFCN to the varMeasCfg +std::pair var_meas_cfg_t::add_meas_obj(uint32_t dl_earfcn) +{ + auto* obj = rrc_details::find_meas_obj(var_meas.meas_obj_list, dl_earfcn); + if (obj != nullptr) { + return {false, obj}; + } + + meas_obj_t new_obj; + new_obj.meas_obj_id = srslte::find_rrc_obj_id_gap(var_meas.meas_obj_list); + asn1::rrc::meas_obj_eutra_s& eutra = new_obj.meas_obj.set_meas_obj_eutra(); + eutra.carrier_freq = dl_earfcn; + eutra.allowed_meas_bw.value = asn1::rrc::allowed_meas_bw_e::mbw6; // TODO: What value to add here? + eutra.neigh_cell_cfg.from_number(1); // No MBSFN subframes present in neighbors + eutra.offset_freq_present = false; // no offset + obj = srslte::add_rrc_obj(var_meas.meas_obj_list, new_obj); + var_meas.meas_obj_list_present = true; + return {true, obj}; +} + //! Add cell parsed in configuration file to the varMeasCfg std::tuple var_meas_cfg_t::add_cell_cfg(const meas_cell_cfg_t& cellcfg) @@ -195,7 +217,7 @@ var_meas_cfg_t::add_cell_cfg(const meas_cell_cfg_t& cellcfg) bool inserted_flag = true; q_offset_range_e offset; - asn1::number_to_enum(offset, (int8_t)cellcfg.q_offset); // TODO: What's the difference + asn1::number_to_enum(offset, (int8_t)cellcfg.q_offset); std::pair ret = rrc_details::find_cell(var_meas.meas_obj_list, cellcfg.earfcn, cellcfg.pci); @@ -221,19 +243,13 @@ var_meas_cfg_t::add_cell_cfg(const meas_cell_cfg_t& cellcfg) } } else { // no measobj has been found with same earfcn, create a new one - meas_obj_t new_obj; - new_obj.meas_obj_id = srslte::find_rrc_obj_id_gap(var_meas.meas_obj_list); - asn1::rrc::meas_obj_eutra_s& eutra = new_obj.meas_obj.set_meas_obj_eutra(); - eutra.carrier_freq = cellcfg.earfcn; - eutra.allowed_meas_bw.value = asn1::rrc::allowed_meas_bw_e::mbw6; // TODO: What value to add here? - eutra.neigh_cell_cfg.from_number(1); // TODO: What value? - eutra.offset_freq_present = true; - // TODO: Assert that q_offset is in ms - asn1::number_to_enum(eutra.offset_freq, cellcfg.q_offset); + auto ret2 = add_meas_obj(cellcfg.earfcn); + ret.first = ret2.second; + new_cell.cell_idx = 1; + auto& eutra = ret2.second->meas_obj.meas_obj_eutra(); eutra.cells_to_add_mod_list_present = true; eutra.cells_to_add_mod_list.push_back(new_cell); - ret.first = srslte::add_rrc_obj(var_meas.meas_obj_list, new_obj); ret.second = &ret.first->meas_obj.meas_obj_eutra().cells_to_add_mod_list.back(); } @@ -399,9 +415,9 @@ std::string var_meas_cfg_t::to_string() const * @param meas_cfg * @return */ -var_meas_cfg_t var_meas_cfg_t::make(uint32_t dl_earfcn, const asn1::rrc::meas_cfg_s& meas_cfg) +var_meas_cfg_t var_meas_cfg_t::make(const asn1::rrc::meas_cfg_s& meas_cfg) { - var_meas_cfg_t var{dl_earfcn}; + var_meas_cfg_t var{}; if (meas_cfg.meas_id_to_add_mod_list_present) { var.var_meas.meas_id_list_present = true; var.var_meas.meas_id_list = meas_cfg.meas_id_to_add_mod_list; @@ -437,45 +453,41 @@ var_meas_cfg_t var_meas_cfg_t::make(uint32_t dl_earfcn, const asn1::rrc::meas_cf return var; } -/************************************************************************************************* - * mobility_cfg class - ************************************************************************************************/ - -rrc::enb_mobility_handler::enb_mobility_handler(rrc* rrc_) : rrc_ptr(rrc_), cfg(&rrc_->cfg) +var_meas_cfg_t var_meas_cfg_t::make(const rrc_cfg_t& cfg) { - cell_meas_cfg_list.reserve(cfg->cell_list.size()); - - /* Create Template Cell VarMeasCfg List for each Cell */ - - for (const auto& cell_cfg : cfg->cell_list) { - cell_meas_cfg_list.emplace_back(cell_cfg.dl_earfcn); - var_meas_cfg_t& var_meas = cell_meas_cfg_list.back(); - - if (cfg->meas_cfg_present) { - // inserts all neighbor cells - for (const meas_cell_cfg_t& meascell : cell_cfg.meas_cfg.meas_cells) { - var_meas.add_cell_cfg(meascell); - } - - // insert same report cfg for all cells - for (const report_cfg_eutra_s& reportcfg : cell_cfg.meas_cfg.meas_reports) { - var_meas.add_report_cfg(reportcfg); - } + var_meas_cfg_t var_meas; + if (not cfg.meas_cfg_present) { + return var_meas; + } - // insert all meas ids - // TODO: add this to the parser - if (var_meas.rep_cfgs().size() > 0) { - for (const auto& measobj : var_meas.meas_objs()) { - var_meas.add_measid_cfg(measobj.meas_obj_id, var_meas.rep_cfgs().begin()->report_cfg_id); - } - } + for (const auto& cell_cfg : cfg.cell_list) { + // inserts all neighbor cells + for (const meas_cell_cfg_t& meascell : cell_cfg.meas_cfg.meas_cells) { + var_meas.add_cell_cfg(meascell); + } + // insert same report cfg for all cells + for (const report_cfg_eutra_s& reportcfg : cell_cfg.meas_cfg.meas_reports) { + var_meas.add_report_cfg(reportcfg); + } + // insert quantity config + var_meas.add_quant_cfg(cell_cfg.meas_cfg.quant_cfg); + } - // insert quantity config - var_meas.add_quant_cfg(cell_cfg.meas_cfg.quant_cfg); + // insert all meas ids + // TODO: add this to the parser + if (var_meas.rep_cfgs().size() > 0) { + for (const auto& measobj : var_meas.meas_objs()) { + var_meas.add_measid_cfg(measobj.meas_obj_id, var_meas.rep_cfgs().begin()->report_cfg_id); } } + + return var_meas; } +/************************************************************************************************* + * mobility_cfg class + ************************************************************************************************/ + /** * Description: Handover Request Handling * - Allocation of RNTI @@ -485,18 +497,16 @@ rrc::enb_mobility_handler::enb_mobility_handler(rrc* rrc_) : rrc_ptr(rrc_), cfg( * - Response from TeNB on whether it was able to allocate resources for user doing handover * @return rnti of created ue */ -uint16_t rrc::enb_mobility_handler::start_ho_ue_resource_alloc( - const asn1::s1ap::ho_request_s& msg, - const asn1::s1ap::sourceenb_to_targetenb_transparent_container_s& container) +uint16_t rrc::start_ho_ue_resource_alloc(const asn1::s1ap::ho_request_s& msg, + const asn1::s1ap::sourceenb_to_targetenb_transparent_container_s& container) { // TODO: Decision Making on whether the same QoS of the source eNB can be provided by target eNB /* Evaluate if cell exists */ uint32_t target_eci = container.target_cell_id.cell_id.to_number(); - const cell_info_common* target_cell = rrc_ptr->cell_common_list->get_cell_id(rrc_details::eci_to_cellid(target_eci)); + const cell_info_common* target_cell = cell_common_list->get_cell_id(rrc_details::eci_to_cellid(target_eci)); if (target_cell == nullptr) { - rrc_ptr->rrc_log->error("The S1-handover target cell_id=0x%x does not exist\n", - rrc_details::eci_to_cellid(target_eci)); + rrc_log->error("The S1-handover target cell_id=0x%x does not exist\n", rrc_details::eci_to_cellid(target_eci)); return SRSLTE_INVALID_RNTI; } @@ -509,15 +519,15 @@ uint16_t rrc::enb_mobility_handler::start_ho_ue_resource_alloc( ue_cfg.supported_cc_list[0].enb_cc_idx = target_cell->enb_cc_idx; ue_cfg.ue_bearers[0].direction = sched_interface::ue_bearer_cfg_t::BOTH; ue_cfg.supported_cc_list[0].dl_cfg.tm = SRSLTE_TM1; - uint16_t rnti = rrc_ptr->mac->reserve_new_crnti(ue_cfg); + uint16_t rnti = mac->reserve_new_crnti(ue_cfg); if (rnti == SRSLTE_INVALID_RNTI) { - rrc_ptr->rrc_log->error("Failed to allocate C-RNTI resources\n"); + rrc_log->error("Failed to allocate C-RNTI resources\n"); return SRSLTE_INVALID_RNTI; } // Register new user in RRC - rrc_ptr->add_user(rnti, ue_cfg); - auto it = rrc_ptr->users.find(rnti); + add_user(rnti, ue_cfg); + auto it = users.find(rnti); ue* ue_ptr = it->second.get(); // Reset activity timer (Response is not expected) ue_ptr->set_activity_timeout(ue::UE_INACTIVITY_TIMEOUT); @@ -530,7 +540,7 @@ uint16_t rrc::enb_mobility_handler::start_ho_ue_resource_alloc( // TODO: KeNB derivations if (not ue_ptr->mobility_handler->start_s1_tenb_ho(msg, container)) { - rrc_ptr->rem_user_thread(rnti); + rem_user_thread(rnti); return SRSLTE_INVALID_RNTI; } return rnti; @@ -544,14 +554,12 @@ rrc::ue::rrc_mobility::rrc_mobility(rrc::ue* outer_ue) : base_t(outer_ue->parent->rrc_log), rrc_ue(outer_ue), rrc_enb(outer_ue->parent), - cfg(outer_ue->parent->enb_mobility_cfg.get()), pool(outer_ue->pool), - rrc_log(outer_ue->parent->rrc_log), - ue_var_meas(outer_ue->cell_ded_list.get_ue_cc_idx(UE_PCELL_CC_IDX)->cell_common->cell_cfg.dl_earfcn) + rrc_log(outer_ue->parent->rrc_log) {} //! Method to add Mobility Info to a RRC Connection Reconfiguration Message -bool rrc::ue::rrc_mobility::fill_conn_recfg_msg(asn1::rrc::rrc_conn_recfg_r8_ies_s* conn_recfg) +bool rrc::ue::rrc_mobility::fill_conn_recfg_no_ho_cmd(asn1::rrc::rrc_conn_recfg_r8_ies_s* conn_recfg) { // only reconfigure meas_cfg if no handover is occurring. // NOTE: We basically freeze ue_var_meas for the whole duration of the handover procedure @@ -559,10 +567,11 @@ bool rrc::ue::rrc_mobility::fill_conn_recfg_msg(asn1::rrc::rrc_conn_recfg_r8_ies return false; } - // Check if there has been any update in ue_var_meas - cell_info_common* pcell = rrc_ue->get_ue_cc_cfg(UE_PCELL_CC_IDX); - asn1::rrc::meas_cfg_s& meas_cfg = conn_recfg->meas_cfg; - conn_recfg->meas_cfg_present = update_ue_var_meas_cfg(ue_var_meas, pcell->enb_cc_idx, &meas_cfg); + // Check if there has been any update in ue_var_meas based on UE current cell list + cell_ctxt_dedicated* pcell = rrc_ue->cell_ded_list.get_ue_cc_idx(UE_PCELL_CC_IDX); + uint32_t src_earfcn = pcell->get_dl_earfcn(); + auto target_cells = rrc_enb->cell_common_list->get_potential_cells(pcell->cell_common->enb_cc_idx); + conn_recfg->meas_cfg_present = update_ue_var_meas_cfg(src_earfcn, target_cells, &conn_recfg->meas_cfg); return conn_recfg->meas_cfg_present; } @@ -693,7 +702,7 @@ bool rrc::ue::rrc_mobility::start_ho_preparation(uint32_t target_eci, /*** fill AS-Config ***/ hoprep_r8.as_cfg_present = true; // NOTE: set source_meas_cnfg equal to the UE's current var_meas_cfg - var_meas_cfg_t empty_meascfg{ue_var_meas.get_dl_earfcn()}, &target_var_meas = ue_var_meas; + var_meas_cfg_t empty_meascfg{}, &target_var_meas = ue_var_meas; // // however, reset the MeasObjToAdd Cells, so that the UE does not measure again the target eNB // meas_obj_to_add_mod_s* obj = rrc_details::binary_find(target_var_meas.meas_objs(), measobj_id); // obj->meas_obj.meas_obj_eutra().cells_to_add_mod_list.resize(0); @@ -771,32 +780,25 @@ bool rrc::ue::rrc_mobility::start_s1_tenb_ho( return is_in_state(); } -bool rrc::ue::rrc_mobility::update_ue_var_meas_cfg(const asn1::rrc::meas_cfg_s& source_meas_cfg, - uint32_t src_dl_earfcn, - uint32_t target_enb_cc_idx, - asn1::rrc::meas_cfg_s* diff_meas_cfg) -{ - // Generate equivalent VarMeasCfg - var_meas_cfg_t source_var = var_meas_cfg_t::make(src_dl_earfcn, source_meas_cfg); - - // Compute difference measCfg and update UE VarMeasCfg - return update_ue_var_meas_cfg(source_var, target_enb_cc_idx, diff_meas_cfg); -} - -bool rrc::ue::rrc_mobility::update_ue_var_meas_cfg(var_meas_cfg_t& source_var_meas_cfg, - uint32_t target_enb_cc_idx, - asn1::rrc::meas_cfg_s* diff_meas_cfg) +bool rrc::ue::rrc_mobility::update_ue_var_meas_cfg(uint32_t src_earfcn, + std::vector target_cells, + asn1::rrc::meas_cfg_s* diff_meas_cfg) { - // Fetch cell VarMeasCfg - const var_meas_cfg_t& target_var_meas = rrc_enb->enb_mobility_cfg->cell_meas_cfg_list[target_enb_cc_idx]; + // Make UE Target VarMeasCfg based on parsed Config files + target cells + var_meas_cfg_t target_var_meas = var_meas_cfg_t::make(rrc_enb->cfg); + // Add PCell+Scells as MeasObjs + for (const cell_info_common* c : target_cells) { + target_var_meas.add_meas_obj(c->cell_cfg.dl_earfcn); + } + uint32_t target_earfcn = target_cells[0]->cell_cfg.dl_earfcn; // Apply TS 36.331 5.5.6.1 - If Source and Target eNB EARFCNs do no match, update SourceVarMeasCfg.MeasIdList - if (target_var_meas.get_dl_earfcn() != source_var_meas_cfg.get_dl_earfcn()) { - auto& meas_objs = source_var_meas_cfg.meas_objs(); - meas_obj_to_add_mod_s* found_target_obj = rrc_details::find_meas_obj(meas_objs, target_var_meas.get_dl_earfcn()); - meas_obj_to_add_mod_s* found_src_obj = rrc_details::find_meas_obj(meas_objs, source_var_meas_cfg.get_dl_earfcn()); + if (target_earfcn != src_earfcn) { + auto& meas_objs = ue_var_meas.meas_objs(); + meas_obj_to_add_mod_s* found_target_obj = rrc_details::find_meas_obj(meas_objs, target_earfcn); + meas_obj_to_add_mod_s* found_src_obj = rrc_details::find_meas_obj(meas_objs, src_earfcn); if (found_target_obj != nullptr and found_src_obj != nullptr) { - for (auto& mid : source_var_meas_cfg.meas_ids()) { + for (auto& mid : ue_var_meas.meas_ids()) { if (found_target_obj->meas_obj_id == mid.meas_obj_id) { mid.meas_obj_id = found_src_obj->meas_obj_id; } else if (found_src_obj->meas_obj_id == mid.meas_obj_id) { @@ -804,10 +806,10 @@ bool rrc::ue::rrc_mobility::update_ue_var_meas_cfg(var_meas_cfg_t& source } } } else if (found_src_obj != nullptr) { - for (auto it = source_var_meas_cfg.meas_ids().begin(); it != source_var_meas_cfg.meas_ids().end();) { + for (auto it = ue_var_meas.meas_ids().begin(); it != ue_var_meas.meas_ids().end();) { if (it->meas_obj_id == found_src_obj->meas_obj_id) { auto rit = it++; - source_var_meas_cfg.meas_ids().erase(rit); + ue_var_meas.meas_ids().erase(rit); } else { ++it; } @@ -816,10 +818,10 @@ bool rrc::ue::rrc_mobility::update_ue_var_meas_cfg(var_meas_cfg_t& source } // Calculate difference between source and target VarMeasCfg - bool meas_cfg_present = source_var_meas_cfg.compute_diff_meas_cfg(target_var_meas, diff_meas_cfg); + bool meas_cfg_present = ue_var_meas.compute_diff_meas_cfg(target_var_meas, diff_meas_cfg); // Update user varMeasCfg to target - rrc_ue->mobility_handler->ue_var_meas = target_var_meas; + ue_var_meas = target_var_meas; rrc_log->debug_long("New rnti=0x%x varMeasConfig: %s", rrc_ue->rnti, ue_var_meas.to_string().c_str()); return meas_cfg_present; @@ -906,7 +908,8 @@ void rrc::ue::rrc_mobility::fill_mobility_reconf_common(asn1::rrc::dl_dcch_msg_s ant_info.ue_tx_ant_sel.set(setup_e::release); // Add MeasConfig of target cell - recfg_r8.meas_cfg_present = update_ue_var_meas_cfg(ue_var_meas, target_cell.enb_cc_idx, &recfg_r8.meas_cfg); + auto target_cells = rrc_enb->cell_common_list->get_potential_cells(target_cell.enb_cc_idx); + recfg_r8.meas_cfg_present = update_ue_var_meas_cfg(src_dl_earfcn, target_cells, &recfg_r8.meas_cfg); } /** @@ -1211,7 +1214,7 @@ bool rrc::ue::rrc_mobility::apply_ho_prep_cfg(const ho_prep_info_r8_ies_s& ho } // Save measConfig - ue_var_meas = var_meas_cfg_t::make(ho_prep.as_cfg.source_dl_carrier_freq, ho_prep.as_cfg.source_meas_cfg); + ue_var_meas = var_meas_cfg_t::make(ho_prep.as_cfg.source_meas_cfg); rrc_log->debug_long("New rnti=0x%x varMeasConfig: %s", rrc_ue->rnti, ue_var_meas.to_string().c_str()); return true; diff --git a/srsenb/src/stack/rrc/rrc_ue.cc b/srsenb/src/stack/rrc/rrc_ue.cc index d8ea8ce18..8ac3efbdb 100644 --- a/srsenb/src/stack/rrc/rrc_ue.cc +++ b/srsenb/src/stack/rrc/rrc_ue.cc @@ -550,7 +550,7 @@ void rrc::ue::send_connection_reconf(srslte::unique_byte_buffer_t pdu) bearer_list.fill_pending_nas_info(conn_reconf); if (mobility_handler != nullptr) { - mobility_handler->fill_conn_recfg_msg(conn_reconf); + mobility_handler->fill_conn_recfg_no_ho_cmd(conn_reconf); } last_rrc_conn_recfg = dl_dcch_msg.msg.c1().rrc_conn_recfg(); diff --git a/srsenb/test/upper/rrc_mobility_test.cc b/srsenb/test/upper/rrc_mobility_test.cc index 8aa1b2114..d7d583606 100644 --- a/srsenb/test/upper/rrc_mobility_test.cc +++ b/srsenb/test/upper/rrc_mobility_test.cc @@ -75,7 +75,7 @@ int test_correct_insertion() // TEST 1: cell/rep insertion in empty varMeasCfg { - var_meas_cfg_t var_cfg{3400}; + var_meas_cfg_t var_cfg{}; auto ret = var_cfg.add_cell_cfg(cell1); TESTASSERT(std::get<0>(ret) and std::get<1>(ret) != nullptr); const auto& objs = var_cfg.meas_objs(); @@ -93,7 +93,7 @@ int test_correct_insertion() } { - var_meas_cfg_t var_cfg{3400}; + var_meas_cfg_t var_cfg{}; const auto& objs = var_cfg.meas_objs(); // TEST 2: insertion of out-of-order cell ids in same earfcn @@ -136,7 +136,7 @@ int test_correct_insertion() int test_correct_meascfg_calculation() { - var_meas_cfg_t src_var{3400}, target_var{3400}; + var_meas_cfg_t src_var{}, target_var{}; meas_cell_cfg_t cell1{}, cell2{}; cell1.earfcn = 3400; @@ -219,7 +219,7 @@ int test_correct_meascfg_calculation() src_var = target_var; TESTASSERT(src_var.meas_objs().size() == 1); TESTASSERT(src_var.meas_objs()[0].meas_obj.meas_obj_eutra().cells_to_add_mod_list.size() == 2); - target_var = var_meas_cfg_t{3400}; + target_var = {}; target_var.add_cell_cfg(cell2); target_var.add_report_cfg(rep1); target_var.add_report_cfg(rep3);