Commit c649e5a8 authored by Tien-Thinh Nguyen's avatar Tien-Thinh Nguyen
Browse files

update default qos rule/flow, add smf-requested modification

parent 251022eb
......@@ -55,29 +55,31 @@ class itti_nx_msg : public itti_msg {
};
//-----------------------------------------------------------------------------
class itti_nx_modify_pdu_session_request_network_requested : public itti_nx_msg {
class itti_nx_trigger_pdu_session_modification : public itti_nx_msg {
public:
itti_nx_modify_pdu_session_request_network_requested(const task_id_t orig,
const task_id_t dest)
itti_nx_trigger_pdu_session_modification(const task_id_t orig,
const task_id_t dest)
:
itti_nx_msg(NX_SESSION_MODIFICATION_REQUEST_NETWORK_REQUESTED, orig, dest) {
itti_nx_msg(NX_TRIGGER_SESSION_MODIFICATION, orig, dest) {
}
itti_nx_modify_pdu_session_request_network_requested(
const itti_nx_modify_pdu_session_request_network_requested &i)
itti_nx_trigger_pdu_session_modification(
const itti_nx_trigger_pdu_session_modification &i)
:
itti_nx_msg(i) {
itti_nx_msg(i),
msg(i.msg) {
}
itti_nx_modify_pdu_session_request_network_requested(
const itti_nx_modify_pdu_session_request_network_requested &i,
const task_id_t orig, const task_id_t dest)
itti_nx_trigger_pdu_session_modification(
const itti_nx_trigger_pdu_session_modification &i, const task_id_t orig,
const task_id_t dest)
:
itti_nx_msg(i, orig, dest) {
itti_nx_msg(i, orig, dest),
msg() {
}
const char* get_msg_name() {
return "NX_SESSION_MODIFICATION_REQUEST_NETWORK_REQUESTED";
return "NX_TRIGGER_PDU_SESSION_MODIFICATION";
}
;
// smf::pdu_session_create_sm_context_request req;
smf::pdu_session_modification_network_requested msg;
};
#endif /* ITTI_MSG_NX_HPP_INCLUDED_ */
......@@ -116,7 +116,7 @@ typedef enum {
N11_SESSION_N1N2_MESSAGE_TRANSFER_RESPONSE_STATUS,
N11_SESSION_RELEASE_SM_CONTEXT_REQUEST,
N11_SESSION_RELEASE_SM_CONTEXT_RESPONSE,
NX_SESSION_MODIFICATION_REQUEST_NETWORK_REQUESTED,
NX_TRIGGER_SESSION_MODIFICATION,
UDP_INIT,
UDP_DATA_REQ,
UDP_DATA_IND,
......
......@@ -8,9 +8,8 @@
int encode_qos_rules(QOSRules qosrules, uint8_t iei, uint8_t *buffer,
uint32_t len) {
uint8_t *len_qosrule = NULL;
uint8_t *len_qosrulesie = NULL;
uint8_t len_pos_qos_rule = 0;
uint8_t bitstream = 0;
uint32_t encoded = 0;
int encode_result = 0;
......@@ -35,6 +34,9 @@ int encode_qos_rules(QOSRules qosrules, uint8_t iei, uint8_t *buffer,
ENCODE_U8(buffer + encoded, qosrules.qosrulesie[i].qosruleidentifer,
encoded);
uint8_t *len_qosrule = NULL;
uint8_t len_pos_qos_rule = 0;
len_qosrule = buffer + encoded;
encoded++;
encoded++;
......@@ -115,6 +117,7 @@ int encode_qos_rules(QOSRules qosrules, uint8_t iei, uint8_t *buffer,
//len of qos rule ie
ENCODE_U16(len_qosrulesie, encoded - len_pos_qos_rulesie, temp);
return encoded;
}
......@@ -135,16 +138,107 @@ int decode_qos_rules(QOSRules *qosrules, uint8_t iei, uint8_t *buffer,
CHECK_LENGTH_DECODER(len - decoded, qosrules->lengthofqosrulesie);
qosrules->qosrulesie = (QOSRulesIE*) calloc(1, sizeof(QOSRulesIE));
QOSRulesIE *qosrulesie = (QOSRulesIE*) calloc(1, sizeof(QOSRulesIE));
int size = 0;
i = 0;
int pre_decoded_pos = decoded;
while (decoded < qosrules->lengthofqosrulesie) {
DECODE_U8(buffer + decoded, qosrulesie->qosruleidentifer,
decoded);
DECODE_U16(buffer + decoded, qosrulesie->LengthofQoSrule,
decoded);
DECODE_U8(buffer + decoded, bitstream, decoded);
qosrulesie->ruleoperationcode = (bitstream >> 5);
qosrulesie->dqrbit = (bitstream >> 4) & 0x01;
qosrulesie->numberofpacketfilters = bitstream & 0x0f;
if (qosrulesie->ruleoperationcode
== MODIFY_EXISTING_QOS_RULE_AND_DELETE_PACKET_FILTERS) {
qosrulesie->packetfilterlist.modifyanddelete =
(ModifyAndDelete*) calloc(
qosrulesie->numberofpacketfilters,
sizeof(ModifyAndDelete));
for (j = 0; j < qosrulesie->numberofpacketfilters; j++) {
DECODE_U8(buffer + decoded, bitstream, decoded);
qosrulesie->packetfilterlist.modifyanddelete[j]
.packetfilteridentifier = bitstream & 0x0f;
}
DECODE_U8(buffer + decoded, bitstream, decoded); //QoS rule precedence
qosrulesie->qosruleprecedence = bitstream;
DECODE_U8(buffer + decoded, bitstream, decoded); //QoS flow identifier (QFI)
qosrulesie->segregation = (bitstream >> 6) & 0x01;
qosrulesie->qosflowidentifer = bitstream & 0x3f;
} else if ((qosrulesie->ruleoperationcode == CREATE_NEW_QOS_RULE)
|| (qosrulesie->ruleoperationcode
== MODIFY_EXISTING_QOS_RULE_AND_ADD_PACKET_FILTERS)
|| (qosrulesie->ruleoperationcode
== MODIFY_EXISTING_QOS_RULE_AND_REPLACE_ALL_PACKET_FILTERS)) {
qosrulesie->packetfilterlist
.create_modifyandadd_modifyandreplace =
(Create_ModifyAndAdd_ModifyAndReplace*) calloc(
qosrulesie->numberofpacketfilters,
sizeof(Create_ModifyAndAdd_ModifyAndReplace));
for (j = 0; j < qosrulesie->numberofpacketfilters; j++) {
DECODE_U8(buffer + decoded, bitstream, decoded);
qosrulesie->packetfilterlist
.create_modifyandadd_modifyandreplace[j].packetfilterdirection =
(bitstream >> 4) & 0x03;
qosrulesie->packetfilterlist
.create_modifyandadd_modifyandreplace[j].packetfilteridentifier =
bitstream & 0x0f;
uint8_t *lenghtofpacketfiltercontents = (uint8_t*) (*(buffer + decoded)
- 1);
decoded++;
DECODE_U8(buffer + decoded, bitstream, decoded);
qosrulesie->packetfilterlist
.create_modifyandadd_modifyandreplace[j].packetfiltercontents
.component_type = bitstream;
if (qosrulesie->packetfilterlist
.create_modifyandadd_modifyandreplace[j].packetfiltercontents
.component_type != QOS_RULE_MATCHALL_TYPE) {
if ((decode_result = decode_bstring(
&qosrulesie->packetfilterlist
.create_modifyandadd_modifyandreplace[j].packetfiltercontents
.component_value,
lenghtofpacketfiltercontents, buffer + decoded, len - decoded))
< 0)
return decode_result;
else
decoded += decode_result;
}
}
DECODE_U8(buffer + decoded, bitstream, decoded);
qosrulesie->qosruleprecedence = bitstream;
DECODE_U8(buffer + decoded, bitstream, decoded);
qosrulesie->segregation = (bitstream >> 6) & 0x01;
qosrulesie->qosflowidentifer = bitstream & 0x3f;
}
i++;
size++;
}
free(qosrulesie);
qosrulesie = NULL;
decoded = pre_decoded_pos;
qosrules->qosrulesie = (QOSRulesIE*) calloc(size, sizeof(QOSRulesIE));
i = 0;
//for(i=0;i<numberrules;i++)
while (decoded < qosrules->lengthofqosrulesie) {
DECODE_U8(buffer + decoded, qosrules->qosrulesie[i].qosruleidentifer,
decoded);
// decoded++;
// decoded++;
DECODE_U16(buffer + decoded, qosrules->qosrulesie[i].LengthofQoSrule, decoded);
DECODE_U16(buffer + decoded, qosrules->qosrulesie[i].LengthofQoSrule,
decoded);
DECODE_U8(buffer + decoded, bitstream, decoded);
qosrules->qosrulesie[i].ruleoperationcode = (bitstream >> 5);
......@@ -162,9 +256,9 @@ int decode_qos_rules(QOSRules *qosrules, uint8_t iei, uint8_t *buffer,
qosrules->qosrulesie[i].packetfilterlist.modifyanddelete[j]
.packetfilteridentifier = bitstream & 0x0f;
}
DECODE_U8(buffer + decoded, bitstream, decoded); //QoS rule precedence
DECODE_U8(buffer + decoded, bitstream, decoded); //QoS rule precedence
qosrules->qosrulesie[i].qosruleprecedence = bitstream;
DECODE_U8(buffer + decoded, bitstream, decoded); //QoS flow identifier (QFI)
DECODE_U8(buffer + decoded, bitstream, decoded); //QoS flow identifier (QFI)
qosrules->qosrulesie[i].segregation = (bitstream >> 6) & 0x01;
qosrules->qosrulesie[i].qosflowidentifer = bitstream & 0x3f;
} else if ((qosrules->qosrulesie[i].ruleoperationcode == CREATE_NEW_QOS_RULE)
......@@ -220,6 +314,7 @@ int decode_qos_rules(QOSRules *qosrules, uint8_t iei, uint8_t *buffer,
i++;
}
return decoded;
}
......
......@@ -924,15 +924,29 @@ void smf_app::handle_pdu_session_release_sm_context_request(
}
//------------------------------------------------------------------------------
void smf_app::handle_network_requested_pdu_session_modification() {
std::shared_ptr<itti_nx_modify_pdu_session_request_network_requested> itti_msg =
std::make_shared<itti_nx_modify_pdu_session_request_network_requested>(
void smf_app::trigger_pdu_session_modification () {
//SMF-requested session modification, see section 4.3.3.2@3GPP TS 23.502
//The SMF may decide to modify PDU Session. This procedure also may be
//triggered based on locally configured policy or triggered from the (R)AN (see clause 4.2.6 and clause 4.9.1).
//It may also be triggered if the UP connection is activated (as described in Service Request procedure) and the
//SMF has marked that the status of one or more QoS Flows are deleted in the 5GC but not synchronized with
//the UE yet.
std::shared_ptr<itti_nx_trigger_pdu_session_modification> itti_msg =
std::make_shared<itti_nx_trigger_pdu_session_modification>(
TASK_SMF_N11, TASK_SMF_APP);
//step 1. collect the necessary information
supi_t supi = { };
std::string dnn;
pdu_session_id_t pdu_session_id = { 0 };
snssai_t nssai = { };
snssai_t snssai = { };
itti_msg->msg.set_supi(supi);
itti_msg->msg.set_dnn(dnn);
itti_msg->msg.set_pdu_session_id(pdu_session_id);
itti_msg->msg.set_snssai(snssai);
supi64_t supi64 = smf_supi_to_u64(supi);
......@@ -944,20 +958,13 @@ void smf_app::handle_network_requested_pdu_session_modification() {
Logger::smf_app().debug("Retrieve SMF context with SUPI " SUPI_64_FMT "",
supi64);
} else {
Logger::smf_app().debug("SMF context with SUPI " SUPI_64_FMT "does not exist",
supi64);
return;
}
//get dnn context
std::shared_ptr<dnn_context> sd = { };
if (!sc.get()->find_dnn_context(nssai, dnn, sd)) {
if (nullptr == sd.get()) {
return;
}
}
// handle the message in smf_context
// sc.get()->handle_network_requested_pdu_session_modification(itti_msg);
sc.get()->handle_pdu_session_modification_network_requested(itti_msg);
}
......
......@@ -218,11 +218,11 @@ class smf_app {
std::shared_ptr<itti_n11_release_sm_context_request> smreq);
/*
* Handle network-requested pdu session modification
* Trigger pdu session modification
* @param should be updated
* @return void
*/
void handle_network_requested_pdu_session_modification();
void trigger_pdu_session_modification();
/*
* Verify if SM Context is existed for this Supi
......
This diff is collapsed.
......@@ -78,8 +78,6 @@ class smf_qos_flow {
far_id_ul = { };
far_id_dl = { };
released = false;
qos_rules_to_be_synchronised = {};
qos_rules = {};
qos_profile = {};
}
......@@ -97,26 +95,14 @@ class smf_qos_flow {
pfcp::pdr_id_t pdr_id_ul;
pfcp::pdr_id_t pdr_id_dl;
pfcp::precedence_t precedence;
//pfcp::pdi pdi;
// may use std::optional ? (fragment memory)
std::pair<bool, pfcp::far_id_t> far_id_ul;
std::pair<bool, pfcp::far_id_t> far_id_dl;
bool released; // finally seems necessary, TODO try to find heuristic ?
void get_default_qos_rule(QOSRulesIE &qos_rule) const;
void get_qos_rule(uint8_t rule_id, QOSRulesIE &qos_rule) const;
void update_qos_rule(QOSRulesIE qos_rule);
void add_qos_rule(QOSRulesIE qos_rule);
pdu_session_id_t pdu_session_id;
//rule_id <-> qos_rule
std::map<uint8_t, QOSRulesIE> qos_rules;
//std::vector<QOSRulesIE> qos_rules;
std::vector<uint8_t> qos_rules_to_be_synchronised;
//QoS profile
qos_profile_t qos_profile;
//cause
uint8_t cause_value;
qos_profile_t qos_profile; //QoS profile
uint8_t cause_value; //cause
};
......@@ -137,6 +123,7 @@ class smf_pdu_session : public std::enable_shared_from_this<smf_pdu_session> {
up_fseid = { };
qos_flows.clear();
released = false;
default_qfi.qfi = NO_QOS_FLOW_IDENTIFIER_ASSIGNED ;
pdu_session_status = pdu_session_status_e::PDU_SESSION_INACTIVE;
timer_T3590 = ITTI_INVALID_TIMER_ID;
timer_T3591 = ITTI_INVALID_TIMER_ID;
......@@ -152,8 +139,8 @@ class smf_pdu_session : public std::enable_shared_from_this<smf_pdu_session> {
bool get_qos_flow(const pfcp::far_id_t &far_id, smf_qos_flow &q);
bool get_qos_flow(const pfcp::qfi_t &qfi, smf_qos_flow &q);
void add_qos_flow(smf_qos_flow &flow);
smf_qos_flow& get_qos_flow(const pfcp::qfi_t &qfi);
void get_qos_flows(std::vector<smf_qos_flow> &flows);
void set_default_qos_flow(const pfcp::qfi_t &qfi);
bool find_qos_flow(const pfcp::pdr_id_t &pdr_id, smf_qos_flow &flow);
bool has_qos_flow(const pfcp::pdr_id_t &pdr_id, pfcp::qfi_t &qfi);
......@@ -195,10 +182,28 @@ class smf_pdu_session : public std::enable_shared_from_this<smf_pdu_session> {
void generate_qos_rule_id(uint8_t &rule_id);
void release_qos_rule_id(const uint8_t &rule_id);
pdn_type_t get_pdn_type() const;
void get_qos_rules_to_be_synchronised(std::vector<QOSRulesIE> &qos_rules) const;
/*
* Get list of QoS rules associated with a given QFI
* @param [pfcp::qfi_t] qfi
* @param [std::vector<QOSRulesIE> &] rules
* @void
*/
void get_qos_rules(pfcp::qfi_t qfi,
std::vector<QOSRulesIE> &rules) const;
/*
* Get default QoS Rule associated with this PDU Session
* @param [QOSRulesIE &] qos_rule
* @void
*/
bool get_default_qos_rule(QOSRulesIE &qos_rule) const;
bool get_qos_rule(uint8_t rule_id, QOSRulesIE &qos_rule) const;
void update_qos_rule(QOSRulesIE qos_rule);
void add_qos_rule(QOSRulesIE qos_rule);
pdn_type_t get_pdn_type() const;
bool ipv4; // IP Address(es): IPv4 address and/or IPv6 prefix
bool ipv6; // IP Address(es): IPv4 address and/or IPv6 prefix
......@@ -223,7 +228,11 @@ class smf_pdu_session : public std::enable_shared_from_this<smf_pdu_session> {
std::string amf_id;
// QFI <-> QoS Flow
std::map<uint8_t, smf_qos_flow> qos_flows;
//pdu session status
pfcp::qfi_t default_qfi;
// QFI <-> QoS Rules
std::map<uint8_t, QOSRulesIE> qos_rules;
std::vector<uint8_t> qos_rules_to_be_synchronised;
std::vector<uint8_t> qos_rules_to_be_removed;
pdu_session_status_e pdu_session_status;
timer_id_t timer_T3590;
timer_id_t timer_T3591;
......@@ -363,6 +372,9 @@ class smf_context : public std::enable_shared_from_this<smf_context> {
void handle_pdu_session_release_sm_context_request(
std::shared_ptr<itti_n11_release_sm_context_request> smreq);
void handle_pdu_session_modification_network_requested(
std::shared_ptr<itti_nx_trigger_pdu_session_modification> msg);
/*
* Find DNN context with name
* @param [const std::string&] dnn
......@@ -456,7 +468,8 @@ class smf_context : public std::enable_shared_from_this<smf_context> {
void get_default_qos_flow_description(
QOSFlowDescriptionsContents &qos_flow_description,
uint8_t pdu_session_type);
uint8_t pdu_session_type,
const pfcp::qfi_t &qfi);
void get_session_ambr(SessionAMBR &session_ambr, const snssai_t &snssai,
const std::string &dnn);
......
......@@ -51,8 +51,15 @@ void qos_flow_context_updated::set_dl_fteid(const fteid_t &teid) {
}
//-----------------------------------------------------------------------------
void qos_flow_context_updated::set_qos_rule(const QOSRulesIE &rule) {
qos_rule = rule;
void qos_flow_context_updated::add_qos_rule(const QOSRulesIE &rule) {
uint8_t rule_id = rule.qosruleidentifer;
if ((rule_id >= QOS_RULE_IDENTIFIER_FIRST )
and (rule_id <= QOS_RULE_IDENTIFIER_LAST )) {
qos_rules.erase(rule_id);
qos_rules.insert(std::pair<uint8_t, QOSRulesIE>(rule_id, rule));
Logger::smf_app().trace("qos_flow_context_updated::add_qos_rule(%d) success",
rule_id);
}
}
void qos_flow_context_updated::set_qos_profile(const qos_profile_t &profile) {
......@@ -567,3 +574,72 @@ uint8_t pdu_session_release_sm_context_response::get_cause() {
return m_cause;
}
//-----------------------------------------------------------------------------
void pdu_session_modification_network_requested::set_cause(uint8_t cause) {
m_cause = cause;
}
//-----------------------------------------------------------------------------
uint8_t pdu_session_modification_network_requested::get_cause() {
return m_cause;
}
//-----------------------------------------------------------------------------
void pdu_session_modification_network_requested::set_http_code(
Pistache::Http::Code code) {
m_code = code;
}
//-----------------------------------------------------------------------------
Pistache::Http::Code pdu_session_modification_network_requested::get_http_code() {
return m_code;
}
//-----------------------------------------------------------------------------
std::string pdu_session_modification_network_requested::get_n2_sm_information() const {
return m_n2_sm_information;
}
//-----------------------------------------------------------------------------
void pdu_session_modification_network_requested::set_n2_sm_information(
std::string const &value) {
m_n2_sm_information = value;
m_n2_sm_info_is_set = true;
}
//-----------------------------------------------------------------------------
std::string pdu_session_modification_network_requested::get_n1_sm_message() const {
return m_n1_sm_message;
}
//-----------------------------------------------------------------------------
void pdu_session_modification_network_requested::set_n1_sm_message(
std::string const &value) {
m_n1_sm_message = value;
m_n1_sm_msg_is_set = true;
}
//-----------------------------------------------------------------------------
bool pdu_session_modification_network_requested::n1_sm_msg_is_set() const {
return m_n1_sm_msg_is_set;
}
//-----------------------------------------------------------------------------
bool pdu_session_modification_network_requested::n2_sm_info_is_set() const {
return m_n2_sm_info_is_set;
}
//-----------------------------------------------------------------------------
void pdu_session_modification_network_requested::set_amf_url(
std::string const &value) {
amf_url = value;
}
//-----------------------------------------------------------------------------
std::string pdu_session_modification_network_requested::get_amf_url() const {
return amf_url;
}
......@@ -53,6 +53,7 @@ typedef enum {
PDU_SESSION_UPDATE_SM_CONTEXT_RESPONSE,
PDU_SESSION_RELEASE_SM_CONTEXT_REQUEST,
PDU_SESSION_RELEASE_SM_CONTEXT_RESPONSE,
PDU_SESSION_MODIFICATION_SMF_REQUESTED,
PDU_SESSION_MSG_TYPE_MAX
} pdu_session_msg_type_t;
......@@ -67,7 +68,7 @@ class qos_flow_context_updated {
qfi(),
ul_fteid(),
dl_fteid(),
qos_rule(),
// qos_rule(),
qos_profile(),
to_be_removed(false) {
}
......@@ -76,14 +77,15 @@ class qos_flow_context_updated {
void set_qfi(const pfcp::qfi_t &q);
void set_ul_fteid(const fteid_t &teid);
void set_dl_fteid(const fteid_t &teid);
void set_qos_rule(const QOSRulesIE &rule);
void add_qos_rule (const QOSRulesIE &rule);
void set_qos_profile(const qos_profile_t &profile);
void set_priority_level(uint8_t p);
uint8_t cause_value;
pfcp::qfi_t qfi;
fteid_t ul_fteid;
fteid_t dl_fteid;
QOSRulesIE qos_rule;
// QOSRulesIE qos_rule;
std::map <uint8_t, QOSRulesIE> qos_rules;
qos_profile_t qos_profile;
bool to_be_removed;
};
......@@ -580,6 +582,56 @@ class pdu_session_release_sm_context_response : public pdu_session_msg {
uint8_t m_cause;
};
//---------------------------------------------------------------------------------------
class pdu_session_modification_network_requested : public pdu_session_msg {
public:
pdu_session_modification_network_requested()
:
pdu_session_msg(PDU_SESSION_MODIFICATION_SMF_REQUESTED) {
m_n1_sm_msg_is_set = false;
m_n2_sm_info_is_set = false;
m_cause = 0;
m_code = { };
m_supi = { };
}
pdu_session_modification_network_requested(supi_t supi, pdu_session_id_t pdi,
std::string dnn, snssai_t snssai)
:
pdu_session_msg(PDU_SESSION_MODIFICATION_SMF_REQUESTED, supi, pdi, dnn,
snssai) {
m_n1_sm_msg_is_set = false;
m_n2_sm_info_is_set = false;
m_cause = 0;
m_code = { };
}
void set_cause(uint8_t cause);
uint8_t get_cause();
void set_http_code(Pistache::Http::Code code);
Pistache::Http::Code get_http_code();
std::string get_n2_sm_information() const;
void set_n2_sm_information(std::string const &value);
std::string get_n1_sm_message() const;
void set_n1_sm_message(std::string const &value);
bool n1_sm_msg_is_set() const;
bool n2_sm_info_is_set() const;
void set_amf_url(std::string const &value);
std::string get_amf_url() const;
nlohmann::json n1n2_message_transfer_data; //N1N2MessageTransferReqData from oai::amf::model
private:
std::string m_n1_sm_message; //N1 SM message after decoding
bool m_n1_sm_msg_is_set;
std::string m_n2_sm_information; //N2 SM info after decoding
bool m_n2_sm_info_is_set;
uint8_t m_cause;
Pistache::Http::Code m_code;
supi_t m_supi;
std::string m_supi_prefix;
std::string amf_url;
};
}
#endif
......@@ -178,41 +178,17 @@ void smf_n1_n2::create_n1_sm_container(pdu_session_msg &msg,
//authorized QoS rules of the PDU session: QOSRules (Section 6.2.5@3GPP TS 24.501)
//(Section 6.4.1.3@3GPP TS 24.501 V16.1.0) Make sure that the number of the packet filters used in the authorized QoS rules of the PDU Session does not
// exceed the maximum number of packet filters supported by the UE for the PDU session
sm_msg->pdu_session_establishment_accept.qosrules.lengthofqosrulesie = 1;
sm_msg->pdu_session_establishment_accept.qosrules.lengthofqosrulesie = qos_flow.qos_rules.size();
sm_msg->pdu_session_establishment_accept.qosrules.qosrulesie =
(QOSRulesIE*) calloc(1, sizeof(QOSRulesIE));
sm_msg->pdu_session_establishment_accept.qosrules.qosrulesie[0]
.qosruleidentifer = qos_flow.qos_rule.qosruleidentifer;
sm_msg->pdu_session_establishment_accept.qosrules.qosrulesie[0]
.ruleoperationcode = qos_flow.qos_rule.ruleoperationcode;
sm_msg->pdu_session_establishment_accept.qosrules.qosrulesie[0].dqrbit =
qos_flow.qos_rule.dqrbit;
sm_msg->pdu_session_establishment_accept.qosrules.qosrulesie[0]
.numberofpacketfilters = qos_flow.qos_rule.numberofpacketfilters;
//1st rule
sm_msg->pdu_session_establishment_accept.qosrules.qosrulesie[0]
.packetfilterlist.create_modifyandadd_modifyandreplace =
(Create_ModifyAndAdd_ModifyAndReplace*) calloc(
1, sizeof(Create_ModifyAndAdd_ModifyAndReplace));
sm_msg->pdu_session_establishment_accept.qosrules.qosrulesie[0]
.packetfilterlist.create_modifyandadd_modifyandreplace
->packetfilterdirection = qos_flow.qos_rule.packetfilterlist
.create_modifyandadd_modifyandreplace->packetfilterdirection;
sm_msg->pdu_session_establishment_accept.qosrules.qosrulesie[0]