pespin has uploaded this change for review. ( https://gerrit.osmocom.org/c/osmo-ttcn3-hacks/+/37033?usp=email )
Change subject: asterisk: Test sending PJSIPUnregister after registration ......................................................................
asterisk: Test sending PJSIPUnregister after registration
Related: SYS#6960 Change-Id: I309732f934a6b4979367e4ce5e5475493818cdbd --- M asterisk/AMI_Functions.ttcn M asterisk/Asterisk_Tests.ttcn M asterisk/IMS_ConnectionHandler.ttcn M library/SIP_Templates.ttcn 4 files changed, 147 insertions(+), 12 deletions(-)
git pull ssh://gerrit.osmocom.org:29418/osmo-ttcn3-hacks refs/changes/33/37033/1
diff --git a/asterisk/AMI_Functions.ttcn b/asterisk/AMI_Functions.ttcn index 9c84d00..16cf71f 100644 --- a/asterisk/AMI_Functions.ttcn +++ b/asterisk/AMI_Functions.ttcn @@ -263,6 +263,25 @@ tr_AMI_Field_Registration(registration) };
+/* Action: PJSIPUnregister + * ActionID: <value> + * Registration: volte_ims + */ +template (value) AMI_Msg +ts_AMI_Action_PJSIPUnregister(template (value) charstring registration := "volte_ims", + template (value) charstring action_id := "0001") := { + ts_AMI_Field_Action("PJSIPUnregister"), + ts_AMI_Field_ActionId(action_id), + ts_AMI_Field_Registration(registration) +}; +template (present) AMI_Msg +tr_AMI_Action_PJSIPUnregister(template (present) charstring registration := ?, + template (present) charstring action_id := ?) := { + tr_AMI_Field_Action("PJSIPUnregister"), + tr_AMI_Field_ActionId(action_id), + tr_AMI_Field_Registration(registration) +}; + /* * RESPONSES */ @@ -661,6 +680,11 @@ f_ami_transceive_match_response_success(pt, ts_AMI_Action_PJSIPRegister(register, reg_action_id)); }
+function f_ami_action_PJSIPUnregister(AMI_Msg_PT pt, charstring register) { + var charstring reg_action_id := f_gen_action_id(); + f_ami_transceive_match_response_success(pt, ts_AMI_Action_PJSIPUnregister(register, reg_action_id)); +} + function f_ami_action_AuthResponse_AUTS(AMI_Msg_PT pt, template (value) charstring registration, template (value) charstring auts) { diff --git a/asterisk/Asterisk_Tests.ttcn b/asterisk/Asterisk_Tests.ttcn index 5a51d1d..20a9e6c 100644 --- a/asterisk/Asterisk_Tests.ttcn +++ b/asterisk/Asterisk_Tests.ttcn @@ -397,16 +397,21 @@ AMI_CLIENT.receive(tr_AMI_Event_Registry(f_sip_SipAddr_to_str(pars.subscr.local_sip_record), "sip:" & mp_ims_domain, "Registered")); +}
- /* TODO: test "Action: PJSIPUnregister" */ - - /* TODO: in another test emulating a call, test "Action: DedicatedBearerStatus" */ +private function f_AMI_IMS_unregister(IMS_ConnHdlrPars pars) runs on test_CT +{ + f_ami_action_PJSIPUnregister(AMI_CLIENT, mp_volte_ims_outbound_registration); + AMI_CLIENT.receive(tr_AMI_Event_Registry(f_sip_SipAddr_to_str(pars.subscr.local_sip_record), + "sip:" & mp_ims_domain, + "Unregistered")); }
/* Test SIP registration of local clients */ private function f_TC_ims_registration(charstring id) runs on IMS_ConnHdlr { f_create_sip_expect(valueof(ts_SipUrl_from_Addr_Union(g_pars.subscr.registrar_sip_record.addr))); as_IMS_register(); + as_IMS_unregister(); setverdict(pass); } testcase TC_ims_registration() runs on test_CT { @@ -418,6 +423,12 @@
f_AMI_IMS_register(pars);
+ /* Stay registered for one second */ + f_sleep(1.0); + + /* Trigger unregistration: */ + f_AMI_IMS_unregister(pars); + vc_conn.done; f_shutdown(); } @@ -467,6 +478,8 @@ COORD.receive(COORD_CMD_CALL_ESTABLISHED) from vc_conn_sip; IMS_COORD.receive(COORD_CMD_CALL_ESTABLISHED) from vc_conn_ims;
+ /* TODO: "Action: DedicatedBearerStatus" */ + /* Call on-going */ f_sleep(1.0);
diff --git a/asterisk/IMS_ConnectionHandler.ttcn b/asterisk/IMS_ConnectionHandler.ttcn index f3e9839..9a37b05 100644 --- a/asterisk/IMS_ConnectionHandler.ttcn +++ b/asterisk/IMS_ConnectionHandler.ttcn @@ -80,6 +80,7 @@ SipUrl local_sip_url_ext, SipAddr local_sip_record, Contact local_contact, + P_Associated_Uri p_associated_uri, IMS_CallPars cp optional } type record of IMS_ConnHdlrSubscrPars IMS_ConnHdlrSubscrParsList; @@ -184,6 +185,7 @@ ts_UserInfo(imsi))), omit) })), + p_associated_uri := ts_P_Associated_Uri({}), cp := cp }
@@ -448,9 +450,8 @@ return sdp; }
-/* Peer is calling us, accept it: */ -altstep as_IMS_register(boolean exp_update_to_direct_rtp := true, - boolean fail_others := true) runs on IMS_ConnHdlr +/* Peer is issuing 1st register, accept it: */ +altstep as_IMS_register(boolean fail_others := true) runs on IMS_ConnHdlr { var template (present) PDU_SIP_Request exp_req := tr_SIP_REGISTER(g_pars.registrar_sip_req_uri, @@ -473,7 +474,6 @@ var template (value) To to_addr; var template (value) CommaParam_List digestCln ; var template (value) WwwAuthenticate wwwAuthenticate; - var template (value) P_Associated_Uri p_associated_uri := ts_P_Associated_Uri({}); var template (value) Security_server security_server; var template (value) Server server_name := ts_Server({c_sip_server_name}); var template (value) Require require := ts_Require({"sec-agree"}); @@ -561,7 +561,7 @@ wwwAuthenticate, sip_seq_nr, "REGISTER", - p_associated_uri := p_associated_uri, + p_associated_uri := g_pars.subscr.p_associated_uri, security_server := security_server, server := server_name, supported := supported, @@ -610,7 +610,7 @@ /* Validate P-Access-Network-Info: */ f_ims_validate_register_P_Access_Network_info(g_rx_sip_req, exp_present := true);
- p_associated_uri := ts_P_Associated_Uri({ + g_pars.subscr.p_associated_uri := valueof(ts_P_Associated_Uri({ ts_P_Assoc_uri_spec(ts_NameAddr(ts_SipUrl(ts_HostPort(g_pars.realm), ts_UserInfo(g_pars.subscr.msisdn), scheme := "sip"))), @@ -618,7 +618,7 @@ omit, scheme := "tel"))), ts_P_Assoc_uri_spec(g_rx_sip_req.msgHeader.toField.addressField.nameAddr) - }); + }));
/* Tx 200 OK */ to_addr.toParams := f_sip_param_set(to_addr.toParams, "tag", f_sip_rand_tag()); @@ -629,7 +629,7 @@ sip_seq_nr, "OK", via, - p_associated_uri := p_associated_uri, + p_associated_uri := g_pars.subscr.p_associated_uri, require := require, server := server_name, supported := supported, @@ -641,6 +641,89 @@
}
+/* Peer wants to unregister, accept it: */ +altstep as_IMS_unregister(boolean fail_others := true) runs on IMS_ConnHdlr +{ + var template (present) PDU_SIP_Request exp_req := + tr_SIP_REGISTER(g_pars.registrar_sip_req_uri, + ?, + tr_From(), + tr_To(), + tr_Via_from(?), + expires := tr_Expires(int2str(0)), + require := tr_Require(superset("sec-agree")), + security_client := tr_Security_client(superset(tr_Security_mechanism("ipsec-3gpp", + superset(tr_Param("alg","hmac-sha-1-96"))))), + supported := tr_Supported(superset("path", "sec-agree"))); + var charstring sip_expect_str := log2str(exp_req); + + [] SIP.receive(exp_req) -> value g_rx_sip_req { + var template (value) PDU_SIP_Response tx_resp; + var Via via; + var CallidString sip_call_id; + var Contact contact; + var template (value) From from_addr; + var template (value) To to_addr; + var template (value) CommaParam_List digestCln ; + var template (value) WwwAuthenticate wwwAuthenticate; + var template (value) Security_server security_server; + var template (value) Server server_name := ts_Server({c_sip_server_name}); + var template (value) Require require := ts_Require({"sec-agree"}); + var template (value) Supported supported := ts_Supported({"sec-agree"}); + var template (present) Authorization authorization; + var integer sip_seq_nr; + var charstring tx_sdp; + + sip_call_id := g_rx_sip_req.msgHeader.callId.callid; + via := g_rx_sip_req.msgHeader.via; + via.viaBody[0].viaParams := f_sip_param_set(via.viaBody[0].viaParams, "rport", "1234"); /* TODO: set remote src port of the REGISTER */ + from_addr := g_rx_sip_req.msgHeader.fromField; + to_addr := g_rx_sip_req.msgHeader.toField; + sip_seq_nr := g_rx_sip_req.msgHeader.cSeq.seqNumber; + + contact := g_rx_sip_req.msgHeader.contact; + f_ims_validate_register_contact(contact); + + /* Validate P-Access-Network-Info: */ + f_ims_validate_register_P_Access_Network_info(g_rx_sip_req, exp_present := true); + + /* Tx 100 Tyring */ + tx_resp := ts_SIP_Response_Trying(sip_call_id, + from_addr, + to_addr, + via, + sip_seq_nr, + "REGISTER", + allow := omit, + server := server_name, + userAgent := omit); + SIP.send(tx_resp); + + /* Change all Contact parameters to expires=0: */ + for (var integer i := 0; i < lengthof(contact.contactBody.contactAddresses); i := i + 1) { + contact.contactBody.contactAddresses[i].contactParams := valueof({ ts_Param("expires", "0") }); + } + /* Tx 200 OK */ + to_addr.toParams := f_sip_param_set(to_addr.toParams, "tag", f_sip_rand_tag()); + tx_resp := ts_SIP_Response(sip_call_id, + from_addr, + to_addr, + "REGISTER", 200, + sip_seq_nr, + "OK", + via, + contact := contact, + p_associated_uri := g_pars.subscr.p_associated_uri, + require := require, + server := server_name, + supported := supported, + userAgent := omit); + SIP.send(tx_resp); + } + [fail_others] as_SIP_fail_resp(sip_expect_str); + [fail_others] as_SIP_fail_req(sip_expect_str); +} + private function f_ConnHdlr_parse_initial_SIP_INVITE(PDU_SIP_Request rx_sip_req) runs on IMS_ConnHdlr { f_SDP_decodeMessage(rx_sip_req.messageBody, g_pars.subscr.cp.peer_sdp); diff --git a/library/SIP_Templates.ttcn b/library/SIP_Templates.ttcn index 9f45b9f..f251767 100644 --- a/library/SIP_Templates.ttcn +++ b/library/SIP_Templates.ttcn @@ -226,6 +226,10 @@ fieldName := EXPIRES_E, deltaSec := deltaSec } +template (present) Expires tr_Expires(template (present) DeltaSec deltaSec := ?) := { + fieldName := EXPIRES_E, + deltaSec := deltaSec +}
// [20.20] template (value) From ts_From(template (value) Addr_Union addressField, @@ -911,6 +915,7 @@ charstring reason, Via via, template (omit) Allow allow := omit, + template (omit) Contact contact := omit, template (omit) P_Associated_Uri p_associated_uri := omit, template (omit) Require require := omit, template (omit) Server server := omit, @@ -918,7 +923,7 @@ template (omit) UserAgent userAgent := omit, template (omit) charstring body := omit) := { statusLine := ts_SIP_StatusLine(status_code, reason), - msgHeader := ts_SIP_msgh_std(call_id, from_addr, to_addr, omit, method, seq_nr, + msgHeader := ts_SIP_msgh_std(call_id, from_addr, to_addr, contact, method, seq_nr, via, content_length := f_ContentLength(body), content_type := f_ContentTypeOrOmit(ts_CT_SDP, body),