Added handling of inter rat measurement config function

Make report config more agonistic
master
David Rupprecht 4 years ago committed by Andre Puschmann
parent 2e51cfc1a5
commit d4fb2dfb16

@ -28,6 +28,10 @@ using namespace asn1::rrc;
typedef std::vector<phy_cell_t> cell_triggered_t; typedef std::vector<phy_cell_t> cell_triggered_t;
// TODO make this agnostic with srsenb
int get_carrier_freq(const meas_obj_to_add_mod_s& obj);
meas_obj_to_add_mod_s* find_meas_obj_map(std::map<uint32_t, meas_obj_to_add_mod_s>& l, uint32_t earfcn);
// RRC Measurements class // RRC Measurements class
class rrc::rrc_meas class rrc::rrc_meas
{ {
@ -92,11 +96,13 @@ private:
void reset(); void reset();
phy_quant_t get_filter_a(); phy_quant_t get_filter_a();
void remove_measId(const uint32_t measId); void remove_measId(const uint32_t measId);
std::list<meas_obj_eutra_s> get_active_objects(); std::list<meas_obj_to_add_mod_s> get_active_objects();
void ho_reest_finish(const uint32_t src_earfcn, const uint32_t dst_earfcn); void ho_reest_finish(const uint32_t src_earfcn, const uint32_t dst_earfcn);
bool parse_meas_config(const meas_cfg_s* meas_config, bool is_ho_reest, uint32_t src_earfcn); bool parse_meas_config(const meas_cfg_s* meas_config, bool is_ho_reest, uint32_t src_earfcn);
void eval_triggers(); void eval_triggers();
void eval_triggers_eutra(uint32_t meas_id, report_cfg_eutra_s& report_cfg, meas_obj_eutra_s& meas_obj, meas_cell* serv_cell, float Ofs, float Ocs);
void report_triggers(); void report_triggers();
void report_triggers_eutra(uint32_t meas_id, report_cfg_eutra_s& report_cfg, meas_obj_eutra_s& meas_obj);
private: private:
void remove_varmeas_report(const uint32_t meas_id); void remove_varmeas_report(const uint32_t meas_id);
@ -108,15 +114,17 @@ private:
void measId_removal(const meas_id_to_rem_list_l& list); void measId_removal(const meas_id_to_rem_list_l& list);
void measId_addmod(const meas_id_to_add_mod_list_l& list); void measId_addmod(const meas_id_to_add_mod_list_l& list);
void quantity_config(const quant_cfg_s& cfg); void quantity_config(const quant_cfg_s& cfg);
void log_debug_trigger_value(const eutra_event_s::event_id_c_& e); void log_debug_trigger_value_eutra(const eutra_event_s::event_id_c_& e);
static bool is_rsrp(report_cfg_eutra_s::trigger_quant_opts::options q); static bool is_rsrp(report_cfg_eutra_s::trigger_quant_opts::options q);
// Helpers // Helpers
void measObject_addmod_eutra(uint8_t meas_obj_id, const meas_obj_eutra_s& cfg_obj); void measObject_addmod_eutra(const meas_obj_to_add_mod_s& l);
void measObject_addmod_nr_r15(uint8_t meas_obj_id, const meas_obj_nr_r15_s& cfg_obj); void measObject_addmod_nr_r15(const meas_obj_to_add_mod_s& l);
void reportConfig_addmod_eutra(uint8_t report_cfg_id, const report_cfg_eutra_s& report_cfg); void reportConfig_addmod_eutra(const report_cfg_to_add_mod_s& l);
void reportConfig_addmod_interrat(const report_cfg_to_add_mod_s& l);
bool reportConfig_addmod_to_reportConfigList(const report_cfg_to_add_mod_s& l);
class cell_trigger_state class cell_trigger_state
{ {
@ -132,9 +140,8 @@ private:
// varMeasConfig data // varMeasConfig data
std::map<uint32_t, meas_id_to_add_mod_s> measIdList; // Uses MeasId as key std::map<uint32_t, meas_id_to_add_mod_s> measIdList; // Uses MeasId as key
std::map<uint32_t, meas_obj_eutra_s> measObjectsList; // Uses MeasObjectId as key std::map<uint32_t, meas_obj_to_add_mod_s> measObjectsList; // Uses MeasObjectId as key
std::map<uint32_t, meas_obj_nr_r15_s> measObjectsListNrR15; // Uses MeasObjectId as key std::map<uint32_t, report_cfg_to_add_mod_s> reportConfigList; // Uses ReportConfigId as key
std::map<uint32_t, report_cfg_eutra_s> reportConfigList; // Uses ReportConfigId as key
phy_quant_t filter_a = {1.0, 1.0}; // disable filtering until quantityConfig is received (see Sec. 5.5.3.2 Note 2) phy_quant_t filter_a = {1.0, 1.0}; // disable filtering until quantityConfig is received (see Sec. 5.5.3.2 Note 2)
float s_measure_value = 0.0; float s_measure_value = 0.0;

@ -27,6 +27,29 @@ using namespace asn1::rrc;
namespace srsue { namespace srsue {
int get_carrier_freq(const meas_obj_to_add_mod_s& obj)
{
if (obj.meas_obj.type().value != meas_obj_to_add_mod_s::meas_obj_c_::types_opts::meas_obj_eutra) {
return -1;
}
return obj.meas_obj.meas_obj_eutra().carrier_freq;
}
meas_obj_to_add_mod_s* find_meas_obj_map(std::map<uint32_t, meas_obj_to_add_mod_s>& l, uint32_t earfcn)
{
auto same_earfcn = [earfcn](const std::pair<uint32_t, meas_obj_to_add_mod_s>& c) {
return (int)earfcn == get_carrier_freq(c.second);
};
auto it = std::find_if(l.begin(), l.end(), same_earfcn);
if (it == l.end()) {
return nullptr;
} else {
return &(*it).second;
}
}
void rrc::rrc_meas::init(rrc* rrc_ptr_) void rrc::rrc_meas::init(rrc* rrc_ptr_)
{ {
rrc_ptr = rrc_ptr_; rrc_ptr = rrc_ptr_;
@ -58,16 +81,26 @@ float rrc::rrc_meas::rsrq_filter(const float new_value, const float avg_value)
/* Instruct PHY to start measurement on every configured frequency */ /* Instruct PHY to start measurement on every configured frequency */
void rrc::rrc_meas::update_phy() void rrc::rrc_meas::update_phy()
{ {
std::list<meas_obj_eutra_s> objects = meas_cfg.get_active_objects(); std::list<meas_obj_to_add_mod_s> objects = meas_cfg.get_active_objects();
rrc_ptr->phy->meas_stop(); rrc_ptr->phy->meas_stop();
for (const auto& obj : objects) { for (const auto& obj : objects) {
// Concatenate cells indicated by enodeb with discovered neighbours switch (obj.meas_obj.type().value) {
std::set<uint32_t> neighbour_pcis = rrc_ptr->get_cells(obj.carrier_freq); case meas_obj_to_add_mod_s::meas_obj_c_::types_opts::meas_obj_eutra: {
for (const auto& cell : obj.cells_to_add_mod_list) { std::set<uint32_t> neighbour_pcis = rrc_ptr->get_cells(obj.meas_obj.meas_obj_eutra().carrier_freq);
for (const auto& cell : obj.meas_obj.meas_obj_eutra().cells_to_add_mod_list) {
neighbour_pcis.insert(cell.pci); neighbour_pcis.insert(cell.pci);
} }
// Instruct PHY to look for cells IDs on this frequency. If neighbour_pcis is empty it will look for new cells // Instruct PHY to look for cells IDs on this frequency. If neighbour_pcis is empty it will look for new cells
rrc_ptr->phy->set_cells_to_meas(obj.carrier_freq, neighbour_pcis); rrc_ptr->phy->set_cells_to_meas(obj.meas_obj.meas_obj_eutra().carrier_freq, neighbour_pcis);
break;
}
case meas_obj_to_add_mod_s::meas_obj_c_::types_opts::meas_obj_nr_r15:
// Todo NR
default:
log_h->error("Not supported\n");
break;
}
// Concatenate cells indicated by enodeb with discovered neighbours
} }
} }
@ -352,25 +385,16 @@ cell_triggered_t rrc::rrc_meas::var_meas_report_list::get_measId_cells(const uin
} }
} }
void rrc::rrc_meas::var_meas_cfg::report_triggers() void rrc::rrc_meas::var_meas_cfg::report_triggers_eutra(uint32_t meas_id,
report_cfg_eutra_s& report_cfg,
meas_obj_eutra_s& meas_obj)
{ {
// for each measId included in the measIdList within VarMeasConfig
for (auto& m : measIdList) {
if (!reportConfigList.count(m.second.report_cfg_id) || !measObjectsList.count(m.second.meas_obj_id)) {
log_h->error("MEAS: Computing report triggers. MeasId=%d has invalid report or object settings\n", m.first);
continue;
}
report_cfg_eutra_s& report_cfg = reportConfigList.at(m.second.report_cfg_id);
meas_obj_eutra_s& meas_obj = measObjectsList.at(m.second.meas_obj_id);
if (report_cfg.trigger_type.type() == report_cfg_eutra_s::trigger_type_c_::types::event) { if (report_cfg.trigger_type.type() == report_cfg_eutra_s::trigger_type_c_::types::event) {
// if the triggerType is set to event and if the entry condition applicable for this event, // if the triggerType is set to event and if the entry condition applicable for this event,
{ {
bool new_cell_trigger = false; bool new_cell_trigger = false;
cell_triggered_t cells_triggered_list = meas_report->get_measId_cells(m.first); cell_triggered_t cells_triggered_list = meas_report->get_measId_cells(meas_id);
for (auto& cell : trigger_state[m.first]) { for (auto& cell : trigger_state[meas_id]) {
if (cell.second.is_enter_equal(report_cfg.trigger_type.event().time_to_trigger.to_number())) { if (cell.second.is_enter_equal(report_cfg.trigger_type.event().time_to_trigger.to_number())) {
// Do not add if already exists // Do not add if already exists
if (std::find_if(cells_triggered_list.begin(), cells_triggered_list.end(), [&cell](const phy_cell_t& c) { if (std::find_if(cells_triggered_list.begin(), cells_triggered_list.end(), [&cell](const phy_cell_t& c) {
@ -386,34 +410,34 @@ void rrc::rrc_meas::var_meas_cfg::report_triggers()
// include a measurement reporting entry within the VarMeasReportList for this measId (nof_reports reset // include a measurement reporting entry within the VarMeasReportList for this measId (nof_reports reset
// inside) include the concerned cell(s) in the cellsTriggeredList defined within the VarMeasReportList // inside) include the concerned cell(s) in the cellsTriggeredList defined within the VarMeasReportList
meas_report->set_measId(m.first, meas_obj.carrier_freq, report_cfg, cells_triggered_list); meas_report->set_measId(meas_id, meas_obj.carrier_freq, report_cfg, cells_triggered_list);
// initiate the measurement reporting procedure, as specified in 5.5.5; // initiate the measurement reporting procedure, as specified in 5.5.5;
meas_report->generate_report(m.first); meas_report->generate_report(meas_id);
} }
} }
{ {
// if the triggerType is set to event and if the leaving condition applicable for this event is fulfilled ... // if the triggerType is set to event and if the leaving condition applicable for this event is fulfilled ...
cell_triggered_t cells_triggered_list = meas_report->get_measId_cells(m.first); cell_triggered_t cells_triggered_list = meas_report->get_measId_cells(meas_id);
// remove the concerned cell(s) in the cellsTriggeredList defined within the VarMeasReportList // remove the concerned cell(s) in the cellsTriggeredList defined within the VarMeasReportList
auto it = cells_triggered_list.begin(); auto it = cells_triggered_list.begin();
while (it != cells_triggered_list.end()) { while (it != cells_triggered_list.end()) {
if (trigger_state[m.first][it->pci].is_exit_equal( if (trigger_state[meas_id][it->pci].is_exit_equal(
report_cfg.trigger_type.event().time_to_trigger.to_number())) { report_cfg.trigger_type.event().time_to_trigger.to_number())) {
it = cells_triggered_list.erase(it); it = cells_triggered_list.erase(it);
meas_report->upd_measId(m.first, cells_triggered_list); meas_report->upd_measId(meas_id, cells_triggered_list);
// if reportOnLeave is set to TRUE for the corresponding reporting configuration // if reportOnLeave is set to TRUE for the corresponding reporting configuration
if (report_cfg.trigger_type.event().event_id.type() == eutra_event_s::event_id_c_::types::event_a3 && if (report_cfg.trigger_type.event().event_id.type() == eutra_event_s::event_id_c_::types::event_a3 &&
report_cfg.trigger_type.event().event_id.event_a3().report_on_leave) { report_cfg.trigger_type.event().event_id.event_a3().report_on_leave) {
// initiate the measurement reporting procedure, as specified in 5.5.5; // initiate the measurement reporting procedure, as specified in 5.5.5;
meas_report->generate_report(m.first); meas_report->generate_report(meas_id);
} }
// if the cellsTriggeredList defined within the VarMeasReportList for this measId is empty: // if the cellsTriggeredList defined within the VarMeasReportList for this measId is empty:
if (cells_triggered_list.empty()) { if (cells_triggered_list.empty()) {
remove_varmeas_report(m.first); remove_varmeas_report(meas_id);
} }
} else { } else {
it++; it++;
@ -429,17 +453,17 @@ void rrc::rrc_meas::var_meas_cfg::report_triggers()
uint32_t serving_pci = serv_cell->get_pci(); uint32_t serving_pci = serv_cell->get_pci();
// remove all cells in the cellsTriggeredList that are no neighbor cells anymore // remove all cells in the cellsTriggeredList that are no neighbor cells anymore
cell_triggered_t cells_triggered_list = meas_report->get_measId_cells(m.first); cell_triggered_t cells_triggered_list = meas_report->get_measId_cells(meas_id);
auto it = cells_triggered_list.begin(); auto it = cells_triggered_list.begin();
while (it != cells_triggered_list.end()) { while (it != cells_triggered_list.end()) {
if (not rrc_ptr->has_neighbour_cell(it->earfcn, it->pci) and it->pci != serving_pci) { if (not rrc_ptr->has_neighbour_cell(it->earfcn, it->pci) and it->pci != serving_pci) {
log_h->debug("MEAS: Removing unknown PCI=%d from event trigger list\n", it->pci); log_h->debug("MEAS: Removing unknown PCI=%d from event trigger list\n", it->pci);
it = cells_triggered_list.erase(it); it = cells_triggered_list.erase(it);
meas_report->upd_measId(m.first, cells_triggered_list); meas_report->upd_measId(meas_id, cells_triggered_list);
// if the cellsTriggeredList defined within the VarMeasReportList for this measId is empty: // if the cellsTriggeredList defined within the VarMeasReportList for this measId is empty:
if (cells_triggered_list.empty()) { if (cells_triggered_list.empty()) {
remove_varmeas_report(m.first); remove_varmeas_report(meas_id);
} }
} else { } else {
it++; it++;
@ -447,6 +471,28 @@ void rrc::rrc_meas::var_meas_cfg::report_triggers()
} }
} }
} }
}
void rrc::rrc_meas::var_meas_cfg::report_triggers()
{
// for each measId included in the measIdList within VarMeasConfig
for (auto& m : measIdList) {
if (!reportConfigList.count(m.second.report_cfg_id) || !measObjectsList.count(m.second.meas_obj_id)) {
log_h->error("MEAS: Computing report triggers. MeasId=%d has invalid report or object settings\n", m.first);
continue;
}
report_cfg_to_add_mod_s& report_cfg = reportConfigList.at(m.second.report_cfg_id);
meas_obj_to_add_mod_s& meas_obj = measObjectsList.at(m.second.meas_obj_id);
if (meas_obj.meas_obj.type().value == meas_obj_to_add_mod_s::meas_obj_c_::types_opts::meas_obj_eutra &&
report_cfg.report_cfg.type().value == report_cfg_to_add_mod_s::report_cfg_c_::types::report_cfg_eutra) {
report_triggers_eutra(m.first, report_cfg.report_cfg.report_cfg_eutra(), meas_obj.meas_obj.meas_obj_eutra());
} else {
log_h->error("Unsupported combination of measurement object type %s and report config type %s \n",
meas_obj.meas_obj.type().to_string().c_str(),
report_cfg.report_cfg.type().to_string().c_str());
}
// upon expiry of the periodical reporting timer for this measId // upon expiry of the periodical reporting timer for this measId
if (meas_report->is_timer_expired(m.first)) { if (meas_report->is_timer_expired(m.first)) {
@ -460,51 +506,13 @@ bool rrc::rrc_meas::var_meas_cfg::is_rsrp(report_cfg_eutra_s::trigger_quant_opts
return q == report_cfg_eutra_s::trigger_quant_opts::rsrp; return q == report_cfg_eutra_s::trigger_quant_opts::rsrp;
} }
/* Evaluate event trigger conditions for each cell 5.5.4 */ void rrc::rrc_meas::var_meas_cfg::eval_triggers_eutra(uint32_t meas_id,
void rrc::rrc_meas::var_meas_cfg::eval_triggers() report_cfg_eutra_s& report_cfg,
meas_obj_eutra_s& meas_obj,
meas_cell* serv_cell,
float Ofs,
float Ocs)
{ {
meas_cell* serv_cell = rrc_ptr->get_serving_cell();
if (serv_cell == nullptr) {
log_h->warning("MEAS: Serving cell not set when evaluating triggers\n");
return;
}
uint32_t serving_earfcn = serv_cell->get_earfcn();
uint32_t serving_pci = serv_cell->get_pci();
// Obtain serving cell specific offset
float Ofs = 0;
float Ocs = 0;
auto serving_obj = std::find_if(
measObjectsList.begin(), measObjectsList.end(), [serving_earfcn](const std::pair<uint32_t, meas_obj_eutra_s>& c) {
return c.second.carrier_freq == serving_earfcn;
});
if (serving_obj != measObjectsList.end()) {
Ofs = offset_val(serving_obj->second);
auto serving_cell_off = find_pci_in_meas_obj(serving_obj->second, serving_pci);
if (serving_cell_off != serving_obj->second.cells_to_add_mod_list.end()) {
Ocs = serving_cell_off->cell_individual_offset.to_number();
}
}
for (auto& m : measIdList) {
if (!reportConfigList.count(m.second.report_cfg_id) || !measObjectsList.count(m.second.meas_obj_id)) {
log_h->error("MEAS: Computing report triggers. MeasId=%d has invalid report or object settings\n", m.first);
continue;
}
log_h->debug("MEAS: Calculating trigger for MeasId=%d, ObjectId=%d, ReportId=%d\n",
m.first,
m.second.meas_obj_id,
m.second.report_cfg_id);
report_cfg_eutra_s& report_cfg = reportConfigList.at(m.second.report_cfg_id);
meas_obj_eutra_s& meas_obj = measObjectsList.at(m.second.meas_obj_id);
double hyst = 0.5 * report_cfg.trigger_type.event().hysteresis; double hyst = 0.5 * report_cfg.trigger_type.event().hysteresis;
float Ms = is_rsrp(report_cfg.trigger_quant.value) ? serv_cell->get_rsrp() : serv_cell->get_rsrq(); float Ms = is_rsrp(report_cfg.trigger_quant.value) ? serv_cell->get_rsrp() : serv_cell->get_rsrq();
@ -516,7 +524,6 @@ void rrc::rrc_meas::var_meas_cfg::eval_triggers()
eutra_event_s::event_id_c_ event_id = report_cfg.trigger_type.event().event_id; eutra_event_s::event_id_c_ event_id = report_cfg.trigger_type.event().event_id;
if (report_cfg.trigger_type.type() == report_cfg_eutra_s::trigger_type_c_::types::event) { if (report_cfg.trigger_type.type() == report_cfg_eutra_s::trigger_type_c_::types::event) {
// A1 & A2 are for serving cell only // A1 & A2 are for serving cell only
if (event_id.type().value < eutra_event_s::event_id_c_::types::event_a3) { if (event_id.type().value < eutra_event_s::event_id_c_::types::event_a3) {
@ -541,7 +548,7 @@ void rrc::rrc_meas::var_meas_cfg::eval_triggers()
exit_condition = Ms - hyst > thresh; exit_condition = Ms - hyst > thresh;
} }
trigger_state[m.first][serving_pci].event_condition(enter_condition, exit_condition); trigger_state[meas_id][serv_cell->get_pci()].event_condition(enter_condition, exit_condition);
log_h->debug("MEAS: eventId=%s, Ms=%.2f, hyst=%.2f, Thresh=%.2f, enter_condition=%d, exit_condition=%d\n", log_h->debug("MEAS: eventId=%s, Ms=%.2f, hyst=%.2f, Thresh=%.2f, enter_condition=%d, exit_condition=%d\n",
event_id.type().to_string().c_str(), event_id.type().to_string().c_str(),
@ -555,15 +562,10 @@ void rrc::rrc_meas::var_meas_cfg::eval_triggers()
} else { } else {
auto cells = rrc_ptr->get_cells(meas_obj.carrier_freq); auto cells = rrc_ptr->get_cells(meas_obj.carrier_freq);
for (auto& pci : cells) { for (auto& pci : cells) {
log_h->debug(
log_h->debug("MEAS: eventId=%s, pci=%d, earfcn=%d\n", "MEAS: eventId=%s, pci=%d, earfcn=%d\n", event_id.type().to_string().c_str(), pci, meas_obj.carrier_freq);
event_id.type().to_string().c_str(),
pci,
meas_obj.carrier_freq);
float Ofn = offset_val(meas_obj); float Ofn = offset_val(meas_obj);
float Ocn = 0; float Ocn = 0;
// If the cell was provided by the configuration, check if it has an individual q_offset // If the cell was provided by the configuration, check if it has an individual q_offset
auto n = find_pci_in_meas_obj(meas_obj, pci); auto n = find_pci_in_meas_obj(meas_obj, pci);
if (n != meas_obj.cells_to_add_mod_list.end()) { if (n != meas_obj.cells_to_add_mod_list.end()) {
@ -616,7 +618,7 @@ void rrc::rrc_meas::var_meas_cfg::eval_triggers()
log_h->error("Error event %s not implemented\n", event_id.type().to_string().c_str()); log_h->error("Error event %s not implemented\n", event_id.type().to_string().c_str());
} }
trigger_state[m.first][pci].event_condition(enter_condition, exit_condition); trigger_state[meas_id][pci].event_condition(enter_condition, exit_condition);
log_h->debug( log_h->debug(
"MEAS: eventId=%s, pci=%d, Ms=%.2f, hyst=%.2f, Thresh=%.2f, enter_condition=%d, exit_condition=%d\n", "MEAS: eventId=%s, pci=%d, Ms=%.2f, hyst=%.2f, Thresh=%.2f, enter_condition=%d, exit_condition=%d\n",
@ -630,6 +632,49 @@ void rrc::rrc_meas::var_meas_cfg::eval_triggers()
} }
} }
} }
}
/* Evaluate event trigger conditions for each cell 5.5.4 */
void rrc::rrc_meas::var_meas_cfg::eval_triggers()
{
meas_cell* serv_cell = rrc_ptr->get_serving_cell();
if (serv_cell == nullptr) {
log_h->warning("MEAS: Serving cell not set when evaluating triggers\n");
return;
}
uint32_t serving_earfcn = serv_cell->get_earfcn();
uint32_t serving_pci = serv_cell->get_pci();
// Obtain serving cell specific offset
float Ofs = 0;
float Ocs = 0;
meas_obj_to_add_mod_s* serving_obj = find_meas_obj_map(measObjectsList, serving_earfcn);
if (serving_obj != nullptr &&
serving_obj->meas_obj.type().value == meas_obj_to_add_mod_s::meas_obj_c_::types_opts::meas_obj_eutra) {
Ofs = offset_val(serving_obj->meas_obj.meas_obj_eutra());
auto serving_cell_off = find_pci_in_meas_obj(serving_obj->meas_obj.meas_obj_eutra(), serving_pci);
if (serving_cell_off != serving_obj->meas_obj.meas_obj_eutra().cells_to_add_mod_list.end()) {
Ocs = serving_cell_off->cell_individual_offset.to_number();
}
}
for (auto& m : measIdList) {
if (!reportConfigList.count(m.second.report_cfg_id) || !measObjectsList.count(m.second.meas_obj_id)) {
log_h->error("MEAS: Computing report triggers. MeasId=%d has invalid report or object settings\n", m.first);
continue;
}
log_h->debug("MEAS: Calculating trigger for MeasId=%d, ObjectId=%d, ReportId=%d\n",
m.first,
m.second.meas_obj_id,
m.second.report_cfg_id);
report_cfg_eutra_s& report_cfg = reportConfigList.at(m.second.report_cfg_id).report_cfg.report_cfg_eutra();
meas_obj_eutra_s& meas_obj = measObjectsList.at(m.second.meas_obj_id).meas_obj.meas_obj_eutra();
eval_triggers_eutra(m.first, report_cfg, meas_obj, serv_cell, Ofs, Ocs);
} }
} }
@ -672,9 +717,9 @@ void rrc::rrc_meas::var_meas_cfg::remove_varmeas_report(const uint32_t meas_id)
trigger_state.erase(meas_id); trigger_state.erase(meas_id);
} }
std::list<meas_obj_eutra_s> rrc::rrc_meas::var_meas_cfg::get_active_objects() std::list<meas_obj_to_add_mod_s> rrc::rrc_meas::var_meas_cfg::get_active_objects()
{ {
std::list<meas_obj_eutra_s> r; std::list<meas_obj_to_add_mod_s> r;
for (auto& m : measIdList) { for (auto& m : measIdList) {
if (measObjectsList.count(m.second.meas_obj_id)) { if (measObjectsList.count(m.second.meas_obj_id)) {
r.push_back(measObjectsList.at(m.second.meas_obj_id)); r.push_back(measObjectsList.at(m.second.meas_obj_id));
@ -683,7 +728,17 @@ std::list<meas_obj_eutra_s> rrc::rrc_meas::var_meas_cfg::get_active_objects()
if (log_h->get_level() == LOG_LEVEL_DEBUG) { if (log_h->get_level() == LOG_LEVEL_DEBUG) {
log_h->debug("MEAS: Returning %zd active objects\n", r.size()); log_h->debug("MEAS: Returning %zd active objects\n", r.size());
for (auto& o : r) { for (auto& o : r) {
log_h->debug("MEAS: carrier_freq=%d, %u cells\n", o.carrier_freq, o.cells_to_add_mod_list.size()); switch (o.meas_obj.type().value) {
case meas_obj_to_add_mod_s::meas_obj_c_::types_opts::meas_obj_eutra:
log_h->debug("MEAS: carrier_freq=%d, %u cells\n",
o.meas_obj.meas_obj_eutra().carrier_freq,
o.meas_obj.meas_obj_eutra().cells_to_add_mod_list.size());
break;
case meas_obj_to_add_mod_s::meas_obj_c_::types_opts::meas_obj_nr_r15:
log_h->debug("MEAS: NR: carrier_freq=%d\n", o.meas_obj.meas_obj_nr_r15().carrier_freq_r15);
default:
break;
}
} }
} }
// we do a copy of all the structs here but this function is only called during reconfiguration // we do a copy of all the structs here but this function is only called during reconfiguration
@ -702,7 +757,9 @@ void rrc::rrc_meas::var_meas_cfg::ho_reest_finish(const uint32_t src_earfcn, con
auto it = measIdList.begin(); auto it = measIdList.begin();
while (it != measIdList.end()) { while (it != measIdList.end()) {
if (reportConfigList.count(it->second.report_cfg_id) && if (reportConfigList.count(it->second.report_cfg_id) &&
reportConfigList.at(it->second.report_cfg_id).trigger_type.type().value == reportConfigList.at(it->second.report_cfg_id).report_cfg.type().value ==
report_cfg_to_add_mod_s::report_cfg_c_::types_opts::report_cfg_eutra &&
reportConfigList.at(it->second.report_cfg_id).report_cfg.report_cfg_eutra().trigger_type.type().value ==
report_cfg_eutra_s::trigger_type_c_::types_opts::periodical) { report_cfg_eutra_s::trigger_type_c_::types_opts::periodical) {
it = measIdList.erase(it); it = measIdList.erase(it);
} else { } else {
@ -721,13 +778,14 @@ void rrc::rrc_meas::var_meas_cfg::ho_reest_finish(const uint32_t src_earfcn, con
// if the procedure was triggered due to inter-frequency handover or successful re-establishment to an inter- // if the procedure was triggered due to inter-frequency handover or successful re-establishment to an inter-
// frequency cell // frequency cell
if (src_earfcn != dst_earfcn) { if (src_earfcn != dst_earfcn) {
auto src_obj = std::find_if( auto src_obj = std::find_if(measObjectsList.begin(),
measObjectsList.begin(), measObjectsList.end(), [&src_earfcn](const std::pair<uint32_t, meas_obj_eutra_s>& c) { measObjectsList.end(),
return c.second.carrier_freq == src_earfcn; [&src_earfcn](const std::pair<uint32_t, meas_obj_to_add_mod_s>& c) {
return c.second.meas_obj.meas_obj_eutra().carrier_freq == src_earfcn;
}); });
auto dst_obj = std::find_if( auto dst_obj = std::find_if(
measObjectsList.begin(), measObjectsList.end(), [&dst_earfcn](const std::pair<uint32_t, meas_obj_eutra_s>& c) { measObjectsList.begin(), measObjectsList.end(), [&dst_earfcn](const std::pair<uint32_t, meas_obj_to_add_mod_s>& c) {
return c.second.carrier_freq == dst_earfcn; return c.second.meas_obj.meas_obj_eutra().carrier_freq == dst_earfcn;
}); });
if (dst_obj != measObjectsList.end()) { if (dst_obj != measObjectsList.end()) {
for (auto& m : measIdList) { for (auto& m : measIdList) {
@ -790,15 +848,18 @@ void rrc::rrc_meas::var_meas_cfg::measObject_removal(const meas_obj_to_rem_list_
} }
} }
void rrc::rrc_meas::var_meas_cfg::measObject_addmod_eutra(uint8_t meas_obj_id, const meas_obj_eutra_s& cfg_obj) void rrc::rrc_meas::var_meas_cfg::measObject_addmod_eutra(const meas_obj_to_add_mod_s& l)
{ {
bool entry_exists = measObjectsList.count(meas_obj_id) > 0; bool entry_exists = measObjectsList.count(l.meas_obj_id) > 0;
if (!entry_exists) { if (!entry_exists) {
// add a new entry for the received measObject to the measObjectList within VarMeasConfig // add a new entry for the received measObject to the measObjectList within VarMeasConfig
measObjectsList.emplace(meas_obj_id, cfg_obj); measObjectsList.emplace(l.meas_obj_id, l);
} }
meas_obj_eutra_s& local_obj = measObjectsList.at(meas_obj_id); meas_obj_eutra_s cfg_obj = l.meas_obj.meas_obj_eutra();
measObjectsList.at(l.meas_obj_id).meas_obj_id = l.meas_obj_id;
// Assert choice will check if existing meas object is of type eutra
meas_obj_eutra_s& local_obj = measObjectsList.at(l.meas_obj_id).meas_obj.meas_obj_eutra();
// if an entry with the matching measObjectId exists in the measObjectList within the VarMeasConfig // if an entry with the matching measObjectId exists in the measObjectList within the VarMeasConfig
if (entry_exists) { if (entry_exists) {
@ -844,7 +905,7 @@ void rrc::rrc_meas::var_meas_cfg::measObject_addmod_eutra(uint8_t meas_obj_id, c
// for each measId associated with this measObjectId in the measIdList within the VarMeasConfig // for each measId associated with this measObjectId in the measIdList within the VarMeasConfig
for (auto& m : measIdList) { for (auto& m : measIdList) {
if (m.second.meas_obj_id == meas_obj_id) { if (m.second.meas_obj_id == l.meas_obj_id) {
remove_varmeas_report(m.first); remove_varmeas_report(m.first);
} }
} }
@ -852,7 +913,7 @@ void rrc::rrc_meas::var_meas_cfg::measObject_addmod_eutra(uint8_t meas_obj_id, c
log_h->info("MEAS: %s objectId=%d, carrier_freq=%d, %u cells, %u black-listed cells\n", log_h->info("MEAS: %s objectId=%d, carrier_freq=%d, %u cells, %u black-listed cells\n",
!entry_exists ? "Added" : "Modified", !entry_exists ? "Added" : "Modified",
meas_obj_id, l.meas_obj_id,
local_obj.carrier_freq, local_obj.carrier_freq,
local_obj.cells_to_add_mod_list.size(), local_obj.cells_to_add_mod_list.size(),
local_obj.black_cells_to_add_mod_list.size()); local_obj.black_cells_to_add_mod_list.size());
@ -867,14 +928,18 @@ void rrc::rrc_meas::var_meas_cfg::measObject_addmod_eutra(uint8_t meas_obj_id, c
} }
} }
void rrc::rrc_meas::var_meas_cfg::measObject_addmod_nr_r15(uint8_t meas_obj_id, const meas_obj_nr_r15_s& cfg_obj) void rrc::rrc_meas::var_meas_cfg::measObject_addmod_nr_r15(const meas_obj_to_add_mod_s& l)
{ {
bool entry_exists = measObjectsListNrR15.count(meas_obj_id) > 0; bool entry_exists = measObjectsList.count(l.meas_obj_id) > 0;
if (!entry_exists) { if (!entry_exists) {
// add a new entry for the received measObject to the measObjectList within VarMeasConfig // add a new entry for the received measObject to the measObjectList within VarMeasConfig
measObjectsListNrR15.emplace(meas_obj_id, cfg_obj); measObjectsList.emplace(l.meas_obj_id, l);
} }
meas_obj_nr_r15_s& local_obj = measObjectsListNrR15.at(meas_obj_id);
meas_obj_nr_r15_s cfg_obj = l.meas_obj.meas_obj_nr_r15();
measObjectsList.at(l.meas_obj_id).meas_obj_id = l.meas_obj_id;
meas_obj_nr_r15_s& local_obj = measObjectsList.at(l.meas_obj_id).meas_obj.meas_obj_nr_r15();
// if an entry with the matching measObjectId exists in the measObjectList within the VarMeasConfig // if an entry with the matching measObjectId exists in the measObjectList within the VarMeasConfig
if (entry_exists) { if (entry_exists) {
@ -897,7 +962,7 @@ void rrc::rrc_meas::var_meas_cfg::measObject_addmod_nr_r15(uint8_t meas_obj_id,
} }
// for each measId associated with this measObjectId in the measIdList within the VarMeasConfig // for each measId associated with this measObjectId in the measIdList within the VarMeasConfig
for (auto& m : measIdList) { for (auto& m : measIdList) {
if (m.second.meas_obj_id == meas_obj_id) { if (m.second.meas_obj_id == l.meas_obj_id) {
remove_varmeas_report(m.first); remove_varmeas_report(m.first);
} }
} }
@ -905,7 +970,7 @@ void rrc::rrc_meas::var_meas_cfg::measObject_addmod_nr_r15(uint8_t meas_obj_id,
log_h->info("MEAS (NR R15): %s objectId=%d, carrier_freq=%d, %u black-listed cells\n", log_h->info("MEAS (NR R15): %s objectId=%d, carrier_freq=%d, %u black-listed cells\n",
!entry_exists ? "Added" : "Modified", !entry_exists ? "Added" : "Modified",
meas_obj_id, l.meas_obj_id,
local_obj.carrier_freq_r15, local_obj.carrier_freq_r15,
local_obj.black_cells_to_add_mod_list_r15.size()); local_obj.black_cells_to_add_mod_list_r15.size());
if (log_h->get_level() == LOG_LEVEL_DEBUG) { if (log_h->get_level() == LOG_LEVEL_DEBUG) {
@ -921,10 +986,10 @@ void rrc::rrc_meas::var_meas_cfg::measObject_addmod(const meas_obj_to_add_mod_li
for (auto& l : list) { for (auto& l : list) {
switch (l.meas_obj.type().value) { switch (l.meas_obj.type().value) {
case meas_obj_to_add_mod_s::meas_obj_c_::types_opts::meas_obj_eutra: case meas_obj_to_add_mod_s::meas_obj_c_::types_opts::meas_obj_eutra:
measObject_addmod_eutra(l.meas_obj_id, l.meas_obj.meas_obj_eutra()); measObject_addmod_eutra(l);
break; break;
case meas_obj_to_add_mod_s::meas_obj_c_::types_opts::meas_obj_nr_r15: case meas_obj_to_add_mod_s::meas_obj_c_::types_opts::meas_obj_nr_r15:
measObject_addmod_nr_r15(l.meas_obj_id, l.meas_obj.meas_obj_nr_r15()); measObject_addmod_nr_r15(l);
break; break;
default: default:
log_h->error("Unsupported measObject type: %s\n", l.meas_obj.type().to_string().c_str()); log_h->error("Unsupported measObject type: %s\n", l.meas_obj.type().to_string().c_str());
@ -956,42 +1021,72 @@ void rrc::rrc_meas::var_meas_cfg::reportConfig_removal(const report_cfg_to_rem_l
} }
} }
void rrc::rrc_meas::var_meas_cfg::reportConfig_addmod_eutra(uint8_t report_cfg_id, const report_cfg_eutra_s& report_cfg) bool rrc::rrc_meas::var_meas_cfg::reportConfig_addmod_to_reportConfigList(const report_cfg_to_add_mod_s& l)
{ {
if (!(report_cfg.trigger_type.type().value == report_cfg_eutra_s::trigger_type_c_::types_opts::event)) { bool entry_exists = reportConfigList.count(l.report_cfg_id) > 0;
log_h->error("MEAS: Periodical reports not supported. Received in reportConfigId=%d\n", report_cfg_id);
return;
}
bool entry_exists = reportConfigList.count(report_cfg_id) > 0;
if (entry_exists) { if (entry_exists) {
reportConfigList.at(report_cfg_id) = report_cfg; reportConfigList.at(l.report_cfg_id) = l;
// for each measId associated with this reportConfigId in the measIdList within the VarMeasConfig // for each measId associated with this reportConfigId in the measIdList within the VarMeasConfig
for (auto& m : measIdList) { for (auto& m : measIdList) {
if (m.second.report_cfg_id == report_cfg_id) { if (m.second.report_cfg_id == l.report_cfg_id) {
remove_varmeas_report(m.first); remove_varmeas_report(m.first);
} }
} }
} else { } else {
reportConfigList.emplace(report_cfg_id, report_cfg); reportConfigList.emplace(l.report_cfg_id, l);
}
return entry_exists;
}
void rrc::rrc_meas::var_meas_cfg::reportConfig_addmod_eutra(const report_cfg_to_add_mod_s& l)
{
const report_cfg_eutra_s& report_cfg = l.report_cfg.report_cfg_eutra();
if (!(report_cfg.trigger_type.type().value == report_cfg_eutra_s::trigger_type_c_::types_opts::event)) {
log_h->error("MEAS: Periodical reports not supported. Received in reportConfigId=%d\n", l.report_cfg_id);
return;
} }
bool entry_exists = reportConfig_addmod_to_reportConfigList(l);
log_h->info("MEAS: %s reportConfig id=%d, event-type=%s, time-to-trigger=%d ms, reportInterval=%d\n", log_h->info("MEAS: %s reportConfig id=%d, event-type=%s, time-to-trigger=%d ms, reportInterval=%d\n",
!entry_exists ? "Added" : "Modified", !entry_exists ? "Added" : "Modified",
report_cfg_id, l.report_cfg_id,
report_cfg.trigger_type.event().event_id.type().to_string().c_str(), report_cfg.trigger_type.event().event_id.type().to_string().c_str(),
report_cfg.trigger_type.event().time_to_trigger.to_number(), report_cfg.trigger_type.event().time_to_trigger.to_number(),
report_cfg.report_interv.to_number()); report_cfg.report_interv.to_number());
if (entry_exists) { if (entry_exists) {
log_debug_trigger_value(report_cfg.trigger_type.event().event_id); log_debug_trigger_value_eutra(report_cfg.trigger_type.event().event_id);
} }
} }
void rrc::rrc_meas::var_meas_cfg::reportConfig_addmod_interrat(const report_cfg_to_add_mod_s& l)
{
const report_cfg_inter_rat_s& report_cfg = l.report_cfg.report_cfg_inter_rat();
if (!(report_cfg.trigger_type.type().value == report_cfg_inter_rat_s::trigger_type_c_::types_opts::event)) {
log_h->error("MEAS: Periodical reports not supported. Received in reportConfigId=%d\n", l.report_cfg_id);
return;
}
bool entry_exists = reportConfig_addmod_to_reportConfigList(l);
log_h->info("MEAS: Inter RAT %s reportConfig id=%d, event-type=%s, time-to-trigger=%d ms, reportInterval=%d\n",
!entry_exists ? "Added" : "Modified",
l.report_cfg_id,
report_cfg.trigger_type.event().event_id.type().to_string().c_str(),
report_cfg.trigger_type.event().time_to_trigger.to_number(),
report_cfg.report_interv.to_number());
if (entry_exists) {
// TODO Debug
}
}
// perform the reporting configuration addition/ modification procedure as specified in 5.5.2.7 // perform the reporting configuration addition/ modification procedure as specified in 5.5.2.7
void rrc::rrc_meas::var_meas_cfg::reportConfig_addmod(const report_cfg_to_add_mod_list_l& list) void rrc::rrc_meas::var_meas_cfg::reportConfig_addmod(const report_cfg_to_add_mod_list_l& list)
{ {
for (auto& l : list) { for (auto& l : list) {
switch (l.report_cfg.type()) switch (l.report_cfg.type()) {
{
case report_cfg_to_add_mod_s::report_cfg_c_::types_opts::report_cfg_eutra: case report_cfg_to_add_mod_s::report_cfg_c_::types_opts::report_cfg_eutra:
reportConfig_addmod_eutra(l.report_cfg_id,l.report_cfg.report_cfg_eutra()); reportConfig_addmod_eutra(l);
break;
case report_cfg_to_add_mod_s::report_cfg_c_::types_opts::report_cfg_inter_rat:
reportConfig_addmod_interrat(l);
break; break;
default: default:
log_h->error("MEAS: Unsupported reportConfig type: %s\n", l.report_cfg.type().to_string().c_str()); log_h->error("MEAS: Unsupported reportConfig type: %s\n", l.report_cfg.type().to_string().c_str());
@ -1001,7 +1096,7 @@ void rrc::rrc_meas::var_meas_cfg::reportConfig_addmod(const report_cfg_to_add_mo
} }
// Warning: Use for Test debug purposes only. Assumes thresholds in RSRP // Warning: Use for Test debug purposes only. Assumes thresholds in RSRP
void rrc::rrc_meas::var_meas_cfg::log_debug_trigger_value(const eutra_event_s::event_id_c_& e) void rrc::rrc_meas::var_meas_cfg::log_debug_trigger_value_eutra(const eutra_event_s::event_id_c_& e)
{ {
if (log_h->get_level() == LOG_LEVEL_DEBUG) { if (log_h->get_level() == LOG_LEVEL_DEBUG) {
switch (e.type()) { switch (e.type()) {
@ -1147,7 +1242,7 @@ bool rrc::rrc_meas::var_meas_cfg::parse_meas_config(const meas_cfg_s* cfg, bool
uint32_t target_earfcn = serv_cell->get_earfcn(); uint32_t target_earfcn = serv_cell->get_earfcn();
if (std::find_if(measIdList.begin(), measIdList.end(), [&](const std::pair<uint32_t, meas_id_to_add_mod_s>& c) { if (std::find_if(measIdList.begin(), measIdList.end(), [&](const std::pair<uint32_t, meas_id_to_add_mod_s>& c) {
return measObjectsList.count(c.second.meas_obj_id) && return measObjectsList.count(c.second.meas_obj_id) &&
measObjectsList.at(c.second.meas_obj_id).carrier_freq == target_earfcn; measObjectsList.at(c.second.meas_obj_id).meas_obj.meas_obj_eutra().carrier_freq == target_earfcn;
}) == measIdList.end()) { }) == measIdList.end()) {
// Run HO procedure // Run HO procedure
ho_reest_finish(src_earfcn, target_earfcn); ho_reest_finish(src_earfcn, target_earfcn);

Loading…
Cancel
Save