Change in osmo-msc[master]: gsm_04_08_cc: Add global guard timer for MNCC

This is merely a historical archive of years 2008-2021, before the migration to mailman3.

A maintained and still updated list archive can be found at https://lists.osmocom.org/hyperkitty/list/gerrit-log@lists.osmocom.org/.

Harald Welte gerrit-no-reply at lists.osmocom.org
Wed Oct 24 09:04:15 UTC 2018


Harald Welte has submitted this change and it was merged. ( https://gerrit.osmocom.org/11307 )

Change subject: gsm_04_08_cc: Add global guard timer for MNCC
......................................................................

gsm_04_08_cc: Add global guard timer for MNCC

The external MNCC handler may hang indefinitely in cases where the remote
end of the MNCC ceases to work properly. Add a global guard timer to
make sure the call reaches ACTIVE state.

Change-Id: I7375d1e17cd746aac4eadfe1e587e82cf1630d3d
Related: OS#3599
---
M include/osmocom/msc/gsm_data.h
M include/osmocom/msc/transaction.h
M src/libmsc/gsm_04_08_cc.c
M src/libmsc/msc_vty.c
M src/libmsc/osmo_msc.c
M tests/msc_vlr/msc_vlr_test_call.err
6 files changed, 94 insertions(+), 0 deletions(-)

Approvals:
  Jenkins Builder: Verified
  Harald Welte: Looks good to me, approved



diff --git a/include/osmocom/msc/gsm_data.h b/include/osmocom/msc/gsm_data.h
index 54026f6..579697e 100644
--- a/include/osmocom/msc/gsm_data.h
+++ b/include/osmocom/msc/gsm_data.h
@@ -332,6 +332,9 @@
 	/* Periodic location update default value */
 	uint8_t t3212;
 
+	/* Global MNCC guard timer value */
+	int mncc_guard_timeout;
+
 	struct {
 		struct mgcp_client_conf conf;
 		struct mgcp_client *client;
diff --git a/include/osmocom/msc/transaction.h b/include/osmocom/msc/transaction.h
index 4ffb468..b7d7971 100644
--- a/include/osmocom/msc/transaction.h
+++ b/include/osmocom/msc/transaction.h
@@ -69,6 +69,7 @@
 			int Tcurrent;		/* current CC timer */
 			int T308_second;	/* used to send release again */
 			struct osmo_timer_list timer;
+			struct osmo_timer_list timer_guard;
 			struct gsm_mncc msg;	/* stores setup/disconnect/release message */
 		} cc;
 		struct {
diff --git a/src/libmsc/gsm_04_08_cc.c b/src/libmsc/gsm_04_08_cc.c
index 19e6cba..f9888d7 100644
--- a/src/libmsc/gsm_04_08_cc.c
+++ b/src/libmsc/gsm_04_08_cc.c
@@ -73,6 +73,43 @@
 
 static uint32_t new_callref = 0x80000001;
 
+static void gsm48_cc_guard_timeout(void *arg)
+{
+	struct gsm_trans *trans = arg;
+	DEBUGP(DCC, "(sub %s) guard timeout expired\n",
+	       vlr_subscr_msisdn_or_name(trans->vsub));
+	trans_free(trans);
+	return;
+}
+
+static void gsm48_stop_guard_timer(struct gsm_trans *trans)
+{
+	if (osmo_timer_pending(&trans->cc.timer_guard)) {
+		DEBUGP(DCC, "(sub %s) stopping pending guard timer\n",
+		       vlr_subscr_msisdn_or_name(trans->vsub));
+		osmo_timer_del(&trans->cc.timer_guard);
+	}
+}
+
+static void gsm48_start_guard_timer(struct gsm_trans *trans)
+{
+	/* NOTE: The purpose of this timer is to prevent the cc state machine
+	 * from hanging in cases where mncc, gsm48 or both become unresponsive
+	 * for some reason. The timer is started initially with the setup from
+	 * the gsm48 side and then re-started with every incoming mncc message.
+	 * Once the mncc state reaches its active state the timer is stopped.
+	 * So if the cc state machine does not show any activity for an
+	 * extended amount of time during call setup or teardown the guard
+	 * timer will time out and hard-clear the connection. */
+	if (osmo_timer_pending(&trans->cc.timer_guard))
+		gsm48_stop_guard_timer(trans);
+	DEBUGP(DCC, "(sub %s) starting guard timer with %d seconds\n",
+	       vlr_subscr_msisdn_or_name(trans->vsub),
+	       trans->net->mncc_guard_timeout);
+	osmo_timer_setup(&trans->cc.timer_guard, gsm48_cc_guard_timeout, trans);
+	osmo_timer_schedule(&trans->cc.timer_guard,
+			    trans->net->mncc_guard_timeout, 0);
+}
 
 /* Call Control */
 
@@ -149,6 +186,10 @@
 
 	count_statistics(trans, state);
 	trans->cc.state = state;
+
+	/* Stop the guard timer when a call reaches the active state */
+	if (state == GSM_CSTATE_ACTIVE)
+		gsm48_stop_guard_timer(trans);
 }
 
 static int gsm48_cc_tx_status(struct gsm_trans *trans, void *arg)
@@ -259,6 +300,8 @@
 	}
 	if (trans->cc.state != GSM_CSTATE_NULL)
 		new_cc_state(trans, GSM_CSTATE_NULL);
+
+	gsm48_stop_guard_timer(trans);
 }
 
 static int gsm48_cc_tx_setup(struct gsm_trans *trans, void *arg);
@@ -474,6 +517,8 @@
 	struct tlv_parsed tp;
 	struct gsm_mncc setup;
 
+	gsm48_start_guard_timer(trans);
+
 	memset(&setup, 0, sizeof(struct gsm_mncc));
 	setup.callref = trans->callref;
 
@@ -1970,6 +2015,8 @@
 		log_set_context(LOG_CTX_VLR_SUBSCR, trans->vsub);
 	}
 
+	gsm48_start_guard_timer(trans);
+
 	if (trans->conn)
 		conn = trans->conn;
 
diff --git a/src/libmsc/msc_vty.c b/src/libmsc/msc_vty.c
index fe6ae88..a16cec8 100644
--- a/src/libmsc/msc_vty.c
+++ b/src/libmsc/msc_vty.c
@@ -333,6 +333,16 @@
 	return CMD_SUCCESS;
 }
 
+DEFUN(cfg_msc_mncc_guard_timeout,
+      cfg_msc_mncc_guard_timeout_cmd,
+      "mncc-guard-timeout <0-255>",
+      "Set global guard timer for mncc interface activity\n"
+      "guard timer value (sec.)")
+{
+	gsmnet->mncc_guard_timeout = atoi(argv[0]);
+	return CMD_SUCCESS;
+}
+
 DEFUN(cfg_msc_assign_tmsi, cfg_msc_assign_tmsi_cmd,
       "assign-tmsi",
       "Assign TMSI during Location Updating.\n")
@@ -421,6 +431,8 @@
 static int config_write_msc(struct vty *vty)
 {
 	vty_out(vty, "msc%s", VTY_NEWLINE);
+	vty_out(vty, " mncc-guard-timeout %i%s",
+		gsmnet->mncc_guard_timeout, VTY_NEWLINE);
 	vty_out(vty, " %sassign-tmsi%s",
 		gsmnet->vlr->cfg.assign_tmsi? "" : "no ", VTY_NEWLINE);
 
@@ -1415,6 +1427,7 @@
 	install_element(CONFIG_NODE, &cfg_msc_cmd);
 	install_node(&msc_node, config_write_msc);
 	install_element(MSC_NODE, &cfg_msc_assign_tmsi_cmd);
+	install_element(MSC_NODE, &cfg_msc_mncc_guard_timeout_cmd);
 	install_element(MSC_NODE, &cfg_msc_no_assign_tmsi_cmd);
 	install_element(MSC_NODE, &cfg_msc_auth_tuple_max_reuse_count_cmd);
 	install_element(MSC_NODE, &cfg_msc_auth_tuple_reuse_on_error_cmd);
diff --git a/src/libmsc/osmo_msc.c b/src/libmsc/osmo_msc.c
index 3965e9b..c9ecb64 100644
--- a/src/libmsc/osmo_msc.c
+++ b/src/libmsc/osmo_msc.c
@@ -54,6 +54,8 @@
 	/* Use 30 min periodic update interval as sane default */
 	net->t3212 = 5;
 
+	net->mncc_guard_timeout = 180;
+
 	net->paging_response_timer = MSC_PAGING_RESPONSE_TIMER_DEFAULT;
 
 	INIT_LLIST_HEAD(&net->trans_list);
diff --git a/tests/msc_vlr/msc_vlr_test_call.err b/tests/msc_vlr/msc_vlr_test_call.err
index 19cb25d..936f61c 100644
--- a/tests/msc_vlr/msc_vlr_test_call.err
+++ b/tests/msc_vlr/msc_vlr_test_call.err
@@ -277,6 +277,7 @@
 DREF MSISDN:42342: MSC conn use + trans_cc == 3 (0x1a: dtap,cm_service,trans_cc)
 DMM MSISDN:42342: rx msg GSM48_MT_CC_SETUP: received_cm_service_request changes to false
 DREF MSISDN:42342: MSC conn use - cm_service == 2 (0x12: dtap,trans_cc)
+DCC (sub 42342) starting guard timer with 180 seconds
 DCC (ti 08 sub MSISDN:42342) new state NULL -> INITIATED
 DCC Subscriber MSISDN:42342 (42342) sends SETUP to 123
 DMNCC transmit message MNCC_SETUP_IND
@@ -287,6 +288,8 @@
 DREF MSISDN:42342: MSC conn use - dtap == 1 (0x10: trans_cc)
 - MNCC says that's fine
 DMNCC receive message MNCC_CALL_PROC_REQ
+DCC (sub 42342) stopping pending guard timer
+DCC (sub 42342) starting guard timer with 180 seconds
 DCC (ti 08 sub 42342) Received 'MNCC_CALL_PROC_REQ' from MNCC in state 1 (INITIATED)
 DCC (ti 08 sub MSISDN:42342) new state INITIATED -> MO_CALL_PROC
 DMSC msc_tx 2 bytes to MSISDN:42342 via RAN_UTRAN_IU
@@ -296,12 +299,16 @@
 - Total time passed: 1.000023 s
 - The other call leg got established (not shown here), MNCC tells us so
 DMNCC receive message MNCC_ALERT_REQ
+DCC (sub 42342) stopping pending guard timer
+DCC (sub 42342) starting guard timer with 180 seconds
 DCC (ti 08 sub 42342) Received 'MNCC_ALERT_REQ' from MNCC in state 3 (MO_CALL_PROC)
 DCC (ti 08 sub MSISDN:42342) new state MO_CALL_PROC -> CALL_DELIVERED
 DMSC msc_tx 2 bytes to MSISDN:42342 via RAN_UTRAN_IU
 - DTAP --RAN_UTRAN_IU--> MS: GSM48_MT_CC_ALERTING: 8301
 - DTAP matches expected message
 DMNCC receive message MNCC_SETUP_RSP
+DCC (sub 42342) stopping pending guard timer
+DCC (sub 42342) starting guard timer with 180 seconds
 DCC (ti 08 sub 42342) Received 'MNCC_SETUP_RSP' from MNCC in state 4 (CALL_DELIVERED)
 DCC starting timer T313 with 30 seconds
 DCC (ti 08 sub MSISDN:42342) new state CALL_DELIVERED -> CONNECT_IND
@@ -314,6 +321,7 @@
 DRLL Dispatching 04.08 message GSM48_MT_CC_CONNECT_ACK (0x3:0xf)
 DCC stopping pending timer T313
 DCC (ti 08 sub MSISDN:42342) new state CONNECT_IND -> ACTIVE
+DCC (sub 42342) stopping pending guard timer
 DMNCC transmit message MNCC_SETUP_COMPL_IND
 DCC Sending 'MNCC_SETUP_COMPL_IND' to MNCC.
   MSC --> MNCC: callref 0x80000001: MNCC_SETUP_COMPL_IND
@@ -334,6 +342,7 @@
 DMM Subscr_Conn(CM_SERVICE_REQ:901700000010650){SUBSCR_CONN_S_COMMUNICATING}: Received Event SUBSCR_CONN_E_COMMUNICATING
 DREF MSISDN:42342: MSC conn use - dtap == 1 (0x10: trans_cc)
 DMNCC receive message MNCC_REL_REQ
+DCC (sub 42342) starting guard timer with 180 seconds
 DCC (ti 08 sub 42342) Received 'MNCC_REL_REQ' from MNCC in state 12 (DISCONNECT_IND)
 DCC starting timer T308 with 10 seconds
 DCC (ti 08 sub MSISDN:42342) new state DISCONNECT_IND -> RELEASE_REQ
@@ -349,6 +358,7 @@
   MSC --> MNCC: callref 0x80000001: MNCC_REL_CNF
   MS <--Call Release-- MSC: subscr=MSISDN:42342 callref=0x0
 DCC (ti 08 sub MSISDN:42342) new state RELEASE_REQ -> NULL
+DCC (sub 42342) stopping pending guard timer
 DREF VLR subscr MSISDN:42342 usage decreases to: 2
 DREF MSISDN:42342: MSC conn use - trans_cc == 1 (0x2: dtap)
 DMM Subscr_Conn(CM_SERVICE_REQ:901700000010650){SUBSCR_CONN_S_COMMUNICATING}: Received Event SUBSCR_CONN_E_COMMUNICATING
@@ -697,8 +707,10 @@
 DMM Subscr_Conn(PAGING_RESP:901700000010650){SUBSCR_CONN_S_COMMUNICATING}: Received Event SUBSCR_CONN_E_COMMUNICATING
 DREF MSISDN:42342: MSC conn use - dtap == 1 (0x10: trans_cc)
 DMNCC receive message MNCC_SETUP_COMPL_REQ
+DCC (sub 42342) starting guard timer with 180 seconds
 DCC (ti 00 sub 42342) Received 'MNCC_SETUP_COMPL_REQ' from MNCC in state 8 (CONNECT_REQUEST)
 DCC (ti 00 sub MSISDN:42342) new state CONNECT_REQUEST -> ACTIVE
+DCC (sub 42342) stopping pending guard timer
 DMSC msc_tx 2 bytes to MSISDN:42342 via RAN_UTRAN_IU
 - DTAP --RAN_UTRAN_IU--> MS: GSM48_MT_CC_CONNECT_ACK: 030f
 - DTAP matches expected message
@@ -717,6 +729,7 @@
 DMM Subscr_Conn(PAGING_RESP:901700000010650){SUBSCR_CONN_S_COMMUNICATING}: Received Event SUBSCR_CONN_E_COMMUNICATING
 DREF MSISDN:42342: MSC conn use - dtap == 1 (0x10: trans_cc)
 DMNCC receive message MNCC_REL_REQ
+DCC (sub 42342) starting guard timer with 180 seconds
 DCC (ti 00 sub 42342) Received 'MNCC_REL_REQ' from MNCC in state 12 (DISCONNECT_IND)
 DCC starting timer T308 with 10 seconds
 DCC (ti 00 sub MSISDN:42342) new state DISCONNECT_IND -> RELEASE_REQ
@@ -732,6 +745,7 @@
   MSC --> MNCC: callref 0x423: MNCC_REL_CNF
   MS <--Call Release-- MSC: subscr=MSISDN:42342 callref=0x0
 DCC (ti 00 sub MSISDN:42342) new state RELEASE_REQ -> NULL
+DCC (sub 42342) stopping pending guard timer
 DREF VLR subscr MSISDN:42342 usage decreases to: 2
 DREF MSISDN:42342: MSC conn use - trans_cc == 1 (0x2: dtap)
 DMM Subscr_Conn(PAGING_RESP:901700000010650){SUBSCR_CONN_S_COMMUNICATING}: Received Event SUBSCR_CONN_E_COMMUNICATING
@@ -1078,6 +1092,7 @@
 DCC stopping pending timer T301
   MS <--Call Release-- MSC: subscr=MSISDN:42342 callref=0x423
 DMNCC receive message MNCC_REL_REQ
+DCC (sub 42342) starting guard timer with 180 seconds
 DCC (ti 00 sub 42342) Received 'MNCC_REL_REQ' from MNCC in state 7 (CALL_RECEIVED)
 DCC starting timer T308 with 10 seconds
 DCC (ti 00 sub MSISDN:42342) new state CALL_RECEIVED -> RELEASE_REQ
@@ -1089,6 +1104,7 @@
   MSC --> MNCC: callref 0x423: MNCC_REL_CNF
 DCC stopping pending timer T308
 DCC (ti 00 sub MSISDN:42342) new state RELEASE_REQ -> NULL
+DCC (sub 42342) stopping pending guard timer
 DREF VLR subscr MSISDN:42342 usage decreases to: 2
 DREF MSISDN:42342: MSC conn use - trans_cc == 1 (0x100: release)
 - Iu Release --RAN_UTRAN_IU--> MS
@@ -1389,6 +1405,7 @@
 DREF MSISDN:42342: MSC conn use + trans_cc == 3 (0x1a: dtap,cm_service,trans_cc)
 DMM MSISDN:42342: rx msg GSM48_MT_CC_SETUP: received_cm_service_request changes to false
 DREF MSISDN:42342: MSC conn use - cm_service == 2 (0x12: dtap,trans_cc)
+DCC (sub 42342) starting guard timer with 180 seconds
 DCC (ti 08 sub MSISDN:42342) new state NULL -> INITIATED
 DCC Subscriber MSISDN:42342 (42342) sends SETUP to 123
 DMNCC transmit message MNCC_SETUP_IND
@@ -1399,6 +1416,8 @@
 DREF MSISDN:42342: MSC conn use - dtap == 1 (0x10: trans_cc)
 - MNCC says that's fine
 DMNCC receive message MNCC_CALL_PROC_REQ
+DCC (sub 42342) stopping pending guard timer
+DCC (sub 42342) starting guard timer with 180 seconds
 DCC (ti 08 sub 42342) Received 'MNCC_CALL_PROC_REQ' from MNCC in state 1 (INITIATED)
 DCC (ti 08 sub MSISDN:42342) new state INITIATED -> MO_CALL_PROC
 DMSC msc_tx 2 bytes to MSISDN:42342 via RAN_UTRAN_IU
@@ -1407,6 +1426,8 @@
   MS <--Call Assignment-- MSC: subscr=MSISDN:42342 callref=0x80000002
 - But the other side's MSISDN could not be resolved, MNCC tells us to cancel
 DMNCC receive message MNCC_REL_REQ
+DCC (sub 42342) stopping pending guard timer
+DCC (sub 42342) starting guard timer with 180 seconds
 DCC (ti 08 sub 42342) Received 'MNCC_REL_REQ' from MNCC in state 3 (MO_CALL_PROC)
 DCC starting timer T308 with 10 seconds
 DCC (ti 08 sub MSISDN:42342) new state MO_CALL_PROC -> RELEASE_REQ
@@ -1427,6 +1448,7 @@
   MSC --> MNCC: callref 0x80000002: MNCC_REL_CNF
   MS <--Call Release-- MSC: subscr=MSISDN:42342 callref=0x0
 DCC (ti 08 sub MSISDN:42342) new state RELEASE_REQ -> NULL
+DCC (sub 42342) stopping pending guard timer
 DREF VLR subscr MSISDN:42342 usage decreases to: 2
 DREF MSISDN:42342: MSC conn use - trans_cc == 1 (0x2: dtap)
 DMM Subscr_Conn(CM_SERVICE_REQ:901700000010650){SUBSCR_CONN_S_COMMUNICATING}: Received Event SUBSCR_CONN_E_COMMUNICATING
@@ -1733,6 +1755,7 @@
 DREF MSISDN:42342: MSC conn use + trans_cc == 3 (0x1a: dtap,cm_service,trans_cc)
 DMM MSISDN:42342: rx msg GSM48_MT_CC_SETUP: received_cm_service_request changes to false
 DREF MSISDN:42342: MSC conn use - cm_service == 2 (0x12: dtap,trans_cc)
+DCC (sub 42342) starting guard timer with 180 seconds
 DCC (ti 08 sub MSISDN:42342) new state NULL -> INITIATED
 DCC Subscriber MSISDN:42342 (42342) sends SETUP to 123
 DMNCC transmit message MNCC_SETUP_IND
@@ -1743,6 +1766,8 @@
 DREF MSISDN:42342: MSC conn use - dtap == 1 (0x10: trans_cc)
 - MNCC says that's fine
 DMNCC receive message MNCC_CALL_PROC_REQ
+DCC (sub 42342) stopping pending guard timer
+DCC (sub 42342) starting guard timer with 180 seconds
 DCC (ti 08 sub 42342) Received 'MNCC_CALL_PROC_REQ' from MNCC in state 1 (INITIATED)
 DCC (ti 08 sub MSISDN:42342) new state INITIATED -> MO_CALL_PROC
 DMSC msc_tx 2 bytes to MSISDN:42342 via RAN_UTRAN_IU
@@ -1751,6 +1776,8 @@
   MS <--Call Assignment-- MSC: subscr=MSISDN:42342 callref=0x80000003
 - But the other side's MSISDN could not be resolved, MNCC tells us to cancel
 DMNCC receive message MNCC_REL_REQ
+DCC (sub 42342) stopping pending guard timer
+DCC (sub 42342) starting guard timer with 180 seconds
 DCC (ti 08 sub 42342) Received 'MNCC_REL_REQ' from MNCC in state 3 (MO_CALL_PROC)
 DCC starting timer T308 with 10 seconds
 DCC (ti 08 sub MSISDN:42342) new state MO_CALL_PROC -> RELEASE_REQ
@@ -1770,6 +1797,7 @@
 DCC Sending 'MNCC_REL_CNF' to MNCC.
   MSC --> MNCC: callref 0x80000003: MNCC_REL_CNF
 DCC (ti 08 sub MSISDN:42342) new state RELEASE_REQ -> NULL
+DCC (sub 42342) stopping pending guard timer
 DREF VLR subscr MSISDN:42342 usage decreases to: 2
 DREF MSISDN:42342: MSC conn use - trans_cc == 0 (0x0: )
 DMM Subscr_Conn(CM_SERVICE_REQ:901700000010650){SUBSCR_CONN_S_COMMUNICATING}: Received Event SUBSCR_CONN_E_UNUSED

-- 
To view, visit https://gerrit.osmocom.org/11307
To unsubscribe, or for help writing mail filters, visit https://gerrit.osmocom.org/settings

Gerrit-Project: osmo-msc
Gerrit-Branch: master
Gerrit-MessageType: merged
Gerrit-Change-Id: I7375d1e17cd746aac4eadfe1e587e82cf1630d3d
Gerrit-Change-Number: 11307
Gerrit-PatchSet: 5
Gerrit-Owner: dexter <pmaier at sysmocom.de>
Gerrit-Reviewer: Harald Welte <laforge at gnumonks.org>
Gerrit-Reviewer: Jenkins Builder (1000002)
Gerrit-Reviewer: Neels Hofmeyr <nhofmeyr at sysmocom.de>
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://lists.osmocom.org/pipermail/gerrit-log/attachments/20181024/1ba613c1/attachment.htm>


More information about the gerrit-log mailing list