diff --git a/srsgnb/hdr/stack/ric/e2ap.h b/srsgnb/hdr/stack/ric/e2ap.h index 1dcea7b03..b47d5d227 100644 --- a/srsgnb/hdr/stack/ric/e2ap.h +++ b/srsgnb/hdr/stack/ric/e2ap.h @@ -11,13 +11,16 @@ * */ +#include "e2sm_kpm.h" #include "srsran/asn1/e2ap.h" +#include "srsran/asn1/e2sm_kpm.h" #include "srsran/srsran.h" #ifndef RIC_E2AP_H #define RIC_E2AP_H using namespace asn1::e2ap; +using namespace asn1::e2sm_kpm; class e2ap { @@ -34,8 +37,12 @@ public: private: srslog::basic_logger& logger; - bool setup_response_received = false; - bool pending_subscription_request = false; + e2sm_kpm e2sm_; + bool setup_response_received = false; + bool pending_subscription_request = false; + int setup_procedure_transaction_id = 0; + uint64_t plmn_id = 3617847; + uint64_t gnb_id = 381210353; }; #endif /* RIC_E2AP_H */ diff --git a/srsgnb/hdr/stack/ric/e2sm_kpm.h b/srsgnb/hdr/stack/ric/e2sm_kpm.h new file mode 100644 index 000000000..9e4e32872 --- /dev/null +++ b/srsgnb/hdr/stack/ric/e2sm_kpm.h @@ -0,0 +1,33 @@ +/** + * + * \section COPYRIGHT + * + * Copyright 2013-2022 Software Radio Systems Limited + * + * By using this file, you agree to the terms and conditions set + * forth in the LICENSE file which can be found at the top level of + * the distribution. + * + * + */ +#include "srsran/asn1/e2sm.h" +#include "srsran/asn1/e2sm_kpm.h" +#include "srsran/srsran.h" + +#ifndef RIC_E2SM_KPM_H +#define RIC_E2SM_KPM_H + +class e2sm_kpm +{ +public: + e2sm_kpm(srslog::basic_logger& logger_); + bool generate_ran_function_description(srsran::unique_byte_buffer_t& buf); + bool process_ric_action_definition(); + bool generate_indication_header(); + bool generate_indication_message(); + +private: + srslog::basic_logger& logger; +}; + +#endif /*E2SM_KPM*/ diff --git a/srsgnb/src/stack/ric/e2ap.cc b/srsgnb/src/stack/ric/e2ap.cc index 174850138..6dea67906 100644 --- a/srsgnb/src/stack/ric/e2ap.cc +++ b/srsgnb/src/stack/ric/e2ap.cc @@ -2,7 +2,7 @@ #include "srsgnb/hdr/stack/ric/e2ap.h" #include "stdint.h" -e2ap::e2ap(srslog::basic_logger& logger) : logger(logger) {} +e2ap::e2ap(srslog::basic_logger& logger) : logger(logger), e2sm_(logger) {} e2_ap_pdu_c e2ap::generate_setup_request() { @@ -13,13 +13,12 @@ e2_ap_pdu_c e2ap::generate_setup_request() e2setup_request_s& setup = initmsg.value.e2setup_request(); setup->transaction_id.crit = asn1::crit_opts::reject; - setup->transaction_id.value.value = 1; + setup->transaction_id.value.value = setup_procedure_transaction_id; + setup->global_e2node_id.crit = asn1::crit_opts::reject; + auto& gnb_ = setup->global_e2node_id.value.set_gnb(); - setup->global_e2node_id.crit = asn1::crit_opts::reject; - auto& gnb_id = setup->global_e2node_id.value.set_gnb(); - // gnb_id.ext = true; - gnb_id.global_g_nb_id.plmn_id.from_number(3617847); - gnb_id.global_g_nb_id.gnb_id.gnb_id().from_number(381210353); + gnb_.global_g_nb_id.plmn_id.from_number(plmn_id); + gnb_.global_g_nb_id.gnb_id.gnb_id().from_number(gnb_id); setup->ra_nfunctions_added.crit = asn1::crit_opts::reject; auto& list = setup->ra_nfunctions_added.value; @@ -28,17 +27,14 @@ e2_ap_pdu_c e2ap::generate_setup_request() asn1::protocol_ie_single_container_s item; item.load_info_obj(ASN1_E2AP_ID_RA_NFUNCTION_ITEM); item.value().ra_nfunction_item().ran_function_id = 0; - // TODO use E2SM to correctly generate this message - item.value().ra_nfunction_item().ran_function_definition.from_string( - "20C04F52414E2D4532534D2D4B504D0000054F494431323305004B504D206D6F6E69746F720860283861AAE33F0060000101070050657269" - "6F646963207265706F727401051401011D004F2D4455204D6561737572656D656E7420436F6E7461696E657220666F722074686520354743" - "20636F6E6E6563746564206465706C6F796D656E74010101010001021D004F2D4455204D6561737572656D656E7420436F6E7461696E6572" - "20666F72207468652045504320636F6E6E6563746564206465706C6F796D656E74010101010001031E804F2D43552D4350204D6561737572" - "656D656E7420436F6E7461696E657220666F72207468652035474320636F6E6E6563746564206465706C6F796D656E74010101010001041E" - "804F2D43552D4350204D6561737572656D656E7420436F6E7461696E657220666F72207468652045504320636F6E6E656374656420646570" - "6C6F796D656E74010101010001051E804F2D43552D5550204D6561737572656D656E7420436F6E7461696E657220666F7220746865203547" - "4320636F6E6E6563746564206465706C6F796D656E74010101010001061E804F2D43552D5550204D6561737572656D656E7420436F6E7461" - "696E657220666F72207468652045504320636F6E6E6563746564206465706C6F796D656E7401010101"); + + // pack E2SM-KPM-PDU into ran function definition + auto& ran_func_def = item.value().ra_nfunction_item().ran_function_definition; + srsran::unique_byte_buffer_t buf = srsran::make_byte_buffer(); + e2sm_.generate_ran_function_description(buf); + ran_func_def.resize(buf->N_bytes); + std::copy(buf->msg, buf->msg + buf->N_bytes, ran_func_def.data()); + item.value().ra_nfunction_item().ran_function_oid.resize(1); setup->ra_nfunctions_added.value.push_back(item); diff --git a/srsgnb/src/stack/ric/e2sm_kpm.cc b/srsgnb/src/stack/ric/e2sm_kpm.cc new file mode 100644 index 000000000..d52872b28 --- /dev/null +++ b/srsgnb/src/stack/ric/e2sm_kpm.cc @@ -0,0 +1,66 @@ +#include "srsgnb/hdr/stack/ric/e2sm_kpm.h" + +e2sm_kpm::e2sm_kpm(srslog::basic_logger& logger_) : logger(logger_) {} + +bool e2sm_kpm::generate_ran_function_description(srsran::unique_byte_buffer_t& buf) +{ + using namespace asn1::e2sm_kpm; + e2_sm_kpm_ra_nfunction_description_s e2sm_kpm_ra_nfunction_description; + e2sm_kpm_ra_nfunction_description.ran_function_name.ran_function_instance_present = true; + e2sm_kpm_ra_nfunction_description.ran_function_name.ran_function_instance = 0; + e2sm_kpm_ra_nfunction_description.ran_function_name.ran_function_short_name.from_string("ORAN-E2SM-KPM"); + e2sm_kpm_ra_nfunction_description.ran_function_name.ran_function_e2_sm_oid.from_string("OID123"); + e2sm_kpm_ra_nfunction_description.ran_function_name.ran_function_description.from_string("KPM monitor"); + + e2sm_kpm_ra_nfunction_description.e2_sm_kpm_ra_nfunction_item.ric_event_trigger_style_list.resize(1); + auto& ric_event_trigger_style_list_item = + e2sm_kpm_ra_nfunction_description.e2_sm_kpm_ra_nfunction_item.ric_event_trigger_style_list[0]; + ric_event_trigger_style_list_item.ric_event_trigger_format_type = 5; + ric_event_trigger_style_list_item.ric_event_trigger_style_type = 1; + ric_event_trigger_style_list_item.ric_event_trigger_style_name.from_string("Periodic report"); + auto& list = e2sm_kpm_ra_nfunction_description.e2_sm_kpm_ra_nfunction_item.ric_report_style_list; + list.resize(6); + for (int i = 0; i < (int)list.size(); i++) { + auto& ric_report_style_list_item = + e2sm_kpm_ra_nfunction_description.e2_sm_kpm_ra_nfunction_item.ric_report_style_list[i]; + ric_report_style_list_item.ric_ind_hdr_format_type = 1; + ric_report_style_list_item.ric_ind_msg_format_type = 1; + ric_report_style_list_item.ric_report_style_type = i + 1; + switch (i) { + case 0: + ric_report_style_list_item.ric_report_style_name.from_string( + "O-DU Measurement Container for the 5GC connected deployment"); + break; + case 1: + ric_report_style_list_item.ric_report_style_name.from_string( + "O-DU Measurement Container for the EPC connected deployment"); + break; + case 2: + ric_report_style_list_item.ric_report_style_name.from_string( + "O-CU-CP Measurement Container for the 5GC connected deployment"); + break; + case 3: + ric_report_style_list_item.ric_report_style_name.from_string( + "O-CU-CP Measurement Container for the EPC connected deployment"); + break; + case 4: + ric_report_style_list_item.ric_report_style_name.from_string( + "O-CU-UP Measurement Container for the 5GC connected deployment"); + break; + case 5: + ric_report_style_list_item.ric_report_style_name.from_string( + "O-CU-UP Measurement Container for the EPC connected deployment"); + break; + }; + ric_report_style_list_item.ric_report_style_name.from_string("Periodic report"); + } + + logger.info("Generating RAN function description"); + asn1::bit_ref bref(buf->msg, buf->get_tailroom()); + if (e2sm_kpm_ra_nfunction_description.pack(bref) != asn1::SRSASN_SUCCESS) { + printf("Failed to pack TX E2 PDU\n"); + return false; + } + buf->N_bytes = bref.distance_bytes(); + return true; +} diff --git a/srsgnb/src/stack/ric/test/e2ap_test.cc b/srsgnb/src/stack/ric/test/e2ap_test.cc index 12a49da74..f21d5f191 100644 --- a/srsgnb/src/stack/ric/test/e2ap_test.cc +++ b/srsgnb/src/stack/ric/test/e2ap_test.cc @@ -72,10 +72,23 @@ void test_reference_e2ap_setup_request() 0x72, 0x65, 0x73, 0x70, 0x61, 0x72, 0x74}; asn1::cbit_ref bref(&e2ap_msg_foreign[0], sizeof(e2ap_msg_foreign)); - e2_ap_pdu_c pdu, pdu2; - asn1::SRSASN_CODE unpack_ret = pdu2.unpack(bref); + e2_ap_pdu_c pdu; + asn1::SRSASN_CODE unpack_ret = pdu.unpack(bref); TESTASSERT_EQ(asn1::SRSASN_SUCCESS, unpack_ret); printf("Unpacked E2AP PDU %d\n", (int)unpack_ret); + auto& ran_func_data = pdu.init_msg() + .value.e2setup_request() + ->ra_nfunctions_added.value[0] + .value() + .ra_nfunction_item() + .ran_function_definition; + srsran::byte_buffer_t ran_function_def; + asn1::cbit_ref ran_func_bref(ran_function_def.msg, ran_function_def.get_tailroom()); + std::copy(ran_func_data.data(), ran_func_data.data() + ran_func_data.size(), ran_function_def.begin()); + e2_sm_kpm_ra_nfunction_description_s e2sm_kpm_ra_nfunction_description; + asn1::SRSASN_CODE nfunc_unpack = e2sm_kpm_ra_nfunction_description.unpack(ran_func_bref); + TESTASSERT_EQ(asn1::SRSASN_SUCCESS, nfunc_unpack); + printf("Unpacked E2SM PDU (KPM RAN function description) %d\n", (int)nfunc_unpack); } void test_native_e2ap_setup_request()