blob: 2461962463114067c17b2369938af86b45e39cd7 [file] [log] [blame]
Harald Welte96a33b02018-02-04 10:36:22 +01001module SGSN_Tests {
2
Harald Welte34b5a952019-05-27 11:54:11 +02003/* Osmocom SGSN test suite in TTCN-3
4 * (C) 2018-2019 Harald Welte <laforge@gnumonks.org>
5 * (C) 2018-2019 sysmocom - s.f.m.c. GmbH
6 * All rights reserved.
7 *
8 * Released under the terms of GNU General Public License, Version 2 or
9 * (at your option) any later version.
10 *
11 * SPDX-License-Identifier: GPL-2.0-or-later
12 */
13
Harald Welte900d01a2019-08-13 13:27:51 +020014friend module SGSN_Tests_Iu;
Alexander Couzens8e1dfd02020-09-07 04:26:20 +020015friend module SGSN_Tests_NS;
Harald Welte900d01a2019-08-13 13:27:51 +020016
Harald Welte96a33b02018-02-04 10:36:22 +010017import from General_Types all;
18import from Osmocom_Types all;
Harald Welte557c9f82020-09-12 21:30:17 +020019import from GSM_Types all;
Harald Welte37692d82018-02-18 15:21:34 +010020import from Native_Functions all;
Harald Welte96a33b02018-02-04 10:36:22 +010021import from NS_Types all;
22import from NS_Emulation all;
23import from BSSGP_Types all;
24import from BSSGP_Emulation all;
Harald Welte5ac31492018-02-15 20:39:13 +010025import from Osmocom_Gb_Types all;
Harald Welte26fbb6e2019-04-14 17:32:46 +020026import from SCCPasp_Types all;
Harald Welte5ac31492018-02-15 20:39:13 +010027
28import from MobileL3_CommonIE_Types all;
29import from MobileL3_GMM_SM_Types all;
30import from MobileL3_Types all;
31import from L3_Templates all;
32import from L3_Common all;
33
34import from GSUP_Emulation all;
35import from GSUP_Types all;
36import from IPA_Emulation all;
37
Harald Welte26fbb6e2019-04-14 17:32:46 +020038import from RAN_Adapter all;
39import from RAN_Emulation all;
40import from RANAP_Templates all;
41import from RANAP_PDU_Descriptions all;
42import from RANAP_IEs all;
43
Harald Welteeded9ad2018-02-17 20:57:34 +010044import from GTP_Emulation all;
45import from GTP_Templates all;
46import from GTP_CodecPort all;
47import from GTPC_Types all;
48import from GTPU_Types all;
49
Harald Weltea2526a82018-02-18 19:03:36 +010050import from LLC_Types all;
51import from LLC_Templates all;
52
53import from SNDCP_Types all;
54
Harald Weltebd194722018-02-16 22:11:08 +010055import from TELNETasp_PortType all;
56import from Osmocom_VTY_Functions all;
57
Neels Hofmeyr8df7d152018-03-14 19:03:28 +010058import from GSM_RR_Types all;
59
Neels Hofmeyr0ecb2e32018-04-30 15:13:55 +020060import from MobileL3_MM_Types all;
61
Harald Welteeded9ad2018-02-17 20:57:34 +010062
Harald Welte5ac31492018-02-15 20:39:13 +010063modulepar {
64 /* IP/port on which we run our internal GSUP/HLR emulation */
65 charstring mp_hlr_ip := "127.0.0.1";
66 integer mp_hlr_port := 4222;
Pau Espin Pedrol7bac69f2021-05-04 15:53:06 +020067 charstring mp_ggsn_ip := "127.0.0.103";
Pau Espin Pedrolfcec9142019-08-28 17:33:46 +020068 integer mp_echo_interval := 5; /* in seconds. Only used in test enabling g_use_echo */
Pau Espin Pedrol8c74cbb2021-05-04 15:26:56 +020069 charstring mp_sgsn_gtp_ip := "127.0.0.10";
Alexander Couzens2c12b242018-07-31 00:30:11 +020070
Alexander Couzensf3c1b412018-08-24 00:42:51 +020071 NSConfigurations mp_nsconfig := {
72 {
Harald Welte5e514fa2018-07-05 00:01:45 +020073 nsei := 96,
74 role_sgsn := false,
Harald Welte90f19742020-11-06 19:34:40 +010075 handle_sns := false,
76 nsvc := {
77 {
78 provider := {
79 ip := {
80 address_family := AF_INET,
81 local_udp_port := 21010,
82 local_ip := "127.0.0.1",
83 remote_udp_port := 23000,
Harald Weltebe7afce2021-01-17 22:04:36 +010084 remote_ip := "127.0.0.1",
85 data_weight := 1,
86 signalling_weight := 1
Harald Welte90f19742020-11-06 19:34:40 +010087 }
88 },
89 nsvci := 97
90 }
91 }
Alexander Couzensf3c1b412018-08-24 00:42:51 +020092 },
93 {
Harald Welte5e514fa2018-07-05 00:01:45 +020094 nsei := 97,
95 role_sgsn := false,
Harald Welte90f19742020-11-06 19:34:40 +010096 handle_sns := false,
97 nsvc := {
98 {
99 provider := {
100 ip := {
101 address_family := AF_INET,
102 local_udp_port := 21011,
103 local_ip := "127.0.0.1",
104 remote_udp_port := 23000,
Harald Weltebe7afce2021-01-17 22:04:36 +0100105 remote_ip := "127.0.0.1",
106 data_weight := 1,
107 signalling_weight := 1
Harald Welte90f19742020-11-06 19:34:40 +0100108 }
109 },
110 nsvci := 98
111 }
112 }
Alexander Couzensf3c1b412018-08-24 00:42:51 +0200113 },
114 {
Harald Welte5e514fa2018-07-05 00:01:45 +0200115 nsei := 98,
116 role_sgsn := false,
Harald Welte90f19742020-11-06 19:34:40 +0100117 handle_sns := false,
118 nsvc := {
119 {
120 provider := {
121 ip := {
122 address_family := AF_INET,
123 local_udp_port := 21012,
124 local_ip := "127.0.0.1",
125 remote_udp_port := 23000,
Harald Weltebe7afce2021-01-17 22:04:36 +0100126 remote_ip := "127.0.0.1",
127 data_weight := 1,
128 signalling_weight := 1
Harald Welte90f19742020-11-06 19:34:40 +0100129 }
130 },
131 nsvci := 99
132 }
133 }
Alexander Couzensf3c1b412018-08-24 00:42:51 +0200134 }
Alexander Couzens2c12b242018-07-31 00:30:11 +0200135 };
Harald Welte26fbb6e2019-04-14 17:32:46 +0200136
137 RAN_Configurations mp_ranap_cfg := {
138 {
139 transport := RANAP_TRANSPORT_IuCS,
140 sccp_service_type := "mtp3_itu",
141 sctp_addr := { 23908, "127.0.0.1", 2905, "127.0.0.1" },
142 own_pc := 195,
143 own_ssn := 142,
144 peer_pc := 188, /* 0.23.4 */
145 peer_ssn := 142,
146 sio := '83'O,
147 rctx := 2
148 }
149 }
Harald Welte5ac31492018-02-15 20:39:13 +0100150};
151
Harald Welte5339b2e2020-10-04 22:52:56 +0200152const integer NUM_BVC_PER_NSE := 1;
Harald Welte5ac31492018-02-15 20:39:13 +0100153type record GbInstance {
154 NS_CT vc_NS,
155 BSSGP_CT vc_BSSGP,
Harald Welte5339b2e2020-10-04 22:52:56 +0200156 BSSGP_BVC_CT vc_BSSGP_BVC[NUM_BVC_PER_NSE],
Harald Welte5ac31492018-02-15 20:39:13 +0100157 BssgpConfig cfg
158};
Harald Welte96a33b02018-02-04 10:36:22 +0100159
Harald Welte2fa771f2019-05-02 20:13:53 +0200160const integer NUM_GB := 3;
161type record length(NUM_GB) of GbInstance GbInstances;
162type record length(NUM_GB) of NSConfiguration NSConfigurations;
163type record length(NUM_GB) of BssgpCellId BssgpCellIds;
Alexander Couzens51114d12018-07-31 18:41:56 +0200164
Harald Welte26fbb6e2019-04-14 17:32:46 +0200165const integer NUM_RNC := 1;
166type record of RAN_Configuration RAN_Configurations;
167
Harald Welte96a33b02018-02-04 10:36:22 +0100168type component test_CT {
Alexander Couzens51114d12018-07-31 18:41:56 +0200169 var GbInstances g_gb;
Harald Welte26fbb6e2019-04-14 17:32:46 +0200170 var RAN_Adapter g_ranap[NUM_RNC];
Alexander Couzens1552e792019-07-23 20:38:39 +0200171 var boolean g_ranap_enable := false;
Harald Welte96a33b02018-02-04 10:36:22 +0100172
Harald Welte5ac31492018-02-15 20:39:13 +0100173 var GSUP_Emulation_CT vc_GSUP;
174 var IPA_Emulation_CT vc_GSUP_IPA;
175 /* only to get events from IPA underneath GSUP */
176 port IPA_CTRL_PT GSUP_IPA_EVENT;
Harald Welte96a33b02018-02-04 10:36:22 +0100177
Harald Welte5339b2e2020-10-04 22:52:56 +0200178 /* only needed at start to get the per-BVC references */
179 port BSSGP_CT_PROC_PT PROC;
180
Philipp Maier7df55e02020-12-14 23:46:04 +0100181 /* used by RIM related test */
182 port BSSGP_PT RIM[NUM_GB];
Pau Espin Pedrol8c74cbb2021-05-04 15:26:56 +0200183 port GTPEM_PT GTPC;
Philipp Maier7df55e02020-12-14 23:46:04 +0100184
Harald Welteeded9ad2018-02-17 20:57:34 +0100185 var GTP_Emulation_CT vc_GTP;
186
Harald Weltebd194722018-02-16 22:11:08 +0100187 port TELNETasp_PT SGSNVTY;
188
Harald Welte96a33b02018-02-04 10:36:22 +0100189 var boolean g_initialized := false;
Pau Espin Pedroldc27e482018-07-10 14:02:49 +0200190 var boolean g_use_echo := false;
Harald Welte96a33b02018-02-04 10:36:22 +0100191};
192
Harald Welte26fbb6e2019-04-14 17:32:46 +0200193type component BSSGP_ConnHdlr extends BSSGP_Client_CT, GSUP_ConnHdlr, GTP_ConnHdlr, RAN_ConnHdlr {
Harald Welte5ac31492018-02-15 20:39:13 +0100194 var BSSGP_ConnHdlrPars g_pars;
Harald Welte62e29582018-02-16 21:17:11 +0100195 timer g_Tguard;
Alexander Couzenscdfb7512018-07-31 15:37:14 +0200196 var LLC_Entities llc;
Harald Welte5ac31492018-02-15 20:39:13 +0100197}
198
199type record SGSN_ConnHdlrNetworkPars {
200 boolean expect_ptmsi,
201 boolean expect_auth,
202 boolean expect_ciph
203};
204
205type record BSSGP_ConnHdlrPars {
206 /* IMEI of the simulated ME */
207 hexstring imei,
Alexander Couzens8f0fb002018-05-02 19:30:55 +0200208 /* IMSI of the simulated MS */
Harald Welte5ac31492018-02-15 20:39:13 +0100209 hexstring imsi,
210 /* MSISDN of the simulated MS (probably unused) */
211 hexstring msisdn,
212 /* P-TMSI allocated to the simulated MS */
213 OCT4 p_tmsi optional,
Harald Welte04683d02018-02-16 22:43:45 +0100214 OCT3 p_tmsi_sig optional,
Harald Welte5ac31492018-02-15 20:39:13 +0100215 /* TLLI of the simulated MS */
216 OCT4 tlli,
Harald Weltef70997d2018-02-17 10:11:19 +0100217 OCT4 tlli_old optional,
Harald Welte5ac31492018-02-15 20:39:13 +0100218 RoutingAreaIdentificationV ra optional,
Alexander Couzens51114d12018-07-31 18:41:56 +0200219 BssgpCellIds bssgp_cell_id,
Alexander Couzens4444b5a2019-08-13 13:25:32 +0200220 /* Tracks the RNC state. If true next L3 message will be sent with InitiualUe */
221 boolean rnc_send_initial_ue,
Harald Welte5ac31492018-02-15 20:39:13 +0100222 AuthVector vec optional,
Harald Welte62e29582018-02-16 21:17:11 +0100223 SGSN_ConnHdlrNetworkPars net,
Harald Welte26fbb6e2019-04-14 17:32:46 +0200224 float t_guard,
225 /* only in IuPS / RANAP case */
Alexander Couzens1552e792019-07-23 20:38:39 +0200226 SCCP_PAR_Address sccp_addr_local optional,
227 SCCP_PAR_Address sccp_addr_peer optional
Harald Welte5ac31492018-02-15 20:39:13 +0100228};
229
Pau Espin Pedrol8c74cbb2021-05-04 15:26:56 +0200230/* Passed in RAN-INFO message from emulated neighbor using RIM */
231const octetstring si1_default := '198fb100000000000000000000000000007900002b'O;
232const octetstring si3_default := '1b753000f110236ec9033c2747407900003c0b2b2b'O;
233const octetstring si13_default := '009000185a6fc9e08410ab2b2b2b2b2b2b2b2b2b2b'O;
234const octetstring si_default := si1_default & si3_default & si13_default;
235
Alexander Couzens89508702018-07-31 04:16:10 +0200236private function f_cellid_to_RAI(in BssgpCellId cell_id) return RoutingAreaIdentificationV {
Alexander Couzensc7dddbd2019-04-11 19:18:35 +0200237 /* mcc_mnc is encoded as of 24.008 10.5.5.15 */
Alexander Couzens89508702018-07-31 04:16:10 +0200238 var BcdMccMnc mcc_mnc := cell_id.ra_id.lai.mcc_mnc;
239
240 var RoutingAreaIdentificationV ret := {
241 mccDigit1 := mcc_mnc[0],
242 mccDigit2 := mcc_mnc[1],
243 mccDigit3 := mcc_mnc[2],
Alexander Couzensc7dddbd2019-04-11 19:18:35 +0200244 mncDigit3 := mcc_mnc[3],
245 mncDigit1 := mcc_mnc[4],
246 mncDigit2 := mcc_mnc[5],
Pau Espin Pedroldeaaa902021-02-12 18:41:04 +0100247 lac := int2oct(cell_id.ra_id.lai.lac, 2),
248 rac := int2oct(cell_id.ra_id.rac, 1)
Alexander Couzens89508702018-07-31 04:16:10 +0200249 }
250 return ret;
251};
252
Alexander Couzens51114d12018-07-31 18:41:56 +0200253private function f_init_gb(inout GbInstance gb, charstring id, integer offset) runs on test_CT {
254 gb.vc_NS := NS_CT.create(id & "-NS" & int2str(offset));
255 gb.vc_BSSGP := BSSGP_CT.create(id & "-BSSGP" & int2str(offset));
Harald Welte5ac31492018-02-15 20:39:13 +0100256 /* connect lower end of BSSGP emulation with NS upper port */
257 connect(gb.vc_BSSGP:BSCP, gb.vc_NS:NS_SP);
Harald Welte5ac31492018-02-15 20:39:13 +0100258
Alexander Couzensf3c1b412018-08-24 00:42:51 +0200259 gb.vc_NS.start(NSStart(mp_nsconfig[offset]));
Harald Welte5339b2e2020-10-04 22:52:56 +0200260 gb.vc_BSSGP.start(BssgpStart(gb.cfg, testcasename()));
261 /* resolve the per-BVC component references */
262 for (var integer i := 0; i < lengthof(gb.cfg.bvc); i := i+1) {
263 connect(self:PROC, gb.vc_BSSGP:PROC);
264 gb.vc_BSSGP_BVC[i] := f_bssgp_get_bvci_ct(gb.cfg.bvc[i].bvci, PROC);
265 disconnect(self:PROC, gb.vc_BSSGP:PROC);
266 }
Philipp Maier7df55e02020-12-14 23:46:04 +0100267 /* connect RIM related port */
268 connect(gb.vc_BSSGP:RIM, self:RIM[offset]);
Harald Welte5ac31492018-02-15 20:39:13 +0100269}
270
271private function f_init_gsup(charstring id) runs on test_CT {
272 id := id & "-GSUP";
273 var GsupOps ops := {
274 create_cb := refers(GSUP_Emulation.ExpectedCreateCallback)
275 };
276
277 vc_GSUP_IPA := IPA_Emulation_CT.create(id & "-IPA");
278 vc_GSUP := GSUP_Emulation_CT.create(id);
279
280 map(vc_GSUP_IPA:IPA_PORT, system:IPA_CODEC_PT);
281 connect(vc_GSUP:GSUP, vc_GSUP_IPA:IPA_GSUP_PORT);
282 /* we use this hack to get events like ASP_IPA_EVENT_UP */
283 connect(vc_GSUP_IPA:IPA_CTRL_PORT, self:GSUP_IPA_EVENT);
284
285 vc_GSUP.start(GSUP_Emulation.main(ops, id));
286 vc_GSUP_IPA.start(IPA_Emulation.main_server(mp_hlr_ip, mp_hlr_port));
287
288 /* wait for incoming connection to GSUP port before proceeding */
289 timer T := 10.0;
290 T.start;
291 alt {
Vadim Yanitskiy61564be2020-05-18 20:44:14 +0700292 [] GSUP_IPA_EVENT.receive(tr_ASP_IPA_EV(ASP_IPA_EVENT_UP)) { }
Harald Welte5ac31492018-02-15 20:39:13 +0100293 [] T.timeout {
294 setverdict(fail, "No connection to GSUP Port");
Daniel Willmannafce8662018-07-06 23:11:32 +0200295 mtc.stop;
Harald Welte5ac31492018-02-15 20:39:13 +0100296 }
297 }
298}
299
Harald Welteeded9ad2018-02-17 20:57:34 +0100300private function f_init_gtp(charstring id) runs on test_CT {
301 id := id & "-GTP";
302
303 var GtpEmulationCfg gtp_cfg := {
304 gtpc_bind_ip := mp_ggsn_ip,
305 gtpc_bind_port := GTP1C_PORT,
306 gtpu_bind_ip := mp_ggsn_ip,
307 gtpu_bind_port := GTP1U_PORT,
308 sgsn_role := false
309 };
310
311 vc_GTP := GTP_Emulation_CT.create(id);
312 vc_GTP.start(GTP_Emulation.main(gtp_cfg));
313}
314
Alexander Couzens8e1dfd02020-09-07 04:26:20 +0200315friend function f_init_vty() runs on test_CT {
Harald Weltebd194722018-02-16 22:11:08 +0100316 map(self:SGSNVTY, system:SGSNVTY);
317 f_vty_set_prompts(SGSNVTY);
318 f_vty_transceive(SGSNVTY, "enable");
Alexander Couzens1d1744f2018-08-07 11:56:14 +0200319 f_vty_transceive(SGSNVTY, "reset sgsn state");
Harald Weltebd194722018-02-16 22:11:08 +0100320 f_vty_config(SGSNVTY, "sgsn", "auth-policy remote");
321}
322
Pau Espin Pedroldc27e482018-07-10 14:02:49 +0200323private function f_vty_enable_echo_interval(boolean enable) runs on test_CT {
324 if (enable) {
Pau Espin Pedrolfcec9142019-08-28 17:33:46 +0200325 f_vty_config(SGSNVTY, "sgsn", "ggsn 0 echo-interval " & int2str(mp_echo_interval));
Pau Espin Pedroldc27e482018-07-10 14:02:49 +0200326 } else {
327 f_vty_config(SGSNVTY, "sgsn", "ggsn 0 no echo-interval");
328 }
329}
330
Harald Weltebd194722018-02-16 22:11:08 +0100331
Alexander Couzensc7dddbd2019-04-11 19:18:35 +0200332/* mcc_mnc is 24.008 10.5.5.15 encoded. 262 42 */
333function f_init(BcdMccMnc mcc_mnc := '262F42'H) runs on test_CT {
Harald Welte26fbb6e2019-04-14 17:32:46 +0200334 var integer i;
335
Harald Welte96a33b02018-02-04 10:36:22 +0100336 if (g_initialized == true) {
337 return;
338 }
339 g_initialized := true;
Harald Welte5ac31492018-02-15 20:39:13 +0100340 g_gb[0].cfg := {
341 nsei := 96,
Oliver Smithaac9b9c2019-09-02 08:36:36 +0200342 sgsn_role := false,
Harald Welte5339b2e2020-10-04 22:52:56 +0200343 bvc := {
344 {
345 bvci := 196,
346 cell_id := {
347 ra_id := {
348 lai := {
349 mcc_mnc := mcc_mnc,
350 lac := 13135
351 },
352 rac := 0
353 },
354 cell_id := 20960
355 },
Harald Welte4d112c92020-11-12 19:48:31 +0100356 depth := BSSGP_DECODE_DEPTH_L3,
357 create_cb := refers(BSSGP_Emulation.DefaultCreateCallback)
Harald Welte5339b2e2020-10-04 22:52:56 +0200358 }
359 }
Harald Welte5ac31492018-02-15 20:39:13 +0100360 };
Alexander Couzens5e2ba752018-07-03 15:13:07 +0200361 g_gb[1].cfg := {
362 nsei := 97,
Oliver Smithaac9b9c2019-09-02 08:36:36 +0200363 sgsn_role := false,
Harald Welte5339b2e2020-10-04 22:52:56 +0200364 bvc := {
365 {
366 bvci := 210,
367 cell_id := {
368 ra_id := {
369 lai := {
370 mcc_mnc := mcc_mnc,
371 lac := 13200
372 },
373 rac := 0
374 },
375 cell_id := 20961
376 },
Harald Welte4d112c92020-11-12 19:48:31 +0100377 depth := BSSGP_DECODE_DEPTH_L3,
378 create_cb := refers(BSSGP_Emulation.DefaultCreateCallback)
Harald Welte5339b2e2020-10-04 22:52:56 +0200379 }
380 }
Alexander Couzens5e2ba752018-07-03 15:13:07 +0200381 };
Pau Espin Pedrol7c052162021-02-12 17:43:35 +0100382 g_gb[2].cfg := { /* [2] configured to have same RAC as [1] */
Alexander Couzens5e2ba752018-07-03 15:13:07 +0200383 nsei := 98,
Oliver Smithaac9b9c2019-09-02 08:36:36 +0200384 sgsn_role := false,
Harald Welte5339b2e2020-10-04 22:52:56 +0200385 bvc := {
386 {
387 bvci := 220,
388 cell_id := {
389 ra_id := {
390 lai := {
391 mcc_mnc := mcc_mnc,
Pau Espin Pedrol7c052162021-02-12 17:43:35 +0100392 lac := 13200
Harald Welte5339b2e2020-10-04 22:52:56 +0200393 },
394 rac := 0
395 },
396 cell_id := 20962
397 },
Harald Welte4d112c92020-11-12 19:48:31 +0100398 depth := BSSGP_DECODE_DEPTH_L3,
399 create_cb := refers(BSSGP_Emulation.DefaultCreateCallback)
Harald Welte5339b2e2020-10-04 22:52:56 +0200400 }
401 }
Alexander Couzens5e2ba752018-07-03 15:13:07 +0200402 };
Harald Welte96a33b02018-02-04 10:36:22 +0100403
Alexander Couzens1d1744f2018-08-07 11:56:14 +0200404 f_init_vty();
Alexander Couzens51114d12018-07-31 18:41:56 +0200405 f_init_gb(g_gb[0], "SGSN_Test-Gb0", 0);
406 f_init_gb(g_gb[1], "SGSN_Test-Gb1", 1);
407 f_init_gb(g_gb[2], "SGSN_Test-Gb2", 2);
Harald Welte26fbb6e2019-04-14 17:32:46 +0200408
Alexander Couzens1552e792019-07-23 20:38:39 +0200409 if (g_ranap_enable) {
410 for (i := 0; i < NUM_RNC; i := i+1) {
411 f_ran_adapter_init(g_ranap[i], mp_ranap_cfg[i], "SGSN_Test_" & int2str(i), RNC_RanOps);
412 f_ran_adapter_start(g_ranap[i]);
413 }
Harald Welte26fbb6e2019-04-14 17:32:46 +0200414 }
Harald Welte5ac31492018-02-15 20:39:13 +0100415 f_init_gsup("SGSN_Test");
Harald Welteeded9ad2018-02-17 20:57:34 +0100416 f_init_gtp("SGSN_Test");
Pau Espin Pedroldc27e482018-07-10 14:02:49 +0200417 f_vty_enable_echo_interval(g_use_echo);
Harald Welte5ac31492018-02-15 20:39:13 +0100418}
Harald Welte96a33b02018-02-04 10:36:22 +0100419
Pau Espin Pedrolce0d6152019-08-27 19:07:27 +0200420function f_cleanup() runs on test_CT {
421 var integer i;
Alexander Couzens1552e792019-07-23 20:38:39 +0200422 if (g_ranap_enable) {
423 for (i := 0; i < NUM_RNC; i := i+1) {
424 f_ran_adapter_cleanup(g_ranap[i]);
425 }
Pau Espin Pedrolce0d6152019-08-27 19:07:27 +0200426 }
427 self.stop;
428}
429
Harald Welte26fbb6e2019-04-14 17:32:46 +0200430private function RncUnitdataCallback(RANAP_PDU ranap)
431runs on RAN_Emulation_CT return template RANAP_PDU {
432 var template RANAP_PDU resp := omit;
433
434 log ("RANAP_RncUnitDataCallback");
435 /* answer all RESET with RESET ACK */
436 if (match(ranap, tr_RANAP_Reset)) {
437 log("RANAP_RncUnitdataCallback: Responding to RESET with RESET-ACK");
438 var CN_DomainIndicator dom;
439 dom := ranap.initiatingMessage.value_.Reset.protocolIEs[1].value_.cN_DomainIndicator;
440 resp := ts_RANAP_ResetAck(dom);
441 }
442 return resp;
443}
444
445const RanOps RNC_RanOps := {
446 ranap_create_cb := refers(RAN_Emulation.RanapExpectedCreateCallback),
447 ranap_unitdata_cb := refers(RncUnitdataCallback),
448 ps_domain := true,
449 decode_dtap := true,
450 role_ms := true,
451 protocol := RAN_PROTOCOL_RANAP,
452 transport := RANAP_TRANSPORT_IuCS,
453 use_osmux := false,
454 sccp_addr_local := omit,
455 sccp_addr_peer := omit
456};
457
Harald Welte5ac31492018-02-15 20:39:13 +0100458type function void_fn(charstring id) runs on BSSGP_ConnHdlr;
459
460/* helper function to create, connect and start a BSSGP_ConnHdlr component */
Alexander Couzens51114d12018-07-31 18:41:56 +0200461function f_start_handler(void_fn fn, charstring id, GbInstances gb, integer imsi_suffix,
Harald Welte62e29582018-02-16 21:17:11 +0100462 float t_guard := 30.0)
Harald Welte5ac31492018-02-15 20:39:13 +0100463runs on test_CT return BSSGP_ConnHdlr {
464 var BSSGP_ConnHdlr vc_conn;
465 var SGSN_ConnHdlrNetworkPars net_pars := {
466 expect_ptmsi := true,
467 expect_auth := true,
468 expect_ciph := false
469 };
470 var BSSGP_ConnHdlrPars pars := {
471 imei := f_gen_imei(imsi_suffix),
472 imsi := f_gen_imsi(imsi_suffix),
473 msisdn := f_gen_msisdn(imsi_suffix),
474 p_tmsi := omit,
Harald Welte04683d02018-02-16 22:43:45 +0100475 p_tmsi_sig := omit,
Harald Welte14a0f942018-02-16 20:42:23 +0100476 tlli := f_gprs_tlli_random(),
Harald Weltef70997d2018-02-17 10:11:19 +0100477 tlli_old := omit,
Harald Welte5ac31492018-02-15 20:39:13 +0100478 ra := omit,
Harald Welte5339b2e2020-10-04 22:52:56 +0200479 bssgp_cell_id := {
480 gb[0].cfg.bvc[0].cell_id,
481 gb[1].cfg.bvc[0].cell_id,
482 gb[2].cfg.bvc[0].cell_id
483 },
Alexander Couzens4444b5a2019-08-13 13:25:32 +0200484 rnc_send_initial_ue := true,
Harald Welte5ac31492018-02-15 20:39:13 +0100485 vec := omit,
Harald Welte62e29582018-02-16 21:17:11 +0100486 net := net_pars,
Harald Welte26fbb6e2019-04-14 17:32:46 +0200487 t_guard := t_guard,
Alexander Couzens1552e792019-07-23 20:38:39 +0200488 sccp_addr_local := omit,
489 sccp_addr_peer := omit
Harald Welte5ac31492018-02-15 20:39:13 +0100490 };
491
Alexander Couzens1552e792019-07-23 20:38:39 +0200492 if (g_ranap_enable) {
493 pars.sccp_addr_local := g_ranap[0].sccp_addr_own;
494 pars.sccp_addr_peer := g_ranap[0].sccp_addr_peer;
495 }
496
Harald Welte5ac31492018-02-15 20:39:13 +0100497 vc_conn := BSSGP_ConnHdlr.create(id);
Harald Welte5339b2e2020-10-04 22:52:56 +0200498
499 connect(vc_conn:BSSGP[0], gb[0].vc_BSSGP_BVC[0]:BSSGP_SP);
500 connect(vc_conn:BSSGP_SIG[0], gb[0].vc_BSSGP_BVC[0]:BSSGP_SP_SIG);
501 connect(vc_conn:BSSGP_PROC[0], gb[0].vc_BSSGP_BVC[0]:BSSGP_PROC);
Harald Welte9b461a92020-12-10 23:41:14 +0100502 connect(vc_conn:BSSGP_GLOBAL[0], gb[0].vc_BSSGP:GLOBAL);
Harald Welte5339b2e2020-10-04 22:52:56 +0200503
504 connect(vc_conn:BSSGP[1], gb[1].vc_BSSGP_BVC[0]:BSSGP_SP);
505 connect(vc_conn:BSSGP_SIG[1], gb[1].vc_BSSGP_BVC[0]:BSSGP_SP_SIG);
506 connect(vc_conn:BSSGP_PROC[1], gb[1].vc_BSSGP_BVC[0]:BSSGP_PROC);
Harald Welte9b461a92020-12-10 23:41:14 +0100507 connect(vc_conn:BSSGP_GLOBAL[1], gb[1].vc_BSSGP:GLOBAL);
Harald Welte5339b2e2020-10-04 22:52:56 +0200508
509 connect(vc_conn:BSSGP[2], gb[2].vc_BSSGP_BVC[0]:BSSGP_SP);
510 connect(vc_conn:BSSGP_SIG[2], gb[2].vc_BSSGP_BVC[0]:BSSGP_SP_SIG);
511 connect(vc_conn:BSSGP_PROC[2], gb[2].vc_BSSGP_BVC[0]:BSSGP_PROC);
Harald Welte9b461a92020-12-10 23:41:14 +0100512 connect(vc_conn:BSSGP_GLOBAL[2], gb[2].vc_BSSGP:GLOBAL);
Harald Welte5ac31492018-02-15 20:39:13 +0100513
Harald Welte26fbb6e2019-04-14 17:32:46 +0200514 /* FIXME: support multiple RNCs */
Alexander Couzens1552e792019-07-23 20:38:39 +0200515 if (g_ranap_enable) {
516 connect(vc_conn:BSSAP, g_ranap[0].vc_RAN:CLIENT);
517 connect(vc_conn:BSSAP_PROC, g_ranap[0].vc_RAN:PROC);
518 }
Harald Welte26fbb6e2019-04-14 17:32:46 +0200519
Harald Welte5ac31492018-02-15 20:39:13 +0100520 connect(vc_conn:GSUP, vc_GSUP:GSUP_CLIENT);
521 connect(vc_conn:GSUP_PROC, vc_GSUP:GSUP_PROC);
522
Harald Welteeded9ad2018-02-17 20:57:34 +0100523 connect(vc_conn:GTP, vc_GTP:CLIENT);
524 connect(vc_conn:GTP_PROC, vc_GTP:CLIENT_PROC);
525
Harald Welte5ac31492018-02-15 20:39:13 +0100526 vc_conn.start(f_handler_init(fn, id, pars));
527 return vc_conn;
528}
529
Harald Welte62e29582018-02-16 21:17:11 +0100530private altstep as_Tguard() runs on BSSGP_ConnHdlr {
531 [] g_Tguard.timeout {
532 setverdict(fail, "Tguard timeout");
Daniel Willmannafce8662018-07-06 23:11:32 +0200533 mtc.stop;
Harald Welte62e29582018-02-16 21:17:11 +0100534 }
535}
536
Harald Welte5ac31492018-02-15 20:39:13 +0100537/* first function called in every ConnHdlr */
538private function f_handler_init(void_fn fn, charstring id, BSSGP_ConnHdlrPars pars)
539runs on BSSGP_ConnHdlr {
540 /* do some common stuff like setting up g_pars */
541 g_pars := pars;
542
Alexander Couzenscdfb7512018-07-31 15:37:14 +0200543 llc := f_llc_create(false);
544
Harald Welte5ac31492018-02-15 20:39:13 +0100545 /* register with BSSGP core */
Harald Welte5339b2e2020-10-04 22:52:56 +0200546 f_bssgp_client_register(g_pars.imsi, g_pars.tlli);
Harald Welte5ac31492018-02-15 20:39:13 +0100547 /* tell GSUP dispatcher to send this IMSI to us */
548 f_create_gsup_expect(hex2str(g_pars.imsi));
Harald Welteeded9ad2018-02-17 20:57:34 +0100549 /* tell GTP dispatcher to send this IMSI to us */
550 f_gtp_register_imsi(g_pars.imsi);
Harald Welte5ac31492018-02-15 20:39:13 +0100551
Harald Welte62e29582018-02-16 21:17:11 +0100552 g_Tguard.start(pars.t_guard);
553 activate(as_Tguard());
554
Harald Welte5ac31492018-02-15 20:39:13 +0100555 /* call the user-supplied test case function */
556 fn.apply(id);
557 f_bssgp_client_unregister(g_pars.imsi);
Harald Welte96a33b02018-02-04 10:36:22 +0100558}
559
560/* TODO:
Harald Welte96a33b02018-02-04 10:36:22 +0100561 * Detach without Attach
562 * SM procedures without attach / RAU
563 * ATTACH / RAU
564 ** with / without authentication
565 ** with / without P-TMSI allocation
Harald Welte96a33b02018-02-04 10:36:22 +0100566 * re-transmissions of LLC frames
567 * PDP Context activation
568 ** with different GGSN config in SGSN VTY
569 ** with different PDP context type (v4/v6/v46)
570 ** timeout from GGSN
Harald Welte6f203162018-02-18 22:04:55 +0100571 ** multiple / secondary PDP context
Harald Welte96a33b02018-02-04 10:36:22 +0100572 */
573
574testcase TC_wait_ns_up() runs on test_CT {
575 f_init();
576 f_sleep(20.0);
Pau Espin Pedrolce0d6152019-08-27 19:07:27 +0200577 f_cleanup();
Harald Welte96a33b02018-02-04 10:36:22 +0100578}
579
Alexander Couzensb1ce1182019-09-15 22:43:40 +0200580friend function is_gb(integer ran_index) return boolean {
581 return ran_index < NUM_GB;
Alexander Couzens4444b5a2019-08-13 13:25:32 +0200582}
Alexander Couzensb1ce1182019-09-15 22:43:40 +0200583friend function is_iu(integer ran_index) return boolean {
584 return ran_index >= NUM_GB;
Alexander Couzens4444b5a2019-08-13 13:25:32 +0200585}
586
Alexander Couzens0507ec32019-09-15 22:41:22 +0200587function f_send_llc(template (value) PDU_LLC llc_pdu, integer ran_index := 0) runs on BSSGP_ConnHdlr {
Harald Weltea05b8072019-04-23 22:35:05 +0200588 var octetstring llc_enc := enc_PDU_LLC(valueof(llc_pdu));
Alexander Couzens0507ec32019-09-15 22:41:22 +0200589 BSSGP[ran_index].send(ts_BSSGP_UL_UD(g_pars.tlli, g_pars.bssgp_cell_id[ran_index], llc_enc));
Harald Weltea05b8072019-04-23 22:35:05 +0200590}
591
Alexander Couzens0507ec32019-09-15 22:41:22 +0200592private function f_send_l3_gmm_llc(template (value) PDU_L3_MS_SGSN l3_mo, integer ran_index := 0) runs on BSSGP_ConnHdlr {
Alexander Couzenscdfb7512018-07-31 15:37:14 +0200593 var octetstring l3_enc := enc_PDU_L3_MS_SGSN(valueof(l3_mo));
594 var BIT4 sapi := f_llc_sapi_by_l3_mo(valueof(l3_mo));
595 var integer n_u := f_llc_get_n_u_tx(llc[bit2int(sapi)]);
Alexander Couzens0507ec32019-09-15 22:41:22 +0200596 f_send_llc(ts_LLC_UI(l3_enc, sapi, '0'B, n_u), ran_index);
Alexander Couzenscdfb7512018-07-31 15:37:14 +0200597}
598
Alexander Couzens4444b5a2019-08-13 13:25:32 +0200599/* trigger sending of a RANAP InitialUE and wait for SCCP connection confirmation */
600function f_send_l3_initial_ue(template (value) PDU_L3_MS_SGSN l3_mo) runs on BSSGP_ConnHdlr {
601 log("Sending InitialUE: ", l3_mo);
602 var octetstring l3_enc := enc_PDU_L3_MS_SGSN(valueof(l3_mo));
603 var RANAP_PDU ranap;
604 var LAI lai := {
605 pLMNidentity := '62F224'O,
606 lAC := '1234'O,
607 iE_Extensions := omit
608 };
609 var SAI sai := {
610 pLMNidentity := lai.pLMNidentity,
611 lAC := lai.lAC,
612 sAC := '0000'O, /* FIXME */
613 iE_Extensions := omit
614 };
615 var IuSignallingConnectionIdentifier sigc_id := int2bit(23, 24); /* FIXME */
616 var GlobalRNC_ID grnc_id := {
617 pLMNidentity := lai.pLMNidentity,
618 rNC_ID := 2342 /* FIXME */
619 };
620
621 ranap := valueof(ts_RANAP_initialUE_CS(lai, sai, l3_enc, sigc_id, grnc_id));
622 BSSAP.send(ts_RANAP_Conn_Req(g_pars.sccp_addr_peer, g_pars.sccp_addr_local, ranap));
623 alt {
624 [] BSSAP.receive(RAN_Conn_Prim:MSC_CONN_PRIM_CONF_IND) {}
625 [] BSSAP.receive(RAN_Conn_Prim:MSC_CONN_PRIM_DISC_IND) {
626 setverdict(fail, "DISC.ind from SCCP");
627 mtc.stop;
628 }
629 }
630}
631
632/* send a L3 (GMM/SM) message over whatever is the appropriate lower-layer bearer */
Alexander Couzens0507ec32019-09-15 22:41:22 +0200633function f_send_l3(template (value) PDU_L3_MS_SGSN l3_mo, integer ran_index := 0) runs on BSSGP_ConnHdlr {
634 if (is_iu(ran_index)) {
Alexander Couzens4444b5a2019-08-13 13:25:32 +0200635 if (g_pars.rnc_send_initial_ue) {
636 g_pars.rnc_send_initial_ue := false;
637 f_send_l3_initial_ue(l3_mo);
638 } else {
639 BSSAP.send(ts_PDU_DTAP_PS_MO(l3_mo));
640 }
641 } else {
Alexander Couzens0507ec32019-09-15 22:41:22 +0200642 f_send_l3_gmm_llc(l3_mo, ran_index);
Alexander Couzens4444b5a2019-08-13 13:25:32 +0200643 }
644}
645
Alexander Couzensb1ce1182019-09-15 22:43:40 +0200646altstep as_mm_identity(integer ran_index := 0) runs on BSSGP_ConnHdlr {
Vadim Yanitskiy98bb2d52020-03-28 00:57:21 +0700647 var MobileIdentityLV mi;
Alexander Couzensb1ce1182019-09-15 22:43:40 +0200648 [is_gb(ran_index)] BSSGP[ran_index].receive(tr_GMM_ID_REQ('001'B)) {
Harald Welte5ac31492018-02-15 20:39:13 +0100649 mi := valueof(ts_MI_IMSI_LV(g_pars.imsi));
Alexander Couzensb1ce1182019-09-15 22:43:40 +0200650 f_send_l3(ts_GMM_ID_RESP(mi), ran_index);
Harald Welte5ac31492018-02-15 20:39:13 +0100651 repeat;
652 }
Alexander Couzensb1ce1182019-09-15 22:43:40 +0200653 [is_iu(ran_index)] BSSAP.receive(tr_PDU_DTAP_PS_MT(tr_GMM_ID_REQ('001'B))) {
Alexander Couzens4444b5a2019-08-13 13:25:32 +0200654 mi := valueof(ts_MI_IMSI_LV(g_pars.imsi));
Alexander Couzensb1ce1182019-09-15 22:43:40 +0200655 f_send_l3(ts_GMM_ID_RESP(mi), ran_index);
Alexander Couzens4444b5a2019-08-13 13:25:32 +0200656 repeat;
657 }
Alexander Couzensb1ce1182019-09-15 22:43:40 +0200658 [is_gb(ran_index)] BSSGP[ran_index].receive(tr_GMM_ID_REQ('010'B)) {
Harald Welte5ac31492018-02-15 20:39:13 +0100659 mi := valueof(ts_MI_IMEI_LV(g_pars.imei));
Alexander Couzensb1ce1182019-09-15 22:43:40 +0200660 f_send_l3(ts_GMM_ID_RESP(mi), ran_index);
Alexander Couzens4444b5a2019-08-13 13:25:32 +0200661 repeat;
662 }
Alexander Couzensb1ce1182019-09-15 22:43:40 +0200663 [is_iu(ran_index)] BSSAP.receive(tr_PDU_DTAP_PS_MT(tr_GMM_ID_REQ('010'B))) {
Alexander Couzens4444b5a2019-08-13 13:25:32 +0200664 mi := valueof(ts_MI_IMEI_LV(g_pars.imei));
Alexander Couzensb1ce1182019-09-15 22:43:40 +0200665 f_send_l3(ts_GMM_ID_RESP(mi), ran_index);
Harald Welte5ac31492018-02-15 20:39:13 +0100666 repeat;
667 }
668}
Harald Welte96a33b02018-02-04 10:36:22 +0100669
Harald Welteca362462019-05-02 20:11:21 +0200670/* receive a L3 (GMM/SM) message over whatever is the appropriate lower-layer bearer */
Alexander Couzensb1ce1182019-09-15 22:43:40 +0200671function f_receive_l3(template PDU_L3_SGSN_MS rx_tpl := ?, integer ran_index := 0)
Harald Welteca362462019-05-02 20:11:21 +0200672runs on BSSGP_ConnHdlr return PDU_L3_SGSN_MS {
Alexander Couzens4444b5a2019-08-13 13:25:32 +0200673 var PDU_DTAP_PS_MT mt;
Harald Welteca362462019-05-02 20:11:21 +0200674 var PDU_L3_SGSN_MS l3_mt;
675 alt {
Alexander Couzensb1ce1182019-09-15 22:43:40 +0200676 [is_gb(ran_index)] BSSGP[ran_index].receive(rx_tpl) -> value l3_mt { }
677 [is_iu(ran_index)] BSSAP.receive(tr_PDU_DTAP_PS_MT(rx_tpl)) -> value mt {
Alexander Couzens4444b5a2019-08-13 13:25:32 +0200678 l3_mt := mt.dtap;
679 }
Harald Welteca362462019-05-02 20:11:21 +0200680 }
681 return l3_mt;
682}
683
Neels Hofmeyr0ecb2e32018-04-30 15:13:55 +0200684/* perform GMM authentication (if expected).
685 * Note, for umts_aka_challenge to work, the revisionLevelIndicatior needs to
686 * be 1 to mark R99 capability, in the GMM Attach Request, see f_gmm_attach(). */
Alexander Couzensb1ce1182019-09-15 22:43:40 +0200687function f_gmm_auth (boolean umts_aka_challenge := false, boolean force_gsm_sres := false, integer ran_index := 0) runs on BSSGP_ConnHdlr {
Harald Welte5ac31492018-02-15 20:39:13 +0100688 var PDU_L3_MS_SGSN l3_mo;
689 var PDU_L3_SGSN_MS l3_mt;
Alexander Couzensb1ce1182019-09-15 22:43:40 +0200690 var default di := activate(as_mm_identity(ran_index));
Harald Welte5ac31492018-02-15 20:39:13 +0100691 if (g_pars.net.expect_auth) {
Neels Hofmeyr0ecb2e32018-04-30 15:13:55 +0200692 var GSUP_IE auth_tuple;
693 var template AuthenticationParameterAUTNTLV autn;
694
695 if (umts_aka_challenge) {
696 g_pars.vec := f_gen_auth_vec_3g();
697 autn := {
698 elementIdentifier := '28'O,
699 lengthIndicator := lengthof(g_pars.vec.autn),
700 autnValue := g_pars.vec.autn
701 };
702
703 auth_tuple := valueof(ts_GSUP_IE_AuthTuple2G3G(g_pars.vec.rand,
704 g_pars.vec.sres,
705 g_pars.vec.kc,
706 g_pars.vec.ik,
707 g_pars.vec.ck,
708 g_pars.vec.autn,
709 g_pars.vec.res));
710 log("GSUP sends 2G and 3G auth tuples", auth_tuple);
711 } else {
712 g_pars.vec := f_gen_auth_vec_2g();
713 autn := omit;
714 auth_tuple := valueof(ts_GSUP_IE_AuthTuple2G(g_pars.vec.rand,
715 g_pars.vec.sres,
716 g_pars.vec.kc));
717 log("GSUP sends only 2G auth tuple", auth_tuple);
718 }
Harald Welteca362462019-05-02 20:11:21 +0200719
Harald Welte5ac31492018-02-15 20:39:13 +0100720 GSUP.receive(tr_GSUP_SAI_REQ(g_pars.imsi));
721 GSUP.send(ts_GSUP_SAI_RES(g_pars.imsi, auth_tuple));
Neels Hofmeyr0ecb2e32018-04-30 15:13:55 +0200722
723 var template PDU_L3_SGSN_MS auth_ciph_req := tr_GMM_AUTH_REQ(g_pars.vec.rand);
724 auth_ciph_req.msgs.gprs_mm.authenticationAndCipheringRequest.authenticationParameterAUTN := autn;
Alexander Couzensb1ce1182019-09-15 22:43:40 +0200725 l3_mt := f_receive_l3(auth_ciph_req, ran_index);
Harald Welte5ac31492018-02-15 20:39:13 +0100726 var BIT4 ac_ref := l3_mt.msgs.gprs_mm.authenticationAndCipheringRequest.acReferenceNumber.valueField;
Neels Hofmeyr0ecb2e32018-04-30 15:13:55 +0200727 var template PDU_L3_MS_SGSN auth_ciph_resp := ts_GMM_AUTH_RESP_2G(ac_ref, g_pars.vec.sres);
728
729 if (umts_aka_challenge and not force_gsm_sres) {
730 /* set UMTS response instead */
731 auth_ciph_resp.msgs.gprs_mm.authenticationAndCipheringResponse.authenticationParResp := {
732 valueField := substr(g_pars.vec.res, 0, 4)
733 };
734 auth_ciph_resp.msgs.gprs_mm.authenticationAndCipheringResponse.authenticationRespParExt := {
735 elementIdentifier := '21'O,
736 lengthIndicator := lengthof(g_pars.vec.res) - 4,
737 valueField := substr(g_pars.vec.res, 4, lengthof(g_pars.vec.res) - 4)
738 };
739 }
740
741 l3_mo := valueof(auth_ciph_resp);
Harald Welte5ac31492018-02-15 20:39:13 +0100742 if (ispresent(l3_mt.msgs.gprs_mm.authenticationAndCipheringRequest.imeisvRequest) and
743 l3_mt.msgs.gprs_mm.authenticationAndCipheringRequest.imeisvRequest.valueField == '001'B) {
744 l3_mo.msgs.gprs_mm.authenticationAndCipheringResponse.imeisv :=
745 valueof(ts_MI_IMEISV_TLV(g_pars.imei & '0'H));
746 }
Alexander Couzensb1ce1182019-09-15 22:43:40 +0200747 f_send_l3(l3_mo, ran_index);
Alexander Couzens4444b5a2019-08-13 13:25:32 +0200748
749 /* Security Mode Command + Complete on Iu case */
Alexander Couzensb1ce1182019-09-15 22:43:40 +0200750 if (is_iu(ran_index)) {
Alexander Couzens4444b5a2019-08-13 13:25:32 +0200751 BSSAP.receive(tr_RANAP_SecurityModeCmd(uia_algs := ?, uia_key := oct2bit(g_pars.vec.ik),
752 key_sts := ?)) {
753 var IntegrityProtectionAlgorithm uia_chosen := 0; /* 0 = standard_UMTS_integrity_algorithm_UIA1 */
754 BSSAP.send(ts_RANAP_SecurityModeComplete(uia_chosen));
Alexander Couzensed61ae82019-09-15 23:18:08 +0200755 BSSAP.receive(tr_RANAP_CommonId(imsi_hex2oct(g_pars.imsi)))
Alexander Couzens4444b5a2019-08-13 13:25:32 +0200756 }
757 }
Harald Welte76dee092018-02-16 22:12:59 +0100758 } else {
759 /* wait for identity procedure */
760 f_sleep(1.0);
Harald Welte5ac31492018-02-15 20:39:13 +0100761 }
Harald Welte76dee092018-02-16 22:12:59 +0100762
Harald Welte5ac31492018-02-15 20:39:13 +0100763 deactivate(di);
764}
765
Alexander Couzensb22e8ce2019-09-15 22:39:58 +0200766function f_upd_ptmsi_and_tlli(OCT4 p_tmsi, integer ran_index := 0) runs on BSSGP_ConnHdlr {
Harald Weltef70997d2018-02-17 10:11:19 +0100767 g_pars.p_tmsi := p_tmsi;
768 /* update TLLI */
769 g_pars.tlli_old := g_pars.tlli;
770 g_pars.tlli := g_pars.p_tmsi or4b 'c0000000'O;
Daniel Willmann1c2ff0f2020-01-28 14:39:25 +0100771 if (is_gb(ran_index)) {
772 f_bssgp_client_llgmm_assign(g_pars.tlli_old, g_pars.tlli, BSSGP_PROC[ran_index]);
773 }
Harald Weltef70997d2018-02-17 10:11:19 +0100774}
775
Pau Espin Pedrold792b9e2021-02-12 19:49:59 +0100776function f_process_attach_accept(PDU_GMM_AttachAccept aa, integer ran_index := 0) runs on BSSGP_ConnHdlr {
Harald Welte04683d02018-02-16 22:43:45 +0100777 /* mandatory IE */
Neels Hofmeyr8df7d152018-03-14 19:03:28 +0100778 var hexstring aa_plmn := f_RAI_to_plmn_hexstr(aa.routingAreaIdentification);
Harald Weltedd9fb842021-02-16 20:21:22 +0100779 /* we cannot use ran_index here, as it would overflow the cell_id object, since ran_idx > NUM_GB
780 * indicates an Iu RAN connection. All cells are expected to run the same MCC/MNC anyway... */
781 if (not (g_pars.bssgp_cell_id[0].ra_id.lai.mcc_mnc == aa_plmn)) {
Neels Hofmeyr8df7d152018-03-14 19:03:28 +0100782 setverdict(fail, "mismatching PLMN in Attach Accept: " & hex2str(aa_plmn)
Pau Espin Pedrold792b9e2021-02-12 19:49:59 +0100783 & "; expected " & hex2str(g_pars.bssgp_cell_id[ran_index].ra_id.lai.mcc_mnc));
Daniel Willmannafce8662018-07-06 23:11:32 +0200784 mtc.stop;
Neels Hofmeyr8df7d152018-03-14 19:03:28 +0100785 }
Harald Welte04683d02018-02-16 22:43:45 +0100786 g_pars.ra := aa.routingAreaIdentification;
787 if (ispresent(aa.allocatedPTMSI)) {
788 if (not g_pars.net.expect_ptmsi) {
789 setverdict(fail, "unexpected P-TMSI allocation");
Daniel Willmannafce8662018-07-06 23:11:32 +0200790 mtc.stop;
Harald Welte04683d02018-02-16 22:43:45 +0100791 }
Pau Espin Pedrold792b9e2021-02-12 19:49:59 +0100792 f_upd_ptmsi_and_tlli(aa.allocatedPTMSI.mobileIdentityLV.mobileIdentityV.oddEvenInd_identity.tmsi_ptmsi.octets,
793 ran_index);
Harald Welte04683d02018-02-16 22:43:45 +0100794 }
795 if (ispresent(aa.msIdentity)) {
796 setverdict(fail, "unexpected TMSI allocation in non-combined attach");
Daniel Willmannafce8662018-07-06 23:11:32 +0200797 mtc.stop;
Harald Welte04683d02018-02-16 22:43:45 +0100798 }
799 /* P-TMSI.sig */
800 if (ispresent(aa.ptmsiSignature)) {
801 g_pars.p_tmsi_sig := aa.ptmsiSignature.valueField;
802 }
803 /* updateTimer */
804 // aa.readyTimer
805 /* T3302, T3319, T3323, T3312_ext, T3324 */
806}
807
Alexander Couzensb22e8ce2019-09-15 22:39:58 +0200808function f_process_rau_accept(PDU_GMM_RoutingAreaUpdateAccept ra, integer ran_index := 0) runs on BSSGP_ConnHdlr {
Harald Welte91636de2018-02-17 10:16:14 +0100809 /* mandatory IE */
810 g_pars.ra := ra.routingAreaId;
811 if (ispresent(ra.allocatedPTMSI)) {
812 if (not g_pars.net.expect_ptmsi) {
813 setverdict(fail, "unexpected P-TMSI allocation");
Daniel Willmannafce8662018-07-06 23:11:32 +0200814 mtc.stop;
Harald Welte91636de2018-02-17 10:16:14 +0100815 }
Pau Espin Pedrold792b9e2021-02-12 19:49:59 +0100816 f_upd_ptmsi_and_tlli(ra.allocatedPTMSI.mobileIdentityLV.mobileIdentityV.oddEvenInd_identity.tmsi_ptmsi.octets,
817 ran_index);
Harald Welte91636de2018-02-17 10:16:14 +0100818 }
819 if (ispresent(ra.msIdentity)) {
820 setverdict(fail, "unexpected TMSI allocation in non-combined attach");
Daniel Willmannafce8662018-07-06 23:11:32 +0200821 mtc.stop;
Harald Welte91636de2018-02-17 10:16:14 +0100822 }
823 /* P-TMSI.sig */
824 if (ispresent(ra.ptmsiSignature)) {
825 g_pars.p_tmsi_sig := ra.ptmsiSignature.valueField;
826 }
827 /* updateTimer */
828 // aa.readyTimer
829 /* T3302, T3319, T3323, T3312_ext, T3324 */
830}
831
832
Harald Welte5a4fa042018-02-16 20:59:21 +0100833function f_random_RAI(HEX0_3n mcc := '262'H, HEX0_3n mnc := '42'H) return RoutingAreaIdentificationV {
834 return f_RAI(mcc, mnc, f_rnd_octstring(2), f_rnd_octstring(1));
835}
836
Harald Welte23178c52018-02-17 09:36:33 +0100837/* return a MobileIdentityLV: P-TMSI if we have one, IMSI otherwise */
Vadim Yanitskiy98bb2d52020-03-28 00:57:21 +0700838private function f_mi_get_lv() runs on BSSGP_ConnHdlr return MobileIdentityLV {
Harald Welte23178c52018-02-17 09:36:33 +0100839 if (ispresent(g_pars.p_tmsi)) {
840 return valueof(ts_MI_TMSI_LV(g_pars.p_tmsi));
841 } else {
842 return valueof(ts_MI_IMSI_LV(g_pars.imsi));
843 }
844}
845
Harald Welte311ec272018-02-17 09:40:03 +0100846private function f_gmm_gsup_lu_isd() runs on BSSGP_ConnHdlr {
Harald Welteeded9ad2018-02-17 20:57:34 +0100847 var GSUP_PDU gsup;
Harald Welte311ec272018-02-17 09:40:03 +0100848 /* Expect MSC to perform LU with HLR */
849 GSUP.receive(tr_GSUP_UL_REQ(g_pars.imsi));
Harald Welteeded9ad2018-02-17 20:57:34 +0100850 gsup := valueof(ts_GSUP_ISD_REQ(g_pars.imsi, g_pars.msisdn));
851 gsup.ies := gsup.ies & { valueof(ts_GSUP_IE_PdpInfo(char2oct("*"), '0121'O, ''O)) };
852 GSUP.send(gsup);
Harald Welte311ec272018-02-17 09:40:03 +0100853 GSUP.receive(tr_GSUP_ISD_RES(g_pars.imsi));
854 GSUP.send(ts_GSUP_UL_RES(g_pars.imsi));
855}
856
Pau Espin Pedrol7c052162021-02-12 17:43:35 +0100857friend function f_gmm_attach(boolean umts_aka_challenge, boolean force_gsm_sres, integer ran_index := 0,
858 template (omit) RoutingAreaIdentificationV old_ra := omit) runs on BSSGP_ConnHdlr {
859 var RoutingAreaIdentificationV old_ra_val;
860 var template PDU_L3_MS_SGSN attach_req;
Harald Welteca362462019-05-02 20:11:21 +0200861 var PDU_L3_SGSN_MS l3_mt;
Harald Welte5ac31492018-02-15 20:39:13 +0100862
Pau Espin Pedrol7c052162021-02-12 17:43:35 +0100863 if (istemplatekind(old_ra, "omit")) {
864 old_ra_val := f_random_RAI();
865 } else {
866 old_ra_val := valueof(old_ra);
867 }
868
869 attach_req := ts_GMM_ATTACH_REQ(f_mi_get_lv(), old_ra_val, false, false, omit, omit);
Neels Hofmeyr0ecb2e32018-04-30 15:13:55 +0200870 /* indicate R99 capability of the MS to enable UMTS AKA in presence of
871 * 3G auth vectors */
872 attach_req.msgs.gprs_mm.attachRequest.msNetworkCapability.msNetworkCapabilityV.revisionLevelIndicatior := '1'B;
873 /* The thing is, if the solSACapability is 'omit', then the
874 * revisionLevelIndicatior is at the wrong place! */
875 attach_req.msgs.gprs_mm.attachRequest.msNetworkCapability.msNetworkCapabilityV.solSACapability := '0'B;
876
Alexander Couzensb1ce1182019-09-15 22:43:40 +0200877 f_send_l3(attach_req, ran_index);
878 f_gmm_auth(umts_aka_challenge, force_gsm_sres, ran_index);
Alexander Couzens5844d5b2018-05-14 06:30:56 +0200879 /* Expect SGSN to perform LU with HLR */
Harald Welte311ec272018-02-17 09:40:03 +0100880 f_gmm_gsup_lu_isd();
Harald Welte5ac31492018-02-15 20:39:13 +0100881
Alexander Couzensb1ce1182019-09-15 22:43:40 +0200882 l3_mt := f_receive_l3(tr_GMM_ATTACH_ACCEPT('001'B, ?, ?), ran_index);
Pau Espin Pedrold792b9e2021-02-12 19:49:59 +0100883 f_process_attach_accept(l3_mt.msgs.gprs_mm.attachAccept, ran_index);
Harald Welteca362462019-05-02 20:11:21 +0200884
Harald Welte04683d02018-02-16 22:43:45 +0100885 /* FIXME: Extract P-TMSI, if any. Only send Complete if necessary */
Alexander Couzensb1ce1182019-09-15 22:43:40 +0200886 f_send_l3(ts_GMM_ATTACH_COMPL, ran_index);
Alexander Couzens4444b5a2019-08-13 13:25:32 +0200887
888 /* IuPS case: Expect Iu Release */
Alexander Couzensb1ce1182019-09-15 22:43:40 +0200889 if (is_iu(ran_index)) {
Alexander Couzens4444b5a2019-08-13 13:25:32 +0200890 as_iu_release_compl_disc();
891 }
Alexander Couzens42d3cad2019-10-08 16:29:26 +0200892
893 /* Race condition
894 * It has shown, that GMM_ATTACH_COMPL might take some time to arrive at the SGSN through the layers.
895 * In TC hlr_location_cancel_request_update, the GMM_ATTACH_COMPL came 2ms too late, so that the Location Cancel Request
896 * arrived before it. This results in a test case failure.
897 * Delay execution by 50 ms
898 */
899 f_sleep(0.05);
Neels Hofmeyr0ecb2e32018-04-30 15:13:55 +0200900}
901
Harald Weltef2f3c9b2020-06-17 22:11:43 +0200902friend function f_bssgp_suspend(integer ran_idx := 0) runs on BSSGP_ConnHdlr return OCT1 {
903 timer T := 5.0;
904 var PDU_BSSGP rx_pdu;
Harald Welte9b461a92020-12-10 23:41:14 +0100905 BSSGP_GLOBAL[ran_idx].send(ts_BSSGP_SUSPEND(g_pars.tlli, g_pars.bssgp_cell_id[ran_idx].ra_id));
Harald Weltef2f3c9b2020-06-17 22:11:43 +0200906 T.start;
907 alt {
Harald Welte9b461a92020-12-10 23:41:14 +0100908 [] BSSGP_GLOBAL[ran_idx].receive(tr_BSSGP_SUSPEND_ACK(g_pars.tlli, g_pars.bssgp_cell_id[ran_idx].ra_id, ?)) -> value rx_pdu {
Harald Weltef2f3c9b2020-06-17 22:11:43 +0200909 return rx_pdu.pDU_BSSGP_SUSPEND_ACK.suspend_Reference_Number.suspend_Reference_Number_value;
910 }
Harald Welte9b461a92020-12-10 23:41:14 +0100911 [] BSSGP_GLOBAL[ran_idx].receive(tr_BSSGP_SUSPEND_NACK(g_pars.tlli, g_pars.bssgp_cell_id[ran_idx].ra_id, ?)) -> value rx_pdu {
Harald Weltef2f3c9b2020-06-17 22:11:43 +0200912 setverdict(fail, "SUSPEND-NACK in response to SUSPEND for TLLI ", g_pars.tlli);
913 mtc.stop;
914 }
915 [] T.timeout {
916 setverdict(fail, "No SUSPEND-ACK in response to SUSPEND for TLLI ", g_pars.tlli);
917 mtc.stop;
918 }
919 }
920 return '00'O;
921}
922
923friend function f_bssgp_resume(OCT1 susp_ref, integer ran_idx := 0) runs on BSSGP_ConnHdlr {
924 timer T := 5.0;
Harald Welte9b461a92020-12-10 23:41:14 +0100925 BSSGP_GLOBAL[ran_idx].send(ts_BSSGP_RESUME(g_pars.tlli, g_pars.bssgp_cell_id[ran_idx].ra_id, susp_ref));
Harald Weltef2f3c9b2020-06-17 22:11:43 +0200926 T.start;
927 alt {
Harald Welte9b461a92020-12-10 23:41:14 +0100928 [] BSSGP_GLOBAL[ran_idx].receive(tr_BSSGP_RESUME_ACK(g_pars.tlli, g_pars.bssgp_cell_id[ran_idx].ra_id));
929 [] BSSGP_GLOBAL[ran_idx].receive(tr_BSSGP_RESUME_NACK(g_pars.tlli, g_pars.bssgp_cell_id[ran_idx].ra_id,
Harald Weltef2f3c9b2020-06-17 22:11:43 +0200930?)) {
931 setverdict(fail, "RESUME-NACK in response to RESUME for TLLI ", g_pars.tlli);
932 mtc.stop;
933 }
934 [] T.timeout {
935 setverdict(fail, "No RESUME-ACK in response to SUSPEND for TLLI ", g_pars.tlli);
936 mtc.stop;
937 }
938 }
939}
940
941
Neels Hofmeyr0ecb2e32018-04-30 15:13:55 +0200942private function f_TC_attach(charstring id) runs on BSSGP_ConnHdlr {
943 f_gmm_attach(false, false);
Harald Welte5a4fa042018-02-16 20:59:21 +0100944 setverdict(pass);
Harald Welte5ac31492018-02-15 20:39:13 +0100945}
946
947testcase TC_attach() runs on test_CT {
948 var BSSGP_ConnHdlr vc_conn;
949 f_init();
950 f_sleep(1.0);
Alexander Couzens51114d12018-07-31 18:41:56 +0200951 vc_conn := f_start_handler(refers(f_TC_attach), testcasename(), g_gb, 1);
Harald Welte5ac31492018-02-15 20:39:13 +0100952 vc_conn.done;
Pau Espin Pedrolce0d6152019-08-27 19:07:27 +0200953 f_cleanup();
Harald Welte5ac31492018-02-15 20:39:13 +0100954}
955
Neels Hofmeyr8df7d152018-03-14 19:03:28 +0100956testcase TC_attach_mnc3() runs on test_CT {
957 var BSSGP_ConnHdlr vc_conn;
958 f_init('023042'H);
959 f_sleep(1.0);
Alexander Couzens51114d12018-07-31 18:41:56 +0200960 vc_conn := f_start_handler(refers(f_TC_attach), testcasename(), g_gb, 1001);
Neels Hofmeyr8df7d152018-03-14 19:03:28 +0100961 vc_conn.done;
Pau Espin Pedrolce0d6152019-08-27 19:07:27 +0200962 f_cleanup();
Neels Hofmeyr8df7d152018-03-14 19:03:28 +0100963}
964
Neels Hofmeyr0ecb2e32018-04-30 15:13:55 +0200965private function f_TC_attach_umts_aka_umts_res(charstring id) runs on BSSGP_ConnHdlr {
966 f_gmm_attach(true, false);
967 setverdict(pass);
968}
969testcase TC_attach_umts_aka_umts_res() runs on test_CT {
970 var BSSGP_ConnHdlr vc_conn;
971 f_init();
972 f_sleep(1.0);
Alexander Couzens51114d12018-07-31 18:41:56 +0200973 vc_conn := f_start_handler(refers(f_TC_attach_umts_aka_umts_res), testcasename(), g_gb, 1002);
Neels Hofmeyr0ecb2e32018-04-30 15:13:55 +0200974 vc_conn.done;
Pau Espin Pedrolce0d6152019-08-27 19:07:27 +0200975 f_cleanup();
Neels Hofmeyr0ecb2e32018-04-30 15:13:55 +0200976}
977
978private function f_TC_attach_umts_aka_gsm_sres(charstring id) runs on BSSGP_ConnHdlr {
979 f_gmm_attach(true, true);
980 setverdict(pass);
981}
982testcase TC_attach_umts_aka_gsm_sres() runs on test_CT {
983 var BSSGP_ConnHdlr vc_conn;
984 f_init();
985 f_sleep(1.0);
Alexander Couzens51114d12018-07-31 18:41:56 +0200986 vc_conn := f_start_handler(refers(f_TC_attach_umts_aka_gsm_sres), testcasename(), g_gb, 1003);
Neels Hofmeyr0ecb2e32018-04-30 15:13:55 +0200987 vc_conn.done;
Pau Espin Pedrolce0d6152019-08-27 19:07:27 +0200988 f_cleanup();
Neels Hofmeyr0ecb2e32018-04-30 15:13:55 +0200989}
990
Harald Welte5b7c8122018-02-16 21:48:17 +0100991/* MS never responds to ID REQ, expect ATTACH REJECT */
992private function f_TC_attach_auth_id_timeout(charstring id) runs on BSSGP_ConnHdlr {
Harald Welte5b7c8122018-02-16 21:48:17 +0100993 var RoutingAreaIdentificationV old_ra := f_random_RAI();
994
Alexander Couzens4444b5a2019-08-13 13:25:32 +0200995 f_send_l3(ts_GMM_ATTACH_REQ(f_mi_get_lv(), old_ra, false, false, omit, omit));
Harald Welte5b7c8122018-02-16 21:48:17 +0100996 alt {
Harald Welte955aa942019-05-03 01:29:29 +0200997 [] BSSGP[0].receive(tr_GMM_ID_REQ(?)) {
Harald Welte5b7c8122018-02-16 21:48:17 +0100998 /* don't send ID Response */
999 repeat;
1000 }
Harald Welte955aa942019-05-03 01:29:29 +02001001 [] BSSGP[0].receive(tr_GMM_ATTACH_REJECT('09'O)) {
Harald Welte5b7c8122018-02-16 21:48:17 +01001002 setverdict(pass);
1003 }
Harald Welte955aa942019-05-03 01:29:29 +02001004 [] BSSGP[0].receive(tr_GMM_ATTACH_REJECT(?)) {
Harald Welte5b7c8122018-02-16 21:48:17 +01001005 setverdict(fail, "Wrong Attach Reject Cause");
Daniel Willmannafce8662018-07-06 23:11:32 +02001006 mtc.stop;
Harald Welte5b7c8122018-02-16 21:48:17 +01001007 }
1008 }
1009}
1010testcase TC_attach_auth_id_timeout() runs on test_CT {
1011 var BSSGP_ConnHdlr vc_conn;
1012 f_init();
Alexander Couzens51114d12018-07-31 18:41:56 +02001013 vc_conn := f_start_handler(refers(f_TC_attach_auth_id_timeout), testcasename(), g_gb, 2, 40.0);
Harald Welte5b7c8122018-02-16 21:48:17 +01001014 vc_conn.done;
Pau Espin Pedrolce0d6152019-08-27 19:07:27 +02001015 f_cleanup();
Harald Welte5b7c8122018-02-16 21:48:17 +01001016}
1017
1018/* HLR never responds to SAI REQ, expect ATTACH REJECT */
1019private function f_TC_attach_auth_sai_timeout(charstring id) runs on BSSGP_ConnHdlr {
Harald Welte5b7c8122018-02-16 21:48:17 +01001020 var RoutingAreaIdentificationV old_ra := f_random_RAI();
1021
Alexander Couzens4444b5a2019-08-13 13:25:32 +02001022 f_send_l3(ts_GMM_ATTACH_REQ(f_mi_get_lv(), old_ra, false, false, omit, omit));
Harald Welte5b7c8122018-02-16 21:48:17 +01001023 alt {
1024 [] as_mm_identity();
1025 [] GSUP.receive(tr_GSUP_SAI_REQ(g_pars.imsi)); { }
1026 }
1027 /* don't send SAI-response from HLR */
Harald Welte955aa942019-05-03 01:29:29 +02001028 BSSGP[0].receive(tr_GMM_ATTACH_REJECT(?));
Harald Welte5b7c8122018-02-16 21:48:17 +01001029 setverdict(pass);
1030}
1031testcase TC_attach_auth_sai_timeout() runs on test_CT {
1032 var BSSGP_ConnHdlr vc_conn;
1033 f_init();
Alexander Couzens51114d12018-07-31 18:41:56 +02001034 vc_conn := f_start_handler(refers(f_TC_attach_auth_sai_timeout), testcasename(), g_gb, 3);
Harald Welte5b7c8122018-02-16 21:48:17 +01001035 vc_conn.done;
Pau Espin Pedrolce0d6152019-08-27 19:07:27 +02001036 f_cleanup();
Harald Welte5b7c8122018-02-16 21:48:17 +01001037}
1038
Harald Weltefe253882018-02-17 09:25:00 +01001039/* HLR rejects SAI, expect ATTACH REJECT */
1040private function f_TC_attach_auth_sai_reject(charstring id) runs on BSSGP_ConnHdlr {
Harald Weltefe253882018-02-17 09:25:00 +01001041 var RoutingAreaIdentificationV old_ra := f_random_RAI();
1042
Alexander Couzens4444b5a2019-08-13 13:25:32 +02001043 f_send_l3(ts_GMM_ATTACH_REQ(f_mi_get_lv(), old_ra, false, false, omit, omit));
Harald Weltefe253882018-02-17 09:25:00 +01001044 alt {
1045 [] as_mm_identity();
1046 [] GSUP.receive(tr_GSUP_SAI_REQ(g_pars.imsi)); {
1047 GSUP.send(ts_GSUP_SAI_ERR(g_pars.imsi, 23));
1048 }
1049 }
Harald Welte955aa942019-05-03 01:29:29 +02001050 BSSGP[0].receive(tr_GMM_ATTACH_REJECT(?));
Harald Weltefe253882018-02-17 09:25:00 +01001051 setverdict(pass);
1052}
1053testcase TC_attach_auth_sai_reject() runs on test_CT {
1054 var BSSGP_ConnHdlr vc_conn;
1055 f_init();
Alexander Couzens51114d12018-07-31 18:41:56 +02001056 vc_conn := f_start_handler(refers(f_TC_attach_auth_sai_reject), testcasename(), g_gb, 4);
Harald Weltefe253882018-02-17 09:25:00 +01001057 vc_conn.done;
Pau Espin Pedrolce0d6152019-08-27 19:07:27 +02001058 f_cleanup();
Harald Weltefe253882018-02-17 09:25:00 +01001059}
1060
Harald Welte5b7c8122018-02-16 21:48:17 +01001061/* HLR never responds to UL REQ, expect ATTACH REJECT */
1062private function f_TC_attach_gsup_lu_timeout(charstring id) runs on BSSGP_ConnHdlr {
Harald Welte955aa942019-05-03 01:29:29 +02001063 var PDU_L3_SGSN_MS l3_mt;
Harald Welte5b7c8122018-02-16 21:48:17 +01001064 var RoutingAreaIdentificationV old_ra := f_random_RAI();
1065
Alexander Couzens4444b5a2019-08-13 13:25:32 +02001066 f_send_l3(ts_GMM_ATTACH_REQ(f_mi_get_lv(), old_ra, false, false, omit, omit));
Harald Welte5b7c8122018-02-16 21:48:17 +01001067 f_gmm_auth();
1068 /* Expect MSC to perform LU with HLR */
1069 GSUP.receive(tr_GSUP_UL_REQ(g_pars.imsi));
1070 /* Never follow-up with ISD_REQ or UL_RES */
1071 alt {
Harald Welte955aa942019-05-03 01:29:29 +02001072 [] BSSGP[0].receive(tr_GMM_ATTACH_REJECT(?)) {
Harald Welte5b7c8122018-02-16 21:48:17 +01001073 setverdict(pass);
1074 }
Harald Welte955aa942019-05-03 01:29:29 +02001075 [] BSSGP[0].receive(tr_GMM_ATTACH_ACCEPT('001'B, ?, ?)) -> value l3_mt {
1076 f_process_attach_accept(l3_mt.msgs.gprs_mm.attachAccept);
Harald Welte5b7c8122018-02-16 21:48:17 +01001077 setverdict(fail);
Daniel Willmannafce8662018-07-06 23:11:32 +02001078 mtc.stop;
Harald Welte5b7c8122018-02-16 21:48:17 +01001079 }
1080 }
1081}
1082testcase TC_attach_gsup_lu_timeout() runs on test_CT {
1083 var BSSGP_ConnHdlr vc_conn;
1084 f_init();
1085 f_sleep(1.0);
Alexander Couzens51114d12018-07-31 18:41:56 +02001086 vc_conn := f_start_handler(refers(f_TC_attach_gsup_lu_timeout), testcasename(), g_gb, 5);
Harald Welte5b7c8122018-02-16 21:48:17 +01001087 vc_conn.done;
Pau Espin Pedrolce0d6152019-08-27 19:07:27 +02001088 f_cleanup();
Harald Welte5b7c8122018-02-16 21:48:17 +01001089}
1090
Harald Welteb7c14e92018-02-17 09:29:16 +01001091/* HLR rejects UL REQ, expect ATTACH REJECT */
1092private function f_TC_attach_gsup_lu_reject(charstring id) runs on BSSGP_ConnHdlr {
Harald Welte955aa942019-05-03 01:29:29 +02001093 var PDU_L3_SGSN_MS l3_mt;
Harald Welteb7c14e92018-02-17 09:29:16 +01001094 var RoutingAreaIdentificationV old_ra := f_random_RAI();
1095
Alexander Couzens4444b5a2019-08-13 13:25:32 +02001096 f_send_l3(ts_GMM_ATTACH_REQ(f_mi_get_lv(), old_ra, false, false, omit, omit));
Harald Welteb7c14e92018-02-17 09:29:16 +01001097 f_gmm_auth();
1098 /* Expect MSC to perform LU with HLR */
1099 GSUP.receive(tr_GSUP_UL_REQ(g_pars.imsi)) {
1100 GSUP.send(ts_GSUP_UL_ERR(g_pars.imsi, 0));
1101 }
1102 alt {
Harald Welte955aa942019-05-03 01:29:29 +02001103 [] BSSGP[0].receive(tr_GMM_ATTACH_REJECT(?)) {
Harald Welteb7c14e92018-02-17 09:29:16 +01001104 setverdict(pass);
1105 }
Harald Welte955aa942019-05-03 01:29:29 +02001106 [] BSSGP[0].receive(tr_GMM_ATTACH_ACCEPT('001'B, ?, ?)) -> value l3_mt {
1107 f_process_attach_accept(l3_mt.msgs.gprs_mm.attachAccept);
Harald Welteb7c14e92018-02-17 09:29:16 +01001108 setverdict(fail);
Daniel Willmannafce8662018-07-06 23:11:32 +02001109 mtc.stop;
Harald Welteb7c14e92018-02-17 09:29:16 +01001110 }
1111 }
1112}
1113testcase TC_attach_gsup_lu_reject() runs on test_CT {
1114 var BSSGP_ConnHdlr vc_conn;
1115 f_init();
1116 f_sleep(1.0);
Alexander Couzens51114d12018-07-31 18:41:56 +02001117 vc_conn := f_start_handler(refers(f_TC_attach_gsup_lu_reject), testcasename(), g_gb, 6);
Harald Welteb7c14e92018-02-17 09:29:16 +01001118 vc_conn.done;
Pau Espin Pedrolce0d6152019-08-27 19:07:27 +02001119 f_cleanup();
Harald Welteb7c14e92018-02-17 09:29:16 +01001120}
1121
1122
Harald Welte3823e2e2018-02-16 21:53:48 +01001123/* Attempt of combined GPRS + IMSI attach: network should ACK only GPRS attach */
1124private function f_TC_attach_combined(charstring id) runs on BSSGP_ConnHdlr {
Harald Welte955aa942019-05-03 01:29:29 +02001125 var PDU_L3_SGSN_MS l3_mt;
Harald Welte3823e2e2018-02-16 21:53:48 +01001126 var RoutingAreaIdentificationV old_ra := f_random_RAI();
1127
Alexander Couzens4444b5a2019-08-13 13:25:32 +02001128 f_send_l3(ts_GMM_ATTACH_REQ(f_mi_get_lv(), old_ra, true, false, omit, omit));
Harald Welte3823e2e2018-02-16 21:53:48 +01001129 f_gmm_auth();
1130 /* Expect MSC to perform LU with HLR */
Harald Welte311ec272018-02-17 09:40:03 +01001131 f_gmm_gsup_lu_isd();
Harald Welte3823e2e2018-02-16 21:53:48 +01001132
Harald Welte955aa942019-05-03 01:29:29 +02001133 BSSGP[0].receive(tr_GMM_ATTACH_ACCEPT('001'B, ?, ?)) -> value l3_mt {
1134 f_process_attach_accept(l3_mt.msgs.gprs_mm.attachAccept);
Harald Welte04683d02018-02-16 22:43:45 +01001135 }
Alexander Couzens4444b5a2019-08-13 13:25:32 +02001136 f_send_l3(ts_GMM_ATTACH_COMPL);
Harald Welte3823e2e2018-02-16 21:53:48 +01001137 setverdict(pass);
1138}
Harald Welte3823e2e2018-02-16 21:53:48 +01001139testcase TC_attach_combined() runs on test_CT {
1140 var BSSGP_ConnHdlr vc_conn;
1141 f_init();
1142 f_sleep(1.0);
Alexander Couzens51114d12018-07-31 18:41:56 +02001143 vc_conn := f_start_handler(refers(f_TC_attach_combined), testcasename(), g_gb, 7);
Harald Welte3823e2e2018-02-16 21:53:48 +01001144 vc_conn.done;
Pau Espin Pedrolce0d6152019-08-27 19:07:27 +02001145 f_cleanup();
Harald Welte3823e2e2018-02-16 21:53:48 +01001146}
1147
Harald Welte76dee092018-02-16 22:12:59 +01001148/* Attempt of GPRS ATTACH in 'accept all' mode */
1149private function f_TC_attach_accept_all(charstring id) runs on BSSGP_ConnHdlr {
Harald Welte955aa942019-05-03 01:29:29 +02001150 var PDU_L3_SGSN_MS l3_mt;
Harald Welte76dee092018-02-16 22:12:59 +01001151 var RoutingAreaIdentificationV old_ra := f_random_RAI();
1152
1153 g_pars.net.expect_auth := false;
1154
Alexander Couzens4444b5a2019-08-13 13:25:32 +02001155 f_send_l3(ts_GMM_ATTACH_REQ(f_mi_get_lv(), old_ra, false, false, omit, omit));
Harald Welte76dee092018-02-16 22:12:59 +01001156 f_gmm_auth();
Harald Welte955aa942019-05-03 01:29:29 +02001157 BSSGP[0].receive(tr_GMM_ATTACH_ACCEPT('001'B, ?, ?)) -> value l3_mt {
1158 f_process_attach_accept(l3_mt.msgs.gprs_mm.attachAccept);
Harald Welte04683d02018-02-16 22:43:45 +01001159 }
Alexander Couzens4444b5a2019-08-13 13:25:32 +02001160 f_send_l3(ts_GMM_ATTACH_COMPL);
Harald Welte76dee092018-02-16 22:12:59 +01001161 setverdict(pass);
1162}
1163testcase TC_attach_accept_all() runs on test_CT {
1164 var BSSGP_ConnHdlr vc_conn;
1165 f_init();
1166 f_sleep(1.0);
1167 f_vty_config(SGSNVTY, "sgsn", "auth-policy accept-all");
Alexander Couzens51114d12018-07-31 18:41:56 +02001168 vc_conn := f_start_handler(refers(f_TC_attach_accept_all), testcasename(), g_gb, 8);
Harald Welte76dee092018-02-16 22:12:59 +01001169 vc_conn.done;
Pau Espin Pedrolce0d6152019-08-27 19:07:27 +02001170 f_cleanup();
Harald Welte76dee092018-02-16 22:12:59 +01001171}
Harald Welte5b7c8122018-02-16 21:48:17 +01001172
Harald Welteb2124b22018-02-16 22:26:56 +01001173/* Attempt of GPRS ATTACH in 'accept all' mode */
1174private function f_TC_attach_closed_foreign(charstring id) runs on BSSGP_ConnHdlr {
Harald Welteb2124b22018-02-16 22:26:56 +01001175 var RoutingAreaIdentificationV old_ra := f_random_RAI();
1176
1177 /* Simulate a foreign IMSI */
1178 g_pars.imsi := '001010123456789'H;
Harald Welte5339b2e2020-10-04 22:52:56 +02001179 f_bssgp_client_register(g_pars.imsi, g_pars.tlli);
Harald Welteb2124b22018-02-16 22:26:56 +01001180
1181 g_pars.net.expect_auth := false;
1182
Alexander Couzens4444b5a2019-08-13 13:25:32 +02001183 f_send_l3(ts_GMM_ATTACH_REQ(f_mi_get_lv(), old_ra, false, false, omit, omit));
Harald Welteb2124b22018-02-16 22:26:56 +01001184 alt {
1185 [] as_mm_identity();
Harald Welte955aa942019-05-03 01:29:29 +02001186 [] BSSGP[0].receive(tr_GMM_ATTACH_REJECT('07'O)) {
Harald Welteb2124b22018-02-16 22:26:56 +01001187 setverdict(pass);
1188 }
Harald Welte955aa942019-05-03 01:29:29 +02001189 [] BSSGP[0].receive(tr_GMM_ATTACH_REJECT(?)) {
Harald Welteb2124b22018-02-16 22:26:56 +01001190 setverdict(pass);
1191 }
Harald Welte955aa942019-05-03 01:29:29 +02001192 [] BSSGP[0].receive(tr_GMM_ATTACH_ACCEPT(*, *, *)) {
Alexander Couzens0ca0d9c2018-06-12 14:01:34 +02001193 setverdict(fail);
Daniel Willmannafce8662018-07-06 23:11:32 +02001194 mtc.stop;
Alexander Couzens0ca0d9c2018-06-12 14:01:34 +02001195 }
Harald Welteb2124b22018-02-16 22:26:56 +01001196 }
1197}
1198testcase TC_attach_closed() runs on test_CT {
1199 var BSSGP_ConnHdlr vc_conn;
1200 f_init();
1201 f_sleep(1.0);
1202 f_vty_config(SGSNVTY, "sgsn", "auth-policy closed");
1203 /* test with foreign IMSI: Must Reject */
Alexander Couzens51114d12018-07-31 18:41:56 +02001204 vc_conn := f_start_handler(refers(f_TC_attach_closed_foreign), testcasename(), g_gb, 9);
Harald Welteb2124b22018-02-16 22:26:56 +01001205 vc_conn.done;
1206 /* test with home IMSI: Must Accept */
Alexander Couzens51114d12018-07-31 18:41:56 +02001207 vc_conn := f_start_handler(refers(f_TC_attach_accept_all), testcasename(), g_gb, 10);
Harald Welteb2124b22018-02-16 22:26:56 +01001208 vc_conn.done;
Pau Espin Pedrolce0d6152019-08-27 19:07:27 +02001209 f_cleanup();
Harald Welteb2124b22018-02-16 22:26:56 +01001210}
1211
Harald Welte04683d02018-02-16 22:43:45 +01001212/* Routing Area Update from Unknown TLLI -> REJECT */
1213private function f_TC_rau_unknown(charstring id) runs on BSSGP_ConnHdlr {
Harald Welte04683d02018-02-16 22:43:45 +01001214 var RoutingAreaIdentificationV old_ra := f_random_RAI();
1215
Alexander Couzens4444b5a2019-08-13 13:25:32 +02001216 f_send_l3(ts_GMM_RAU_REQ(f_mi_get_lv(), GPRS_UPD_T_RA, old_ra, false, omit, omit));
Harald Welte04683d02018-02-16 22:43:45 +01001217 alt {
Pau Espin Pedrolce571b52019-11-08 18:32:28 +01001218 [] BSSGP[0].receive(tr_GMM_RAU_REJECT('0a'O)) { /* gmm cause: implicitly detached */
Harald Welte04683d02018-02-16 22:43:45 +01001219 setverdict(pass);
1220 }
1221 /* FIXME: Expect XID RESET? */
Alexander Couzens0e510e62018-07-28 23:06:00 +02001222 [] BSSGP[0].receive { repeat; }
Harald Welte04683d02018-02-16 22:43:45 +01001223 }
1224}
1225testcase TC_rau_unknown() runs on test_CT {
1226 var BSSGP_ConnHdlr vc_conn;
1227 f_init();
1228 f_sleep(1.0);
Alexander Couzens51114d12018-07-31 18:41:56 +02001229 vc_conn := f_start_handler(refers(f_TC_rau_unknown), testcasename(), g_gb, 11);
Harald Welte04683d02018-02-16 22:43:45 +01001230 vc_conn.done;
Pau Espin Pedrolce0d6152019-08-27 19:07:27 +02001231 f_cleanup();
Harald Welte04683d02018-02-16 22:43:45 +01001232}
1233
Harald Welte91636de2018-02-17 10:16:14 +01001234private function f_TC_attach_rau(charstring id) runs on BSSGP_ConnHdlr {
Harald Welte91636de2018-02-17 10:16:14 +01001235 /* first perform regular attach */
1236 f_TC_attach(id);
1237
Alexander Couzens5dce90d2018-07-31 03:16:37 +02001238 f_routing_area_update(g_pars.ra);
1239
Harald Welte91636de2018-02-17 10:16:14 +01001240}
1241testcase TC_attach_rau() runs on test_CT {
1242 var BSSGP_ConnHdlr vc_conn;
1243 f_init();
1244 f_sleep(1.0);
Alexander Couzens51114d12018-07-31 18:41:56 +02001245 vc_conn := f_start_handler(refers(f_TC_attach_rau), testcasename(), g_gb, 12);
Harald Welte91636de2018-02-17 10:16:14 +01001246 vc_conn.done;
Pau Espin Pedrolce0d6152019-08-27 19:07:27 +02001247 f_cleanup();
Harald Welte91636de2018-02-17 10:16:14 +01001248}
Harald Welte04683d02018-02-16 22:43:45 +01001249
Harald Welte6abb9fe2018-02-17 15:24:48 +01001250/* general GPRS DETACH helper */
Alexander Couzensb22e8ce2019-09-15 22:39:58 +02001251function f_detach_mo(BIT3 detach_type, boolean power_off, boolean expect_purge, integer ran_index := 0) runs on BSSGP_ConnHdlr {
Harald Welte955aa942019-05-03 01:29:29 +02001252 var PDU_L3_SGSN_MS l3_mt;
Harald Welte6abb9fe2018-02-17 15:24:48 +01001253 timer T := 5.0;
Alexander Couzensb22e8ce2019-09-15 22:39:58 +02001254 f_send_l3(ts_GMM_DET_REQ_MO(detach_type, power_off), ran_index);
Harald Welte6abb9fe2018-02-17 15:24:48 +01001255 if (expect_purge) {
1256 GSUP.receive(tr_GSUP_PURGE_MS_REQ(g_pars.imsi, OSMO_GSUP_CN_DOMAIN_PS));
1257 GSUP.send(ts_GSUP_PURGE_MS_RES(g_pars.imsi));
1258 }
1259 T.start;
1260 alt {
1261 [not expect_purge] GSUP.receive(tr_GSUP_PURGE_MS_REQ(?)) {
1262 setverdict(fail, "Unexpected GSUP PURGE MS for unregistered TLLI");
Daniel Willmannafce8662018-07-06 23:11:32 +02001263 mtc.stop;
Harald Welte6abb9fe2018-02-17 15:24:48 +01001264 }
Alexander Couzensb22e8ce2019-09-15 22:39:58 +02001265 [power_off] BSSGP[ran_index].receive(tr_GMM_DET_ACCEPT_MT) -> value l3_mt {
Harald Welte6abb9fe2018-02-17 15:24:48 +01001266 g_pars.ra := omit;
Alexander Couzens8e0fd462019-05-11 01:20:55 +02001267 setverdict(fail, "Unexpected DETACH ACCEPT in power-off DETACH");
Daniel Willmannafce8662018-07-06 23:11:32 +02001268 mtc.stop;
Harald Welte6abb9fe2018-02-17 15:24:48 +01001269 /* TODO: check if any PDP contexts are deactivated on network side? */
1270 }
1271 [power_off] T.timeout {
1272 setverdict(pass);
1273 }
Alexander Couzensb22e8ce2019-09-15 22:39:58 +02001274 [not power_off] BSSGP[ran_index].receive(tr_GMM_DET_ACCEPT_MT) -> value l3_mt {
Harald Welte6abb9fe2018-02-17 15:24:48 +01001275 g_pars.ra := omit;
1276 setverdict(pass);
1277 /* TODO: check if any PDP contexts are deactivated on network side? */
1278 }
Alexander Couzensb22e8ce2019-09-15 22:39:58 +02001279 [] BSSGP[ran_index].receive(PDU_L3_SGSN_MS:?) -> value l3_mt {
Alexander Couzens4630e742019-05-11 01:50:10 +02001280 if (power_off) {
1281 setverdict(fail, "Unexpected Layer 3 package received in power-off DETACH");
1282 } else {
1283 setverdict(fail, "Unexpected Layer 3 package received in normal DETACH");
1284 }
1285 mtc.stop;
1286 }
Alexander Couzensb22e8ce2019-09-15 22:39:58 +02001287 [] BSSGP[ran_index].receive { repeat; }
Harald Welte6abb9fe2018-02-17 15:24:48 +01001288 }
1289}
1290
1291/* IMSI DETACH (non-power-off) for unknown TLLI */
1292private function f_TC_detach_unknown_nopoweroff(charstring id) runs on BSSGP_ConnHdlr {
1293 f_detach_mo(c_GMM_DTT_MO_GPRS, false, false);
1294}
1295testcase TC_detach_unknown_nopoweroff() runs on test_CT {
1296 var BSSGP_ConnHdlr vc_conn;
1297 f_init();
1298 f_sleep(1.0);
Alexander Couzens51114d12018-07-31 18:41:56 +02001299 vc_conn := f_start_handler(refers(f_TC_detach_unknown_nopoweroff), testcasename(), g_gb, 13);
Harald Welte6abb9fe2018-02-17 15:24:48 +01001300 vc_conn.done;
Pau Espin Pedrolce0d6152019-08-27 19:07:27 +02001301 f_cleanup();
Harald Welte6abb9fe2018-02-17 15:24:48 +01001302}
1303
1304/* IMSI DETACH (power-off) for unknown TLLI */
1305private function f_TC_detach_unknown_poweroff(charstring id) runs on BSSGP_ConnHdlr {
1306 f_detach_mo(c_GMM_DTT_MO_GPRS, true, false);
1307}
1308testcase TC_detach_unknown_poweroff() runs on test_CT {
1309 var BSSGP_ConnHdlr vc_conn;
1310 f_init();
1311 f_sleep(1.0);
Alexander Couzens51114d12018-07-31 18:41:56 +02001312 vc_conn := f_start_handler(refers(f_TC_detach_unknown_poweroff), testcasename(), g_gb, 14);
Harald Welte6abb9fe2018-02-17 15:24:48 +01001313 vc_conn.done;
Pau Espin Pedrolce0d6152019-08-27 19:07:27 +02001314 f_cleanup();
Harald Welte6abb9fe2018-02-17 15:24:48 +01001315}
1316
1317/* IMSI DETACH (non-power-off) for known TLLI */
1318private function f_TC_detach_nopoweroff(charstring id) runs on BSSGP_ConnHdlr {
1319 /* first perform regular attach */
1320 f_TC_attach(id);
1321
1322 f_detach_mo(c_GMM_DTT_MO_GPRS, false, true);
1323}
1324testcase TC_detach_nopoweroff() runs on test_CT {
1325 var BSSGP_ConnHdlr vc_conn;
1326 f_init();
1327 f_sleep(1.0);
Alexander Couzens51114d12018-07-31 18:41:56 +02001328 vc_conn := f_start_handler(refers(f_TC_detach_nopoweroff), testcasename(), g_gb, 15);
Harald Welte6abb9fe2018-02-17 15:24:48 +01001329 vc_conn.done;
Pau Espin Pedrolce0d6152019-08-27 19:07:27 +02001330 f_cleanup();
Harald Welte6abb9fe2018-02-17 15:24:48 +01001331}
1332
1333/* IMSI DETACH (power-off) for known TLLI */
1334private function f_TC_detach_poweroff(charstring id) runs on BSSGP_ConnHdlr {
1335 /* first perform regular attach */
1336 f_TC_attach(id);
1337
1338 f_detach_mo(c_GMM_DTT_MO_GPRS, true, true);
1339}
1340testcase TC_detach_poweroff() runs on test_CT {
1341 var BSSGP_ConnHdlr vc_conn;
1342 f_init();
1343 f_sleep(1.0);
Alexander Couzens51114d12018-07-31 18:41:56 +02001344 vc_conn := f_start_handler(refers(f_TC_detach_poweroff), testcasename(), g_gb, 16);
Harald Welte6abb9fe2018-02-17 15:24:48 +01001345 vc_conn.done;
Pau Espin Pedrolce0d6152019-08-27 19:07:27 +02001346 f_cleanup();
Harald Welte6abb9fe2018-02-17 15:24:48 +01001347}
1348
Harald Welteeded9ad2018-02-17 20:57:34 +01001349type record PdpActPars {
Harald Welte822f9102018-02-18 20:39:06 +01001350 BIT3 tid, /* L3 Transaction ID */
1351 BIT4 nsapi, /* SNDCP NSAPI */
1352 BIT4 sapi, /* LLC SAPI */
1353 QoSV qos, /* QoS parameters */
1354 PDPAddressV addr, /* IP address */
1355 octetstring apn optional, /* APN name */
1356 ProtocolConfigOptionsV pco optional, /* protoco config opts */
1357 OCT1 exp_rej_cause optional, /* expected SM reject cause */
Harald Welte1d6ae932018-02-18 21:24:44 +01001358 OCT1 gtp_resp_cause, /* GTP response cause */
Harald Welte822f9102018-02-18 20:39:06 +01001359 OCT4 chg_id, /* GTP Charging Identifier */
Harald Welte6abb9fe2018-02-17 15:24:48 +01001360
Harald Welte822f9102018-02-18 20:39:06 +01001361 OCT4 ggsn_tei_c, /* GGSN TEI Control*/
1362 OCT4 ggsn_tei_u, /* GGSN TEI User */
1363 octetstring ggsn_ip_c, /* GGSN IP Control */
1364 octetstring ggsn_ip_u, /* GGSN IP User */
Pau Espin Pedroldc27e482018-07-10 14:02:49 +02001365 OCT1 ggsn_restart_ctr, /* GGSN Restart Counter */
Harald Welteeded9ad2018-02-17 20:57:34 +01001366
Harald Welte822f9102018-02-18 20:39:06 +01001367 OCT4 sgsn_tei_c optional, /* SGSN TEI Control */
1368 OCT4 sgsn_tei_u optional, /* SGSN TEI User */
1369 octetstring sgsn_ip_c optional, /* SGSN IP Control */
1370 octetstring sgsn_ip_u optional /* SGSN IP USer */
Harald Welteeded9ad2018-02-17 20:57:34 +01001371};
1372
Harald Welte5b5ca1b2018-02-18 21:25:03 +01001373
1374private function f_process_gtp_ctx_act_req(inout PdpActPars apars, PDU_GTPC gtpc) runs on BSSGP_ConnHdlr {
1375 var GTPC_PDUs gtpc_rx := gtpc.gtpc_pdu;
1376 apars.sgsn_tei_c := gtpc_rx.createPDPContextRequest.teidControlPlane.teidControlPlane;
1377 apars.sgsn_tei_u := gtpc_rx.createPDPContextRequest.teidDataI.teidDataI;
1378 apars.sgsn_ip_c := gtpc_rx.createPDPContextRequest.sgsn_addr_signalling.addressf;
1379 apars.sgsn_ip_u := gtpc_rx.createPDPContextRequest.sgsn_addr_traffic.addressf;
1380 f_gtp_register_teid(apars.ggsn_tei_c);
1381 f_gtp_register_teid(apars.ggsn_tei_u);
1382}
1383
Alexander Couzensb1ce1182019-09-15 22:43:40 +02001384function f_pdp_ctx_act(inout PdpActPars apars, boolean send_recovery := false, integer ran_index := 0)
Harald Weltef7191672019-05-02 20:37:23 +02001385runs on BSSGP_ConnHdlr {
Harald Welteeded9ad2018-02-17 20:57:34 +01001386 var boolean exp_rej := ispresent(apars.exp_rej_cause);
1387 var Gtp1cUnitdata g_ud;
Pau Espin Pedrol94013452018-07-17 15:50:21 +02001388 var template Recovery_gtpc recovery := omit;
1389
1390 if (send_recovery) {
1391 recovery := ts_Recovery(apars.ggsn_restart_ctr);
1392 }
Harald Welteeded9ad2018-02-17 20:57:34 +01001393
Alexander Couzens4444b5a2019-08-13 13:25:32 +02001394 f_send_l3(ts_SM_ACT_PDP_REQ(apars.tid, apars.nsapi, apars.sapi, apars.qos, apars.addr,
Alexander Couzensb1ce1182019-09-15 22:43:40 +02001395 apars.apn, apars.pco), ran_index);
Harald Welte5b5ca1b2018-02-18 21:25:03 +01001396 GTP.receive(tr_GTPC_MsgType(?, createPDPContextRequest, ?)) -> value g_ud {
1397 f_process_gtp_ctx_act_req(apars, g_ud.gtpc);
1398 var integer seq_nr := oct2int(g_ud.gtpc.opt_part.sequenceNumber);
1399 GTP.send(ts_GTPC_CreatePdpResp(g_ud.peer, seq_nr,
1400 apars.sgsn_tei_c, apars.gtp_resp_cause,
1401 apars.ggsn_tei_c, apars.ggsn_tei_u,
1402 apars.nsapi,
Pau Espin Pedrol94013452018-07-17 15:50:21 +02001403 apars.ggsn_ip_c, apars.ggsn_ip_u, apars.chg_id,
1404 omit, recovery));
Harald Welteeded9ad2018-02-17 20:57:34 +01001405 }
1406 alt {
Alexander Couzensb1ce1182019-09-15 22:43:40 +02001407 [exp_rej] BSSGP[ran_index].receive(tr_SM_ACT_PDP_REJ(apars.tid, apars.exp_rej_cause)) {
Harald Welteeded9ad2018-02-17 20:57:34 +01001408 setverdict(pass);
1409 }
Alexander Couzensb1ce1182019-09-15 22:43:40 +02001410 [exp_rej] BSSGP[ran_index].receive(tr_SM_ACT_PDP_ACCEPT) {
Harald Welteeded9ad2018-02-17 20:57:34 +01001411 setverdict(fail, "Unexpected PDP CTX ACT ACC");
Daniel Willmannafce8662018-07-06 23:11:32 +02001412 mtc.stop;
Harald Welteeded9ad2018-02-17 20:57:34 +01001413 }
Alexander Couzensb1ce1182019-09-15 22:43:40 +02001414 [not exp_rej] BSSGP[ran_index].receive(tr_SM_ACT_PDP_REJ(apars.tid, ?)) {
Harald Welteeded9ad2018-02-17 20:57:34 +01001415 setverdict(fail, "Unexpected PDP CTX ACT FAIL");
Daniel Willmannafce8662018-07-06 23:11:32 +02001416 mtc.stop;
Harald Welteeded9ad2018-02-17 20:57:34 +01001417 }
Alexander Couzensb1ce1182019-09-15 22:43:40 +02001418 [not exp_rej] BSSGP[ran_index].receive(tr_SM_ACT_PDP_REJ(apars.tid, ?)) {
Harald Weltef7191672019-05-02 20:37:23 +02001419 setverdict(fail, "Unexpected PDP CTX ACT FAIL");
1420 mtc.stop;
1421 }
Alexander Couzensb1ce1182019-09-15 22:43:40 +02001422 [not exp_rej] BSSGP[ran_index].receive(tr_SM_ACT_PDP_ACCEPT(apars.tid, apars.sapi)) {
Harald Welteeded9ad2018-02-17 20:57:34 +01001423 setverdict(pass);
1424 }
Alexander Couzensb1ce1182019-09-15 22:43:40 +02001425 [] as_xid(apars, ran_index);
Harald Welteeded9ad2018-02-17 20:57:34 +01001426 }
1427}
1428
Alexander Couzensb1ce1182019-09-15 22:43:40 +02001429function f_pdp_ctx_deact_mo(inout PdpActPars apars, OCT1 cause, integer ran_index := 0)
Harald Weltef7191672019-05-02 20:37:23 +02001430runs on BSSGP_ConnHdlr {
Harald Welte6f203162018-02-18 22:04:55 +01001431 var boolean exp_rej := ispresent(apars.exp_rej_cause);
1432 var Gtp1cUnitdata g_ud;
1433
Alexander Couzensb1ce1182019-09-15 22:43:40 +02001434 f_send_l3(ts_SM_DEACT_PDP_REQ_MO(apars.tid, cause, false, omit), ran_index);
Harald Welte6f203162018-02-18 22:04:55 +01001435 GTP.receive(tr_GTPC_MsgType(?, deletePDPContextRequest, apars.ggsn_tei_c)) -> value g_ud {
1436 var integer seq_nr := oct2int(g_ud.gtpc.opt_part.sequenceNumber);
Alexander Couzensb1ce1182019-09-15 22:43:40 +02001437 BSSGP[ran_index].clear;
Harald Welte6f203162018-02-18 22:04:55 +01001438 GTP.send(ts_GTPC_DeletePdpResp(g_ud.peer, seq_nr, apars.sgsn_tei_c, '7F'O));
1439 }
1440 alt {
Alexander Couzensb1ce1182019-09-15 22:43:40 +02001441 [] BSSGP[ran_index].receive(tr_SM_DEACT_PDP_ACCEPT_MT(apars.tid)) {
Harald Welte6f203162018-02-18 22:04:55 +01001442 setverdict(pass);
1443 }
Alexander Couzensb1ce1182019-09-15 22:43:40 +02001444 [] as_xid(apars, ran_index);
Harald Welte6f203162018-02-18 22:04:55 +01001445 }
1446}
1447
Alexander Couzensb1ce1182019-09-15 22:43:40 +02001448function f_pdp_ctx_deact_mt(inout PdpActPars apars, boolean error_ind := false, integer ran_index := 0)
Harald Weltef7191672019-05-02 20:37:23 +02001449runs on BSSGP_ConnHdlr {
Harald Welte57b9b7f2018-02-18 22:28:13 +01001450 var Gtp1cUnitdata g_ud;
1451 var integer seq_nr := 23;
1452 var GtpPeer peer := valueof(ts_GtpPeerC(apars.sgsn_ip_c));
1453
Alexander Couzensb1ce1182019-09-15 22:43:40 +02001454 BSSGP[ran_index].clear;
Pau Espin Pedrol482dde62018-07-18 13:47:42 +02001455 if (error_ind) {
1456 GTP.send(ts_GTPU_ErrorIndication(peer, 0 /* seq */, apars.ggsn_tei_u, apars.ggsn_ip_u));
1457 } else {
1458 GTP.send(ts_GTPC_DeletePDP(peer, seq_nr, apars.sgsn_tei_c, apars.nsapi, '1'B));
1459 }
Alexander Couzens5e71c142018-08-07 17:21:24 +02001460
1461 timer T := 5.0;
1462 T.start;
1463
Pau Espin Pedrol482dde62018-07-18 13:47:42 +02001464 alt {
Alexander Couzensb1ce1182019-09-15 22:43:40 +02001465 [] BSSGP[ran_index].receive(tr_SM_DEACT_PDP_REQ_MT(apars.tid, ?, true)) {
1466 f_send_l3(ts_SM_DEACT_PDP_ACCEPT_MO(apars.tid), ran_index);
Harald Welte57b9b7f2018-02-18 22:28:13 +01001467 }
Alexander Couzens5e71c142018-08-07 17:21:24 +02001468 [not error_ind] GTP.receive(tr_GTPC_MsgType(?, deletePDPContextResponse, apars.ggsn_tei_c)) {
1469 repeat;
1470 }
1471 [] T.timeout {
1472 setverdict(fail, "Waiting for SM_DEACT_PDP_REQ_MT");
1473 }
Harald Welte57b9b7f2018-02-18 22:28:13 +01001474 }
1475}
1476
Harald Welte6f203162018-02-18 22:04:55 +01001477
Harald Welteeded9ad2018-02-17 20:57:34 +01001478/* Table 10.5.156/3GPP TS 24.008 */
1479template (value) QoSV t_QosDefault := {
1480 reliabilityClass := '011'B, /* unacknowledged GTP+LLC, acknowledged RLC */
1481 delayClass := '100'B, /* best effort */
1482 spare1 := '00'B,
1483 precedenceClass := '010'B, /* normal */
1484 spare2 := '0'B,
1485 peakThroughput := '0000'B, /* subscribed */
1486 meanThroughput := '00000'B, /* subscribed */
1487 spare3 := '000'B,
1488 deliverErroneusSDU := omit,
1489 deliveryOrder := omit,
1490 trafficClass := omit,
1491 maxSDUSize := omit,
1492 maxBitrateUplink := omit,
1493 maxBitrateDownlink := omit,
1494 sduErrorRatio := omit,
1495 residualBER := omit,
1496 trafficHandlingPriority := omit,
1497 transferDelay := omit,
1498 guaranteedBitRateUplink := omit,
1499 guaranteedBitRateDownlink := omit,
1500 sourceStatisticsDescriptor := omit,
1501 signallingIndication := omit,
1502 spare4 := omit,
1503 maxBitrateDownlinkExt := omit,
1504 guaranteedBitRateDownlinkExt := omit,
1505 maxBitrateUplinkExt := omit,
1506 guaranteedBitRateUplinkExt := omit,
1507 maxBitrateDownlinkExt2 := omit,
1508 guaranteedBitRateDownlinkExt2 := omit,
1509 maxBitrateUplinkExt2 := omit,
1510 guaranteedBitRateUplinkExt2 := omit
1511}
1512
1513/* 10.5.6.4 / 3GPP TS 24.008 */
1514template (value) PDPAddressV t_AddrIPv4dyn := {
1515 pdpTypeOrg := '0001'B, /* IETF */
1516 spare := '0000'B,
1517 pdpTypeNum := '21'O, /* IPv4 */
1518 addressInfo := omit
1519}
1520template (value) PDPAddressV t_AddrIPv6dyn := {
1521 pdpTypeOrg := '0001'B, /* IETF */
1522 spare := '0000'B,
1523 pdpTypeNum := '53'O, /* IPv6 */
1524 addressInfo := omit
1525}
1526
Harald Welte37692d82018-02-18 15:21:34 +01001527template (value) PdpActPars t_PdpActPars(charstring ggsn_ip) := {
Harald Welteeded9ad2018-02-17 20:57:34 +01001528 tid := '000'B,
1529 nsapi := '0101'B, /* < 5 are reserved */
1530 sapi := '0011'B, /* 3/5/9/11 */
1531 qos := t_QosDefault,
1532 addr := t_AddrIPv4dyn,
1533 apn := omit,
1534 pco := omit,
1535 exp_rej_cause := omit,
Harald Welte1d6ae932018-02-18 21:24:44 +01001536 gtp_resp_cause := int2oct(128, 1),
1537 chg_id := f_rnd_octstring(4),
Harald Welteeded9ad2018-02-17 20:57:34 +01001538
1539 /* FIXME: make below dynamic !! */
Harald Welte1d6ae932018-02-18 21:24:44 +01001540 ggsn_tei_c := f_rnd_octstring(4),
1541 ggsn_tei_u := f_rnd_octstring(4),
Harald Welte37692d82018-02-18 15:21:34 +01001542 ggsn_ip_c := f_inet_addr(ggsn_ip),
1543 ggsn_ip_u := f_inet_addr(ggsn_ip),
Pau Espin Pedroldc27e482018-07-10 14:02:49 +02001544 ggsn_restart_ctr := int2oct(2, 1),
Harald Welteeded9ad2018-02-17 20:57:34 +01001545
Harald Welteeded9ad2018-02-17 20:57:34 +01001546 sgsn_tei_c := omit,
Harald Weltef8af5d62018-02-18 15:06:42 +01001547 sgsn_tei_u := omit,
1548 sgsn_ip_c := omit,
1549 sgsn_ip_u := omit
Harald Welteeded9ad2018-02-17 20:57:34 +01001550}
1551
Harald Welte37692d82018-02-18 15:21:34 +01001552template (value) GtpPeer ts_GtpPeerU(octetstring ip) := {
1553 connId := 1,
1554 remName := f_inet_ntoa(ip),
1555 remPort := GTP1U_PORT
1556}
1557
1558template (value) GtpPeer ts_GtpPeerC(octetstring ip) := {
1559 connId := 1,
1560 remName := f_inet_ntoa(ip),
1561 remPort := GTP1C_PORT
1562}
1563
1564private function f_gtpu_send(inout PdpActPars apars, octetstring payload) runs on BSSGP_ConnHdlr {
1565 var GtpPeer peer := valueof(ts_GtpPeerU(apars.sgsn_ip_u));
1566 GTP.send(ts_GTP1U_GPDU(peer, 0 /*seq*/, apars.sgsn_tei_u, payload));
1567}
1568
Alexander Couzensb1ce1182019-09-15 22:43:40 +02001569private altstep as_xid(PdpActPars apars, integer ran_index := 0) runs on BSSGP_ConnHdlr {
1570 [] BSSGP[ran_index].receive(tr_LLC_XID_MT_CMD(?, apars.sapi)) {
Harald Welte37692d82018-02-18 15:21:34 +01001571 repeat;
1572 }
1573}
1574
1575template PDU_SN tr_SN_UD(template BIT4 nsapi, template octetstring payload) := {
1576 pDU_SN_UNITDATA := {
1577 nsapi := nsapi,
1578 moreBit := ?,
1579 snPduType := '1'B,
1580 firstSegmentIndicator := ?,
1581 spareBit := ?,
1582 pcomp := ?,
1583 dcomp := ?,
1584 npduNumber := ?,
1585 segmentNumber := ?,
1586 npduNumberContinued := ?,
1587 dataSegmentSnUnitdataPdu := payload
1588 }
1589}
1590
1591/* simple case: single segment, no compression */
1592template (value) PDU_SN ts_SN_UD(BIT4 nsapi, octetstring payload) := {
1593 pDU_SN_UNITDATA := {
1594 nsapi := nsapi,
1595 moreBit := '0'B,
1596 snPduType := '1'B,
1597 firstSegmentIndicator := '1'B,
1598 spareBit := '0'B,
1599 pcomp := '0000'B,
1600 dcomp := '0000'B,
1601 npduNumber := '0000'B,
1602 segmentNumber := '0000'B,
1603 npduNumberContinued := '00'O,
1604 dataSegmentSnUnitdataPdu := payload
1605 }
1606}
1607
1608/* Transceive given 'payload' as MT message from GTP -> OsmoSGSN -> Gb */
Harald Weltea5c71cd2020-06-17 22:12:04 +02001609private function f_gtpu_xceive_mt(inout PdpActPars apars, octetstring payload, integer ran_index := 0, boolean expect_fwd := true)
Harald Weltef7191672019-05-02 20:37:23 +02001610runs on BSSGP_ConnHdlr {
Harald Weltea5c71cd2020-06-17 22:12:04 +02001611 timer T := 5.0;
Harald Welte37692d82018-02-18 15:21:34 +01001612 /* Send PDU via GTP from our simulated GGSN to the SGSN */
1613 f_gtpu_send(apars, payload);
Harald Weltea5c71cd2020-06-17 22:12:04 +02001614 T.start;
Harald Welte37692d82018-02-18 15:21:34 +01001615 /* Expect PDU via BSSGP/LLC on simulated PCU from SGSN */
1616 alt {
Alexander Couzensb1ce1182019-09-15 22:43:40 +02001617 [] as_xid(apars, ran_index);
1618 //[] BSSGP[ran_index].receive(tr_BD_SNDCP(apars.sapi, tr_SN_UD(apars.nsapi, payload)));
Harald Weltea5c71cd2020-06-17 22:12:04 +02001619 [expect_fwd] BSSGP[ran_index].receive(tr_SN_UD(apars.nsapi, payload));
1620 [expect_fwd] T.timeout {
1621 setverdict(fail, "Timeout waiting for GTP-U to appear on BSSGP");
1622 mtc.stop;
1623 }
1624 [not expect_fwd] BSSGP[ran_index].receive(tr_SN_UD(apars.nsapi, payload)) {
1625 setverdict(fail, "GTP-U forwarded to BSSGP but not expected")
1626 mtc.stop;
1627 }
1628 [not expect_fwd] T.timeout {}
Harald Welte37692d82018-02-18 15:21:34 +01001629 }
1630}
1631
Harald Welte64d6b512020-06-17 16:42:00 +02001632/* Transceive given 'payload' as MO message from Gb -> OsmoSGSN -> GTP */
Pau Espin Pedrol7c052162021-02-12 17:43:35 +01001633private function f_gtpu_xceive_mo(inout PdpActPars apars, octetstring payload, integer ran_index := 0, uint9_t n_u := 0)
Harald Weltef7191672019-05-02 20:37:23 +02001634runs on BSSGP_ConnHdlr {
Harald Welte37692d82018-02-18 15:21:34 +01001635 /* Send PDU via SNDCP/LLC/BSSGP/NS via simulated MS/PCU to the SGSN */
1636 var GtpPeer peer := valueof(ts_GtpPeerU(apars.sgsn_ip_u));
1637 var PDU_SN sndcp := valueof(ts_SN_UD(apars.nsapi, payload));
Pau Espin Pedrol7c052162021-02-12 17:43:35 +01001638 BSSGP[ran_index].send(ts_LLC_UI(enc_PDU_SN(sndcp), apars.sapi, '0'B, n_u));
Harald Welte37692d82018-02-18 15:21:34 +01001639 /* Expect PDU via GTP from SGSN on simulated GGSN */
1640 alt {
1641 [] GTP.receive(tr_GTPU_GPDU(peer, apars.ggsn_tei_u, payload));
1642 }
1643}
1644
Harald Welteeded9ad2018-02-17 20:57:34 +01001645private function f_TC_attach_pdp_act(charstring id) runs on BSSGP_ConnHdlr {
Harald Welte37692d82018-02-18 15:21:34 +01001646 var PdpActPars apars := valueof(t_PdpActPars(mp_ggsn_ip));
Harald Welteeded9ad2018-02-17 20:57:34 +01001647
1648 /* first perform regular attach */
1649 f_TC_attach(id);
1650
1651 f_pdp_ctx_act(apars);
1652}
1653testcase TC_attach_pdp_act() runs on test_CT {
1654 var BSSGP_ConnHdlr vc_conn;
1655 f_init();
Alexander Couzens51114d12018-07-31 18:41:56 +02001656 vc_conn := f_start_handler(refers(f_TC_attach_pdp_act), testcasename(), g_gb, 17);
Harald Welteeded9ad2018-02-17 20:57:34 +01001657 vc_conn.done;
Pau Espin Pedrolce0d6152019-08-27 19:07:27 +02001658 f_cleanup();
Harald Welteeded9ad2018-02-17 20:57:34 +01001659}
Harald Welteb2124b22018-02-16 22:26:56 +01001660
Harald Welte835b15f2018-02-18 14:39:11 +01001661/* PDP Context activation for not-attached subscriber; expect fail */
1662private function f_TC_pdp_act_unattached(charstring id) runs on BSSGP_ConnHdlr {
Harald Welte37692d82018-02-18 15:21:34 +01001663 var PdpActPars apars := valueof(t_PdpActPars(mp_ggsn_ip));
Alexander Couzens4444b5a2019-08-13 13:25:32 +02001664 f_send_l3(ts_SM_ACT_PDP_REQ(apars.tid, apars.nsapi, apars.sapi, apars.qos, apars.addr,
Harald Welte835b15f2018-02-18 14:39:11 +01001665 apars.apn, apars.pco));
1666 alt {
1667 /* We might want toalso actually expect a PDPC CTX ACT REJ? */
Harald Welte955aa942019-05-03 01:29:29 +02001668 [] BSSGP[0].receive(tr_GMM_DET_REQ_MT(?, ?)) {
Harald Welte835b15f2018-02-18 14:39:11 +01001669 setverdict(pass);
1670 }
1671 [] GTP.receive(tr_GTPC_MsgType(?, createPDPContextRequest, ?)) {
1672 setverdict(fail, "Unexpected GTP PDP CTX ACT");
Daniel Willmannafce8662018-07-06 23:11:32 +02001673 mtc.stop;
Harald Welte835b15f2018-02-18 14:39:11 +01001674 }
Harald Welte955aa942019-05-03 01:29:29 +02001675 [] BSSGP[0].receive(tr_SM_ACT_PDP_ACCEPT(?, ?)) {
Harald Welte835b15f2018-02-18 14:39:11 +01001676 setverdict(fail, "Unexpected SM PDP CTX ACT ACK");
Daniel Willmannafce8662018-07-06 23:11:32 +02001677 mtc.stop;
Harald Welte835b15f2018-02-18 14:39:11 +01001678 }
Alexander Couzens0e510e62018-07-28 23:06:00 +02001679 [] BSSGP[0].receive { repeat; }
Harald Welte835b15f2018-02-18 14:39:11 +01001680 }
1681}
1682testcase TC_pdp_act_unattached() runs on test_CT {
1683 var BSSGP_ConnHdlr vc_conn;
1684 f_init();
Alexander Couzens51114d12018-07-31 18:41:56 +02001685 vc_conn := f_start_handler(refers(f_TC_pdp_act_unattached), testcasename(), g_gb, 18);
Harald Welte835b15f2018-02-18 14:39:11 +01001686 vc_conn.done;
Pau Espin Pedrolce0d6152019-08-27 19:07:27 +02001687 f_cleanup();
Harald Welte835b15f2018-02-18 14:39:11 +01001688}
1689
Harald Welte37692d82018-02-18 15:21:34 +01001690/* ATTACH + PDP CTX ACT + user plane traffic */
1691private function f_TC_attach_pdp_act_user(charstring id) runs on BSSGP_ConnHdlr {
1692 var PdpActPars apars := valueof(t_PdpActPars(mp_ggsn_ip));
1693
1694 /* first perform regular attach */
1695 f_TC_attach(id);
1696 /* then activate PDP context */
1697 f_pdp_ctx_act(apars);
1698 /* then transceive a downlink PDU */
1699 f_gtpu_xceive_mt(apars, f_rnd_octstring(100));
1700 f_gtpu_xceive_mo(apars, f_rnd_octstring(200));
1701}
1702testcase TC_attach_pdp_act_user() runs on test_CT {
1703 var BSSGP_ConnHdlr vc_conn;
1704 f_init();
Alexander Couzens51114d12018-07-31 18:41:56 +02001705 vc_conn := f_start_handler(refers(f_TC_attach_pdp_act_user), testcasename(), g_gb, 19);
Harald Welte37692d82018-02-18 15:21:34 +01001706 vc_conn.done;
Pau Espin Pedrolce0d6152019-08-27 19:07:27 +02001707 f_cleanup();
Harald Welte37692d82018-02-18 15:21:34 +01001708}
1709
Harald Welte5b5ca1b2018-02-18 21:25:03 +01001710/* ATTACH + PDP CTX ACT; reject from GGSN */
1711private function f_TC_attach_pdp_act_ggsn_reject(charstring id) runs on BSSGP_ConnHdlr {
1712 var PdpActPars apars := valueof(t_PdpActPars(mp_ggsn_ip));
1713
1714 apars.gtp_resp_cause := int2oct(199, 1); /* no resources available */
1715 apars.exp_rej_cause := '1a'O; /* insufficient resources */
1716
1717 /* first perform regular attach */
1718 f_TC_attach(id);
1719 /* then activate PDP context */
1720 f_pdp_ctx_act(apars);
1721}
1722testcase TC_attach_pdp_act_ggsn_reject() runs on test_CT {
1723 var BSSGP_ConnHdlr vc_conn;
1724 f_init();
Alexander Couzens51114d12018-07-31 18:41:56 +02001725 vc_conn := f_start_handler(refers(f_TC_attach_pdp_act_ggsn_reject), testcasename(), g_gb, 20);
Harald Welte5b5ca1b2018-02-18 21:25:03 +01001726 vc_conn.done;
Pau Espin Pedrolce0d6152019-08-27 19:07:27 +02001727 f_cleanup();
Harald Welte5b5ca1b2018-02-18 21:25:03 +01001728}
Harald Welte835b15f2018-02-18 14:39:11 +01001729
Harald Welte6f203162018-02-18 22:04:55 +01001730/* ATTACH + PDP CTX ACT + user plane traffic + PDP CTX DEACT in MO direction */
1731private function f_TC_attach_pdp_act_user_deact_mo(charstring id) runs on BSSGP_ConnHdlr {
1732 var PdpActPars apars := valueof(t_PdpActPars(mp_ggsn_ip));
1733
1734 /* first perform regular attach */
1735 f_TC_attach(id);
1736 /* then activate PDP context */
1737 f_pdp_ctx_act(apars);
1738 /* then transceive a downlink PDU */
1739 f_gtpu_xceive_mt(apars, f_rnd_octstring(100));
1740 f_gtpu_xceive_mo(apars, f_rnd_octstring(200));
1741
1742 f_pdp_ctx_deact_mo(apars, '00'O);
1743}
1744testcase TC_attach_pdp_act_user_deact_mo() runs on test_CT {
1745 var BSSGP_ConnHdlr vc_conn;
1746 f_init();
Alexander Couzens51114d12018-07-31 18:41:56 +02001747 vc_conn := f_start_handler(refers(f_TC_attach_pdp_act_user_deact_mo), testcasename(), g_gb, 21);
Harald Welte6f203162018-02-18 22:04:55 +01001748 vc_conn.done;
Pau Espin Pedrolce0d6152019-08-27 19:07:27 +02001749 f_cleanup();
Harald Welte6f203162018-02-18 22:04:55 +01001750}
1751
Harald Welte57b9b7f2018-02-18 22:28:13 +01001752/* ATTACH + PDP CTX ACT + user plane traffic + PDP CTX DEACT in MT direction */
1753private function f_TC_attach_pdp_act_user_deact_mt(charstring id) runs on BSSGP_ConnHdlr {
1754 var PdpActPars apars := valueof(t_PdpActPars(mp_ggsn_ip));
1755
1756 /* first perform regular attach */
1757 f_TC_attach(id);
1758 /* then activate PDP context */
1759 f_pdp_ctx_act(apars);
1760 /* then transceive a downlink PDU */
1761 f_gtpu_xceive_mt(apars, f_rnd_octstring(100));
1762 f_gtpu_xceive_mo(apars, f_rnd_octstring(200));
1763
Pau Espin Pedrol482dde62018-07-18 13:47:42 +02001764 f_pdp_ctx_deact_mt(apars, false);
Harald Welte57b9b7f2018-02-18 22:28:13 +01001765}
1766testcase TC_attach_pdp_act_user_deact_mt() runs on test_CT {
1767 var BSSGP_ConnHdlr vc_conn;
1768 f_init();
Alexander Couzens51114d12018-07-31 18:41:56 +02001769 vc_conn := f_start_handler(refers(f_TC_attach_pdp_act_user_deact_mt), testcasename(), g_gb, 22);
Harald Welte57b9b7f2018-02-18 22:28:13 +01001770 vc_conn.done;
Pau Espin Pedrolce0d6152019-08-27 19:07:27 +02001771 f_cleanup();
Harald Welte57b9b7f2018-02-18 22:28:13 +01001772}
1773
Pau Espin Pedrol2a3302a2019-08-15 16:01:20 +02001774/* Test MS sending a duplicate Deact PDP Ctx (OS#3956). */
1775private function f_TC_attach_pdp_act_deact_dup(charstring id) runs on BSSGP_ConnHdlr {
1776 var PdpActPars apars := valueof(t_PdpActPars(mp_ggsn_ip));
1777 var Gtp1cUnitdata g_ud;
1778 var integer i;
1779 var OCT1 cause_regular_deact := '24'O;
1780
1781 /* first perform regular attach + PDP context act */
1782 f_TC_attach(id);
1783 f_pdp_ctx_act(apars);
1784
1785 f_send_l3_gmm_llc(ts_SM_DEACT_PDP_REQ_MO(apars.tid, cause_regular_deact, false, omit), 0);
1786 f_send_l3_gmm_llc(ts_SM_DEACT_PDP_REQ_MO(apars.tid, cause_regular_deact, false, omit), 0);
1787
1788 for (i := 0; i < 2; i := i+1) {
1789 GTP.receive(tr_GTPC_MsgType(?, deletePDPContextRequest, apars.ggsn_tei_c)) -> value g_ud {
1790 var integer seq_nr := oct2int(g_ud.gtpc.opt_part.sequenceNumber);
1791 log("Received deletePDPContextResponse " & int2str(i) & ", seq_nr=" & int2str(seq_nr));
1792 GTP.send(ts_GTPC_DeletePdpResp(g_ud.peer, seq_nr, apars.sgsn_tei_c, '7F'O));
1793 }
1794 }
1795
1796 alt {
1797 [] BSSGP[0].receive(tr_SM_DEACT_PDP_ACCEPT_MT(apars.tid)) {
1798 setverdict(pass);
1799 }
1800 [] as_xid(apars, 0);
1801 }
1802
1803 /* Make sure second DeactPdpAccept is sent: */
1804 timer T := 2.0;
1805 T.start;
1806 alt {
1807 [] BSSGP[0].receive(tr_SM_DEACT_PDP_ACCEPT_MT(apars.tid)) {
1808 setverdict(fail, "Second SM_DEACT_PDP_ACCEPT_MT received");
1809 }
1810 [] T.timeout {
1811 setverdict(pass);
1812 }
1813 }
1814
1815 setverdict(pass);
1816}
1817testcase TC_attach_pdp_act_deact_dup() runs on test_CT {
1818 var BSSGP_ConnHdlr vc_conn;
1819 f_init();
1820 vc_conn := f_start_handler(refers(f_TC_attach_pdp_act_deact_dup), testcasename(), g_gb, 46);
1821 vc_conn.done;
Pau Espin Pedrolce0d6152019-08-27 19:07:27 +02001822 f_cleanup();
Pau Espin Pedrol2a3302a2019-08-15 16:01:20 +02001823}
1824
Alexander Couzens187ad5d2018-05-02 19:31:10 +02001825/* ATTACH + ATTACH (2nd) */
1826private function f_TC_attach_forget_tlli_attach(charstring id) runs on BSSGP_ConnHdlr {
1827 g_pars.t_guard := 5.0;
1828
1829 /* first perform regular attach */
1830 f_TC_attach(id);
1831
1832 /* second to perform regular attach */
1833 f_TC_attach(id);
1834}
1835
1836
1837testcase TC_attach_second_attempt() runs on test_CT {
1838 var BSSGP_ConnHdlr vc_conn;
1839 f_init();
Alexander Couzens51114d12018-07-31 18:41:56 +02001840 vc_conn := f_start_handler(refers(f_TC_attach_forget_tlli_attach), testcasename(), g_gb, 22);
Alexander Couzens187ad5d2018-05-02 19:31:10 +02001841 vc_conn.done;
Pau Espin Pedrolce0d6152019-08-27 19:07:27 +02001842 f_cleanup();
Alexander Couzens187ad5d2018-05-02 19:31:10 +02001843}
Harald Welte57b9b7f2018-02-18 22:28:13 +01001844
Pau Espin Pedrolfcec9142019-08-28 17:33:46 +02001845private function f_TC_attach_echo_timeout(charstring id) runs on BSSGP_ConnHdlr {
1846 var Gtp1cUnitdata g_ud;
1847 var PdpActPars apars := valueof(t_PdpActPars(mp_ggsn_ip));
1848 var integer seq_nr;
1849
1850 /* first perform regular attach */
1851 f_TC_attach(id);
1852 /* then activate PDP context */
1853 f_pdp_ctx_act(apars);
1854
1855 /* Wait to receive first echo request and send initial Restart counter */
1856 GTP.receive(tr_GTPC_MsgType(?, echoRequest, ?)) -> value g_ud {
1857 BSSGP[0].clear;
1858 seq_nr := oct2int(g_ud.gtpc.opt_part.sequenceNumber);
1859 GTP.send(ts_GTPC_PONG(g_ud.peer, seq_nr, apars.ggsn_restart_ctr));
1860 f_sleep(int2float(mp_echo_interval)); /* wait until around next echo is expected */
1861 }
1862
1863 /* At some point next echo request not answered will timeout and SGSN
1864 should drop the pdp ctx. Around T3 (3secs) * 6 (+ extra, a lot due to OS#4178): */
1865 timer T := 3.0 * 6.0 + 16.0;
1866 T.start;
1867 alt {
1868 [] BSSGP[0].receive(tr_SM_DEACT_PDP_REQ_MT(apars.tid, ?, true)) {
1869 f_send_l3_gmm_llc(ts_SM_DEACT_PDP_ACCEPT_MO(apars.tid));
1870 setverdict(pass);
1871 }
1872 [] GTP.receive(tr_GTPC_MsgType(?, deletePDPContextRequest, apars.ggsn_tei_c)) -> value g_ud {
1873 /* SGSN currently doesn't send this message because it expects GGSN to be non-reachable anyway */
1874 seq_nr := oct2int(g_ud.gtpc.opt_part.sequenceNumber);
1875 log("Received deletePDPContextRequest seq_nr=" & int2str(seq_nr));
1876 GTP.send(ts_GTPC_DeletePdpResp(g_ud.peer, seq_nr, apars.sgsn_tei_c, '7F'O));
1877 repeat;
1878 }
1879 [] GTP.receive(tr_GTPC_MsgType(?, echoRequest, ?)) -> value g_ud {
1880 seq_nr := oct2int(g_ud.gtpc.opt_part.sequenceNumber);
1881 log("Received EchoRequest seq_nr=" & int2str(seq_nr));
1882 repeat;
1883 }
1884 [] T.timeout {
1885 setverdict(fail, "BSSGP DeactPdpReq not received");
1886 mtc.stop;
1887 }
1888 [] as_xid(apars);
1889 }
1890 T.stop
1891
1892 setverdict(pass);
1893}
1894/* ATTACH + trigger Recovery procedure through CreatePdpResp */
1895testcase TC_attach_echo_timeout() runs on test_CT {
1896 var BSSGP_ConnHdlr vc_conn;
1897 g_use_echo := true;
1898 f_init();
1899 vc_conn := f_start_handler(refers(f_TC_attach_echo_timeout), testcasename(), g_gb, 67, 50.0);
1900 vc_conn.done;
1901 g_use_echo := false;
Pau Espin Pedrolce0d6152019-08-27 19:07:27 +02001902 f_cleanup();
Pau Espin Pedrolfcec9142019-08-28 17:33:46 +02001903}
1904
Pau Espin Pedrol94013452018-07-17 15:50:21 +02001905private function f_TC_attach_restart_ctr_echo(charstring id) runs on BSSGP_ConnHdlr {
Pau Espin Pedroldc27e482018-07-10 14:02:49 +02001906 var Gtp1cUnitdata g_ud;
1907 var PdpActPars apars := valueof(t_PdpActPars(mp_ggsn_ip));
1908
1909 /* first perform regular attach */
1910 f_TC_attach(id);
1911 /* Activate a pdp context against the GGSN */
1912 f_pdp_ctx_act(apars);
1913 /* Wait to receive first echo request and send initial Restart counter */
1914 GTP.receive(tr_GTPC_MsgType(?, echoRequest, ?)) -> value g_ud {
1915 var integer seq_nr := oct2int(g_ud.gtpc.opt_part.sequenceNumber);
1916 GTP.send(ts_GTPC_PONG(g_ud.peer, seq_nr, apars.ggsn_restart_ctr));
1917 }
1918 /* Wait to receive second echo request and send incremented Restart
1919 counter. This will fake a restarted GGSN, and pdp ctx allocated
1920 should be released by SGSN */
1921 apars.ggsn_restart_ctr := int2oct(oct2int(apars.ggsn_restart_ctr) + 1, 1);
1922 GTP.receive(tr_GTPC_MsgType(?, echoRequest, ?)) -> value g_ud {
1923 var integer seq_nr := oct2int(g_ud.gtpc.opt_part.sequenceNumber);
1924 GTP.send(ts_GTPC_PONG(g_ud.peer, seq_nr, apars.ggsn_restart_ctr));
1925 }
1926 var OCT1 cause_network_failure := int2oct(38, 1)
1927 alt {
Harald Welte955aa942019-05-03 01:29:29 +02001928 [] BSSGP[0].receive(tr_SM_DEACT_PDP_REQ_MT(apars.tid, cause_network_failure, true)) {
Alexander Couzens4444b5a2019-08-13 13:25:32 +02001929 f_send_l3(ts_SM_DEACT_PDP_ACCEPT_MO(apars.tid));
Pau Espin Pedroldc27e482018-07-10 14:02:49 +02001930 setverdict(pass);
1931 }
1932 [] as_xid(apars);
1933 }
1934 setverdict(pass);
1935}
Pau Espin Pedrol94013452018-07-17 15:50:21 +02001936/* ATTACH + trigger Recovery procedure through EchoResp */
1937testcase TC_attach_restart_ctr_echo() runs on test_CT {
Pau Espin Pedroldc27e482018-07-10 14:02:49 +02001938 var BSSGP_ConnHdlr vc_conn;
1939 g_use_echo := true
1940 f_init();
Alexander Couzens51114d12018-07-31 18:41:56 +02001941 vc_conn := f_start_handler(refers(f_TC_attach_restart_ctr_echo), testcasename(), g_gb, 23, 30.0);
Pau Espin Pedroldc27e482018-07-10 14:02:49 +02001942 vc_conn.done;
1943 g_use_echo := false
Pau Espin Pedrolce0d6152019-08-27 19:07:27 +02001944 f_cleanup();
Pau Espin Pedroldc27e482018-07-10 14:02:49 +02001945}
1946
Pau Espin Pedrol94013452018-07-17 15:50:21 +02001947private function f_TC_attach_restart_ctr_create(charstring id) runs on BSSGP_ConnHdlr {
1948 var Gtp1cUnitdata g_ud;
1949 var PdpActPars apars := valueof(t_PdpActPars(mp_ggsn_ip));
1950 var integer seq_nr := 23;
1951 var GtpPeer peer;
1952 /* first perform regular attach */
1953 f_TC_attach(id);
1954
1955 /* Use this CTX ACT to send initial Restart counter to SGSN. */
1956 apars.gtp_resp_cause := int2oct(199, 1); /* no resources available */
1957 apars.exp_rej_cause := '1a'O; /* insufficient resources */
1958 f_pdp_ctx_act(apars, true);
1959
1960 /* Increment restart_ctr. This will fake a restarted GGSN when CreatePdpResp is
1961/* received. */
1962 apars.ggsn_restart_ctr := int2oct(oct2int(apars.ggsn_restart_ctr) + 1, 1);
1963
1964 /* FIXME: Once we can easily handle different pdp ctx simultaneously, it
1965 would be great to have an active pdp context here before triggering
1966 Recovery, and making sure the the DEACT request is sent by the SGSN.
1967 */
1968
1969 /* Activate a pdp context against the GGSN, send incremented Recovery
1970 IE. This should trigger the recovery path, but still this specific
1971 CTX activation should work. */
1972 apars.exp_rej_cause := omit; /* default value for tests */
1973 apars.gtp_resp_cause := int2oct(128, 1); /* default value for tests */
1974 f_pdp_ctx_act(apars, true);
1975
1976 setverdict(pass);
1977}
1978/* ATTACH + trigger Recovery procedure through CreatePdpResp */
1979testcase TC_attach_restart_ctr_create() runs on test_CT {
1980 var BSSGP_ConnHdlr vc_conn;
1981 f_init();
Alexander Couzens51114d12018-07-31 18:41:56 +02001982 vc_conn := f_start_handler(refers(f_TC_attach_restart_ctr_create), testcasename(), g_gb, 24, 30.0);
Pau Espin Pedrol94013452018-07-17 15:50:21 +02001983 vc_conn.done;
Pau Espin Pedrolce0d6152019-08-27 19:07:27 +02001984 f_cleanup();
Pau Espin Pedrol94013452018-07-17 15:50:21 +02001985}
1986
Pau Espin Pedrol72edc8a2018-07-16 15:10:08 +02001987/* ATTACH + PDP CTX ACT + user plane traffic + PDP CTX DEACT in MT direction + trigger T3395 */
1988private function f_TC_attach_pdp_act_deact_mt_t3395_expire(charstring id) runs on BSSGP_ConnHdlr {
1989 var PdpActPars apars := valueof(t_PdpActPars(mp_ggsn_ip));
1990 var integer seq_nr := 23;
1991 var GtpPeer peer;
1992 var integer i;
1993
1994 /* first perform regular attach */
1995 f_TC_attach(id);
1996 /* then activate PDP context */
1997 f_pdp_ctx_act(apars);
1998
Alexander Couzens0e510e62018-07-28 23:06:00 +02001999 BSSGP[0].clear;
Pau Espin Pedrol72edc8a2018-07-16 15:10:08 +02002000 peer := valueof(ts_GtpPeerC(apars.sgsn_ip_c));
2001 GTP.send(ts_GTPC_DeletePDP(peer, seq_nr, apars.sgsn_tei_c, apars.nsapi, '1'B));
2002
2003 for (i := 0; i < 5; i := i+1) {
2004 alt {
Harald Welte955aa942019-05-03 01:29:29 +02002005 [] BSSGP[0].receive(tr_SM_DEACT_PDP_REQ_MT(apars.tid, ?, true)) {}
Pau Espin Pedrol72edc8a2018-07-16 15:10:08 +02002006 [] as_xid(apars);
2007 }
2008 }
2009
2010 GTP.receive(tr_GTPC_MsgType(?, deletePDPContextResponse, apars.ggsn_tei_c)) {}
2011
Alexander Couzens4444b5a2019-08-13 13:25:32 +02002012 f_send_l3(ts_SM_DEACT_PDP_ACCEPT_MO(apars.tid));
Pau Espin Pedrol72edc8a2018-07-16 15:10:08 +02002013 setverdict(pass);
2014}
2015testcase TC_attach_pdp_act_deact_mt_t3395_expire() runs on test_CT {
2016 var BSSGP_ConnHdlr vc_conn;
2017 f_init();
2018 f_sleep(1.0);
Alexander Couzens51114d12018-07-31 18:41:56 +02002019 vc_conn := f_start_handler(refers(f_TC_attach_pdp_act_deact_mt_t3395_expire), testcasename(), g_gb, 25, 60.0);
Pau Espin Pedrol72edc8a2018-07-16 15:10:08 +02002020 vc_conn.done;
Pau Espin Pedrolce0d6152019-08-27 19:07:27 +02002021 f_cleanup();
Pau Espin Pedrol72edc8a2018-07-16 15:10:08 +02002022}
2023
Pau Espin Pedrole6f071f2019-05-29 13:02:42 +02002024/* ATTACH + PDP CTX ACT dropped + retrans */
2025private function f_TC_attach_pdp_act_deact_gtp_retrans(charstring id) runs on BSSGP_ConnHdlr {
2026 var PdpActPars apars := valueof(t_PdpActPars(mp_ggsn_ip));
2027 var Gtp1cUnitdata g_ud_first, g_ud_second;
2028 /* first perform regular attach */
2029 f_TC_attach(id);
2030
2031 /* then activate PDP context on the Gb side */
2032 f_send_l3_gmm_llc(ts_SM_ACT_PDP_REQ(apars.tid, apars.nsapi, apars.sapi, apars.qos, apars.addr,
2033 apars.apn, apars.pco), 0);
2034
2035 GTP.receive(tr_GTPC_MsgType(?, createPDPContextRequest, ?)) -> value g_ud_first {}
2036 log("First createPDPContextRequest received, dropping & waiting for retransmission");
2037 GTP.receive(tr_GTPC_MsgType(?, createPDPContextRequest, ?)) -> value g_ud_second {
2038 if (g_ud_first != g_ud_second) {
2039 setverdict(fail, "Retransmitted GTP message createPDPContextRequest is different from original one!");
2040 mtc.stop;
2041 }
2042 f_process_gtp_ctx_act_req(apars, g_ud_second.gtpc);
2043 var integer seq_nr := oct2int(g_ud_second.gtpc.opt_part.sequenceNumber);
2044 GTP.send(ts_GTPC_CreatePdpResp(g_ud_second.peer, seq_nr,
2045 apars.sgsn_tei_c, apars.gtp_resp_cause,
2046 apars.ggsn_tei_c, apars.ggsn_tei_u,
2047 apars.nsapi,
2048 apars.ggsn_ip_c, apars.ggsn_ip_u, apars.chg_id,
2049 omit, omit));
2050 }
Harald Welte955aa942019-05-03 01:29:29 +02002051 BSSGP[0].receive(tr_SM_ACT_PDP_ACCEPT) {}
Pau Espin Pedrole6f071f2019-05-29 13:02:42 +02002052
2053 /* Now the same with Deact */
2054 f_send_l3_gmm_llc(ts_SM_DEACT_PDP_REQ_MO(apars.tid, '00'O, false, omit), 0);
2055 GTP.receive(tr_GTPC_MsgType(?, deletePDPContextRequest, apars.ggsn_tei_c)) -> value g_ud_first {}
2056 log("First deletePDPContextRequest received, dropping & waiting for retransmission");
2057 GTP.receive(tr_GTPC_MsgType(?, deletePDPContextRequest, apars.ggsn_tei_c)) -> value g_ud_second {
2058 if (g_ud_first != g_ud_second) {
2059 setverdict(fail, "Retransmitted GTP message deletePDPContextRequest is different from original one!");
2060 mtc.stop;
2061 }
2062 var integer seq_nr := oct2int(g_ud_second.gtpc.opt_part.sequenceNumber);
2063 BSSGP[0].clear;
2064 GTP.send(ts_GTPC_DeletePdpResp(g_ud_second.peer, seq_nr, apars.sgsn_tei_c, '7F'O));
2065 }
2066 alt {
Harald Welte955aa942019-05-03 01:29:29 +02002067 [] BSSGP[0].receive(tr_SM_DEACT_PDP_ACCEPT_MT(apars.tid)) {
Pau Espin Pedrole6f071f2019-05-29 13:02:42 +02002068 setverdict(pass);
2069 }
2070 [] as_xid(apars, 0);
2071 }
2072
2073 setverdict(pass);
2074}
2075testcase TC_attach_pdp_act_deact_gtp_retrans() runs on test_CT {
2076 var BSSGP_ConnHdlr vc_conn;
2077 f_init();
2078 vc_conn := f_start_handler(refers(f_TC_attach_pdp_act_deact_gtp_retrans), testcasename(), g_gb, 27);
2079 vc_conn.done;
Pau Espin Pedrolce0d6152019-08-27 19:07:27 +02002080 f_cleanup();
Pau Espin Pedrole6f071f2019-05-29 13:02:42 +02002081}
2082
2083/* Test that SGSN GTP response retransmit queue works fine */
2084private function f_TC_attach_pdp_act_deact_gtp_retrans_resp(charstring id) runs on BSSGP_ConnHdlr {
2085 var PdpActPars apars := valueof(t_PdpActPars(mp_ggsn_ip));
2086 var integer seq_nr := 23;
2087 var Gtp1cUnitdata g_ud_first, g_ud_second;
2088 var template Gtp1cUnitdata g_delete_req;
2089 /* first perform regular attach + PDP context act */
2090 f_TC_attach(id);
2091 f_pdp_ctx_act(apars);
2092
2093 /* Now perform an MT DeleteCtxReq and emulate GGSN didn't receive response and sends a duplicated DeleteCtxReq */
2094 BSSGP[0].clear;
2095 var GtpPeer peer := valueof(ts_GtpPeerC(apars.sgsn_ip_c));
2096 g_delete_req := ts_GTPC_DeletePDP(peer, seq_nr, apars.sgsn_tei_c, apars.nsapi, '1'B);
2097 GTP.send(g_delete_req);
2098 alt {
Harald Welte955aa942019-05-03 01:29:29 +02002099 [] BSSGP[0].receive(tr_SM_DEACT_PDP_REQ_MT(apars.tid, ?, true)) {
Pau Espin Pedrole6f071f2019-05-29 13:02:42 +02002100 f_send_l3_gmm_llc(ts_SM_DEACT_PDP_ACCEPT_MO(apars.tid), 0);
2101 }
2102 [] as_xid(apars, 0);
2103 }
2104 GTP.receive(tr_GTPC_MsgType(?, deletePDPContextResponse, apars.ggsn_tei_c)) -> value g_ud_first {
2105 if (g_ud_first.gtpc.gtpc_pdu.deletePDPContextResponse.cause.causevalue != '80'O) {
2106 setverdict(fail, "Received deletePDPContextResponse cause is not 'Request accepted'");
2107 mtc.stop;
2108 }
2109 };
2110
2111 /* Send duplicate DeleteCtxReq */
2112 log("First deletePDPContextResponse received, dropping & retransmitting retransmission of deletePDPContextRequest");
2113 GTP.send(g_delete_req);
2114 GTP.receive(tr_GTPC_MsgType(?, deletePDPContextResponse, apars.ggsn_tei_c)) -> value g_ud_second {
2115 if (g_ud_first != g_ud_second) {
2116 setverdict(fail, "Retransmitted GTP message deletePDPContextResponse is different from original one!");
2117 mtc.stop;
2118 }
2119 }
2120
2121 /* Let's send now a new DeleteCtxReq (increased seq_nr) to make sure it
2122 * is handled differently by SGSN (expect "non-existent" cause) */
2123 g_delete_req := ts_GTPC_DeletePDP(peer, seq_nr + 1, apars.sgsn_tei_c, apars.nsapi, '1'B);
2124 GTP.send(g_delete_req);
2125 /* Response with cause "non-existent" must be sent with TEID 0 according to specs */
2126 GTP.receive(tr_GTPC_MsgType(?, deletePDPContextResponse, '00000000'O)) -> value g_ud_second {
2127 if (g_ud_second.gtpc.gtpc_pdu.deletePDPContextResponse.cause.causevalue != 'C0'O) {
2128 setverdict(fail, "Received deletePDPContextResponse cause is not 'Non-existent'");
2129 mtc.stop;
2130 }
2131 }
2132
2133 setverdict(pass);
2134}
2135testcase TC_attach_pdp_act_deact_gtp_retrans_resp() runs on test_CT {
2136 var BSSGP_ConnHdlr vc_conn;
2137 f_init();
2138 vc_conn := f_start_handler(refers(f_TC_attach_pdp_act_deact_gtp_retrans_resp), testcasename(), g_gb, 28);
2139 vc_conn.done;
Pau Espin Pedrolce0d6152019-08-27 19:07:27 +02002140 f_cleanup();
Pau Espin Pedrole6f071f2019-05-29 13:02:42 +02002141}
2142
Alexander Couzens5e307b42018-05-22 18:12:20 +02002143private function f_TC_hlr_location_cancel_request_update(charstring id) runs on BSSGP_ConnHdlr {
2144 /* MS: perform regular attach */
2145 f_TC_attach(id);
2146
2147 /* HLR: cancel the location request */
2148 GSUP.send(ts_GSUP_CL_REQ(g_pars.imsi, OSMO_GSUP_CANCEL_TYPE_UPDATE));
2149 GSUP.receive(tr_GSUP_CL_RES(g_pars.imsi));
Alexander Couzens5e307b42018-05-22 18:12:20 +02002150
2151 /* ensure no Detach Request got received */
2152 timer T := 5.0;
2153 T.start;
2154 alt {
Harald Welte955aa942019-05-03 01:29:29 +02002155 [] BSSGP[0].receive(tr_GMM_DET_REQ_MT(*, *, *)) {
Alexander Couzens5e307b42018-05-22 18:12:20 +02002156 T.stop;
2157 setverdict(fail, "Unexpected GMM Detach Request");
Daniel Willmannafce8662018-07-06 23:11:32 +02002158 mtc.stop;
Alexander Couzens5e307b42018-05-22 18:12:20 +02002159 }
2160 [] T.timeout {
2161 setverdict(pass);
Daniel Willmannafce8662018-07-06 23:11:32 +02002162 mtc.stop;
Alexander Couzens5e307b42018-05-22 18:12:20 +02002163 }
Alexander Couzens0e510e62018-07-28 23:06:00 +02002164 [] BSSGP[0].receive {
Alexander Couzens5e307b42018-05-22 18:12:20 +02002165 repeat;
2166 }
2167 }
2168}
2169
Pau Espin Pedrol482dde62018-07-18 13:47:42 +02002170/* ATTACH + PDP CTX ACT + user plane traffic + ERROR IND in MT direction */
2171private function f_TC_attach_pdp_act_user_error_ind_ggsn(charstring id) runs on BSSGP_ConnHdlr {
2172 var PdpActPars apars := valueof(t_PdpActPars(mp_ggsn_ip));
2173
2174 /* first perform regular attach */
2175 f_TC_attach(id);
2176 /* then activate PDP context */
2177 f_pdp_ctx_act(apars);
2178 /* then transceive a downlink PDU */
2179 f_gtpu_xceive_mo(apars, f_rnd_octstring(200));
2180
2181 /* Send Error indication as response from upload PDU and expect deact towards MS */
2182 f_pdp_ctx_deact_mt(apars, true);
2183}
2184testcase TC_attach_pdp_act_user_error_ind_ggsn() runs on test_CT {
2185 var BSSGP_ConnHdlr vc_conn;
2186 f_init();
Alexander Couzens51114d12018-07-31 18:41:56 +02002187 vc_conn := f_start_handler(refers(f_TC_attach_pdp_act_user_error_ind_ggsn), testcasename(), g_gb, 26);
Pau Espin Pedrol482dde62018-07-18 13:47:42 +02002188 vc_conn.done;
Pau Espin Pedrolce0d6152019-08-27 19:07:27 +02002189 f_cleanup();
Pau Espin Pedrol482dde62018-07-18 13:47:42 +02002190}
2191
Alexander Couzens5e307b42018-05-22 18:12:20 +02002192testcase TC_hlr_location_cancel_request_update() runs on test_CT {
2193 /* MS <-> SGSN: GMM Attach
2194 * HLR -> SGSN: Cancel Location Request
2195 * HLR <- SGSN: Cancel Location Ack
2196 */
2197 var BSSGP_ConnHdlr vc_conn;
2198 f_init();
2199 f_sleep(1.0);
Alexander Couzens51114d12018-07-31 18:41:56 +02002200 vc_conn := f_start_handler(refers(f_TC_hlr_location_cancel_request_update), testcasename(), g_gb, 31);
Alexander Couzens5e307b42018-05-22 18:12:20 +02002201 vc_conn.done;
Pau Espin Pedrolce0d6152019-08-27 19:07:27 +02002202 f_cleanup();
Alexander Couzens5e307b42018-05-22 18:12:20 +02002203}
2204
2205
Alexander Couzensc87967a2018-05-22 16:09:54 +02002206private function f_TC_hlr_location_cancel_request_withdraw(charstring id) runs on BSSGP_ConnHdlr {
2207 /* MS: perform regular attach */
2208 f_TC_attach(id);
2209
2210 /* HLR: cancel the location request */
2211 GSUP.send(ts_GSUP_CL_REQ(g_pars.imsi, OSMO_GSUP_CANCEL_TYPE_WITHDRAW));
2212 GSUP.receive(tr_GSUP_CL_RES(g_pars.imsi));
2213 GSUP.send(ts_GSUP_UL_RES(g_pars.imsi));
2214
2215 /* MS: receive a Detach Request */
Harald Welte955aa942019-05-03 01:29:29 +02002216 BSSGP[0].receive(tr_GMM_DET_REQ_MT(c_GMM_DTT_MT_IMSI_DETACH, ?, ?));
Alexander Couzens4444b5a2019-08-13 13:25:32 +02002217 f_send_l3(ts_GMM_DET_ACCEPT_MO);
Alexander Couzensc87967a2018-05-22 16:09:54 +02002218
2219 setverdict(pass);
2220}
2221
2222testcase TC_hlr_location_cancel_request_withdraw() runs on test_CT {
2223 /* MS <-> SGSN: GMM Attach
2224 * HLR -> SGSN: Cancel Location Request
2225 * HLR <- SGSN: Cancel Location Ack
2226 * MS <- SGSN: Detach Request
2227 * SGSN-> MS: Detach Complete
2228 */
2229 var BSSGP_ConnHdlr vc_conn;
2230 f_init();
2231 f_sleep(1.0);
Alexander Couzens51114d12018-07-31 18:41:56 +02002232 vc_conn := f_start_handler(refers(f_TC_hlr_location_cancel_request_withdraw), testcasename(), g_gb, 29);
Alexander Couzensc87967a2018-05-22 16:09:54 +02002233 vc_conn.done;
Pau Espin Pedrolce0d6152019-08-27 19:07:27 +02002234 f_cleanup();
Alexander Couzensc87967a2018-05-22 16:09:54 +02002235}
2236
2237
Alexander Couzens6c47f292018-05-22 17:09:49 +02002238private function f_hlr_location_cancel_request_unknown_subscriber(
2239 charstring id,
2240 GSUP_CancelType canceltype) runs on BSSGP_ConnHdlr {
2241
2242 /* HLR: cancel the location request */
2243 GSUP.send(ts_GSUP_CL_REQ(g_pars.imsi, canceltype));
2244
2245 /* cause 2 = IMSI_UNKNOWN */
2246 GSUP.receive(tr_GSUP_CL_ERR(g_pars.imsi, 2));
2247
2248 setverdict(pass);
2249}
2250
2251private function f_TC_hlr_location_cancel_request_unknown_subscriber_withdraw(charstring id) runs on BSSGP_ConnHdlr {
Alexander Couzensace6fc62018-06-05 16:29:02 +02002252 f_hlr_location_cancel_request_unknown_subscriber(id, OSMO_GSUP_CANCEL_TYPE_WITHDRAW);
Alexander Couzens6c47f292018-05-22 17:09:49 +02002253}
2254
2255testcase TC_hlr_location_cancel_request_unknown_subscriber_withdraw() runs on test_CT {
2256 /* HLR -> SGSN: Cancel Location Request
2257 * HLR <- SGSN: Cancel Location Error
2258 */
2259
2260 var BSSGP_ConnHdlr vc_conn;
2261 f_init();
2262 f_sleep(1.0);
Alexander Couzens51114d12018-07-31 18:41:56 +02002263 vc_conn := f_start_handler(refers(f_TC_hlr_location_cancel_request_unknown_subscriber_withdraw), testcasename(), g_gb, 30);
Alexander Couzens6c47f292018-05-22 17:09:49 +02002264 vc_conn.done;
Pau Espin Pedrolce0d6152019-08-27 19:07:27 +02002265 f_cleanup();
Alexander Couzens6c47f292018-05-22 17:09:49 +02002266}
2267
2268private function f_TC_hlr_location_cancel_request_unknown_subscriber_update(charstring id) runs on BSSGP_ConnHdlr {
Alexander Couzensace6fc62018-06-05 16:29:02 +02002269 f_hlr_location_cancel_request_unknown_subscriber(id, OSMO_GSUP_CANCEL_TYPE_WITHDRAW);
Alexander Couzens6c47f292018-05-22 17:09:49 +02002270}
2271
2272testcase TC_hlr_location_cancel_request_unknown_subscriber_update() runs on test_CT {
2273 /* HLR -> SGSN: Cancel Location Request
2274 * HLR <- SGSN: Cancel Location Error
2275 */
2276
2277 var BSSGP_ConnHdlr vc_conn;
2278 f_init();
2279 f_sleep(1.0);
Alexander Couzens51114d12018-07-31 18:41:56 +02002280 vc_conn := f_start_handler(refers(f_TC_hlr_location_cancel_request_unknown_subscriber_update), testcasename(), g_gb, 30);
Alexander Couzens6c47f292018-05-22 17:09:49 +02002281 vc_conn.done;
Pau Espin Pedrolce0d6152019-08-27 19:07:27 +02002282 f_cleanup();
Alexander Couzens6c47f292018-05-22 17:09:49 +02002283}
2284
Alexander Couzens49bb4b42018-06-05 16:28:36 +02002285private function f_TC_attach_detach_check_subscriber_list(charstring id) runs on BSSGP_ConnHdlr {
2286 f_TC_attach(id);
2287 f_detach_mo(c_GMM_DTT_MO_GPRS, true, true);
2288}
Alexander Couzens6c47f292018-05-22 17:09:49 +02002289
Alexander Couzens49bb4b42018-06-05 16:28:36 +02002290testcase TC_attach_detach_check_subscriber_list() runs on test_CT {
2291 /* MS <-> SGSN: Attach
2292 * MS -> SGSN: Detach Req (Power off)
2293 * VTY -> SGSN: Check if MS is NOT in subscriber cache
2294 */
2295 var BSSGP_ConnHdlr vc_conn;
2296 var integer id := 33;
2297 var charstring imsi := hex2str(f_gen_imsi(id));
2298
2299 f_init();
Alexander Couzens51114d12018-07-31 18:41:56 +02002300 vc_conn := f_start_handler(refers(f_TC_attach_detach_check_subscriber_list), testcasename(), g_gb, id);
Alexander Couzens49bb4b42018-06-05 16:28:36 +02002301 vc_conn.done;
2302
2303 f_vty_transceive_not_match(SGSNVTY, "show subscriber cache", pattern "* IMSI: {imsi}*");
Pau Espin Pedrolce0d6152019-08-27 19:07:27 +02002304 f_cleanup();
Alexander Couzens49bb4b42018-06-05 16:28:36 +02002305}
Alexander Couzens6c47f292018-05-22 17:09:49 +02002306
Alexander Couzens667dd7f2018-06-12 16:24:01 +02002307/* Attempt an attach, but loose the Identification Request (IMEI) */
2308private function f_TC_attach_no_imei_response(charstring id) runs on BSSGP_ConnHdlr {
2309 var integer count_req := 0;
Vadim Yanitskiy98bb2d52020-03-28 00:57:21 +07002310 var MobileIdentityLV mi;
Alexander Couzens667dd7f2018-06-12 16:24:01 +02002311
Alexander Couzens4444b5a2019-08-13 13:25:32 +02002312 f_send_l3(ts_GMM_ATTACH_REQ(f_mi_get_lv(), f_random_RAI(), true, false, omit, omit));
Alexander Couzens667dd7f2018-06-12 16:24:01 +02002313
2314 alt {
Harald Welte955aa942019-05-03 01:29:29 +02002315 [] BSSGP[0].receive(tr_GMM_ATTACH_REJECT(?)) {
Alexander Couzens667dd7f2018-06-12 16:24:01 +02002316 /* break */
2317 }
Harald Welte955aa942019-05-03 01:29:29 +02002318 [] BSSGP[0].receive(tr_GMM_ID_REQ('001'B)) {
Alexander Couzens667dd7f2018-06-12 16:24:01 +02002319 mi := valueof(ts_MI_IMSI_LV(g_pars.imsi));
Alexander Couzens4444b5a2019-08-13 13:25:32 +02002320 f_send_l3(ts_GMM_ID_RESP(mi));
Alexander Couzens667dd7f2018-06-12 16:24:01 +02002321 repeat;
2322 }
Harald Welte955aa942019-05-03 01:29:29 +02002323 [] BSSGP[0].receive(tr_GMM_ID_REQ('010'B)) {
Alexander Couzens667dd7f2018-06-12 16:24:01 +02002324 /* ignore ID REQ IMEI */
2325 count_req := count_req + 1;
2326 repeat;
2327 }
2328 }
2329 if (count_req != 5) {
2330 setverdict(fail, "Did not received GMM ID Request Type IMEI 5 times!");
Daniel Willmannafce8662018-07-06 23:11:32 +02002331 mtc.stop;
Alexander Couzens667dd7f2018-06-12 16:24:01 +02002332 }
2333 setverdict(pass);
2334}
2335
2336testcase TC_attach_no_imei_response() runs on test_CT {
2337 /* MS -> SGSN: Attach Request IMSI
2338 * MS <- SGSN: Identity Request IMSI (optional)
2339 * MS -> SGSN: Identity Response IMSI (optional)
2340 * MS <- SGSN: Identity Request IMEI
2341 * MS -x SGSN: no response
2342 * MS <- SGSN: re-send: Identity Request IMEI 4x
2343 * MS <- SGSN: Attach Reject
2344 */
2345 var BSSGP_ConnHdlr vc_conn;
2346 f_init();
2347 f_sleep(1.0);
Alexander Couzens51114d12018-07-31 18:41:56 +02002348 vc_conn := f_start_handler(refers(f_TC_attach_no_imei_response), testcasename(), g_gb, 32, 60.0);
Alexander Couzens667dd7f2018-06-12 16:24:01 +02002349 vc_conn.done;
Pau Espin Pedrolce0d6152019-08-27 19:07:27 +02002350 f_cleanup();
Alexander Couzens667dd7f2018-06-12 16:24:01 +02002351}
2352
Alexander Couzens53f20562018-06-12 16:24:12 +02002353/* Attempt an attach, but loose the Identification Request (IMSI) */
2354private function f_TC_attach_no_imsi_response(charstring id) runs on BSSGP_ConnHdlr {
2355 var integer count_req := 0;
Vadim Yanitskiy98bb2d52020-03-28 00:57:21 +07002356 var MobileIdentityLV mi;
Alexander Couzens53f20562018-06-12 16:24:12 +02002357
2358 /* set p_tmsi to use it in Attach Req via f_mi_get_lv() */
2359 g_pars.p_tmsi := 'c0000035'O;
2360
Alexander Couzens4444b5a2019-08-13 13:25:32 +02002361 f_send_l3(ts_GMM_ATTACH_REQ(f_mi_get_lv(), f_random_RAI(), true, false, omit, omit));
Alexander Couzens53f20562018-06-12 16:24:12 +02002362
2363 alt {
Harald Welte955aa942019-05-03 01:29:29 +02002364 [] BSSGP[0].receive(tr_GMM_ATTACH_REJECT(?)) {
Alexander Couzens53f20562018-06-12 16:24:12 +02002365 /* break */
2366 }
Harald Welte955aa942019-05-03 01:29:29 +02002367 [] BSSGP[0].receive(tr_GMM_ID_REQ('001'B)) {
Alexander Couzens53f20562018-06-12 16:24:12 +02002368 /* ignore ID REQ IMSI */
2369 count_req := count_req + 1;
2370 repeat;
2371 }
Harald Welte955aa942019-05-03 01:29:29 +02002372 [] BSSGP[0].receive(tr_GMM_ID_REQ('010'B)) {
Alexander Couzens53f20562018-06-12 16:24:12 +02002373 mi := valueof(ts_MI_IMEI_LV(g_pars.imei));
Alexander Couzens4444b5a2019-08-13 13:25:32 +02002374 f_send_l3(ts_GMM_ID_RESP(mi));
Alexander Couzens53f20562018-06-12 16:24:12 +02002375 repeat;
2376 }
2377 }
2378 if (count_req != 5) {
2379 setverdict(fail, "Did not received GMM ID Request Type IMSI 5 times!");
Daniel Willmannafce8662018-07-06 23:11:32 +02002380 mtc.stop;
Alexander Couzens53f20562018-06-12 16:24:12 +02002381 }
2382 setverdict(pass);
2383}
2384
2385testcase TC_attach_no_imsi_response() runs on test_CT {
2386 /* MS -> SGSN: Attach Request TMSI (unknown)
2387 * MS <- SGSN: Identity Request IMEI (optional)
2388 * MS -> SGSN: Identity Response IMEI (optional)
2389 * MS <- SGSN: Identity Request IMSI
2390 * MS -x SGSN: no response
2391 * MS <- SGSN: re-send: Identity Request IMSI 4x
2392 * MS <- SGSN: Attach Reject
2393 */
2394 var BSSGP_ConnHdlr vc_conn;
2395 f_init();
2396 f_sleep(1.0);
Alexander Couzens51114d12018-07-31 18:41:56 +02002397 vc_conn := f_start_handler(refers(f_TC_attach_no_imsi_response), testcasename(), g_gb, 35, 60.0);
Alexander Couzens53f20562018-06-12 16:24:12 +02002398 vc_conn.done;
Pau Espin Pedrolce0d6152019-08-27 19:07:27 +02002399 f_cleanup();
Alexander Couzens53f20562018-06-12 16:24:12 +02002400}
2401
Alexander Couzenscf818962018-06-05 18:00:00 +02002402private function f_sgsn_vty_destroy_subscriber_imsi(TELNETasp_PT pt, charstring imsi) {
2403 f_vty_transceive(pt, "update-subscriber imsi " & imsi & " destroy");
2404}
2405
2406testcase TC_attach_check_subscriber_list() runs on test_CT {
2407 /* MS <-> SGSN: Attach
2408 * VTY -> SGSN: Check if MS is in subscriber cache
2409 */
2410 var BSSGP_ConnHdlr vc_conn;
2411 var integer id := 34;
2412 var charstring imsi := hex2str(f_gen_imsi(id));
2413
2414 f_init();
2415 f_sleep(1.0);
Alexander Couzens51114d12018-07-31 18:41:56 +02002416 vc_conn := f_start_handler(refers(f_TC_attach), testcasename(), g_gb, id);
Alexander Couzenscf818962018-06-05 18:00:00 +02002417 vc_conn.done;
2418
2419 f_vty_transceive_match(SGSNVTY, "show subscriber cache", pattern "* IMSI: {imsi}*");
2420 f_sgsn_vty_destroy_subscriber_imsi(SGSNVTY, imsi);
Pau Espin Pedrolce0d6152019-08-27 19:07:27 +02002421 f_cleanup();
Alexander Couzenscf818962018-06-05 18:00:00 +02002422}
2423
Alexander Couzensf9858652018-06-07 16:14:53 +02002424private function f_TC_attach_closed_imsi_added(charstring id) runs on BSSGP_ConnHdlr {
2425 var RoutingAreaIdentificationV old_ra := f_random_RAI();
Harald Welte955aa942019-05-03 01:29:29 +02002426 var PDU_L3_SGSN_MS l3_mt;
Alexander Couzensf9858652018-06-07 16:14:53 +02002427
2428 /* unregister the old IMSI */
2429 f_bssgp_client_unregister(g_pars.imsi);
2430 /* Simulate a foreign IMSI */
Alexander Couzens03d12242018-08-07 16:13:52 +02002431 g_pars.imsi := '001010123456700'H;
Harald Welte5339b2e2020-10-04 22:52:56 +02002432 f_bssgp_client_register(g_pars.imsi, g_pars.tlli);
Alexander Couzensf9858652018-06-07 16:14:53 +02002433
2434 /* there is no auth */
2435 g_pars.net.expect_auth := false;
2436
Alexander Couzens4444b5a2019-08-13 13:25:32 +02002437 f_send_l3(ts_GMM_ATTACH_REQ(f_mi_get_lv(), old_ra, false, false, omit, omit));
Alexander Couzensf9858652018-06-07 16:14:53 +02002438 f_gmm_auth();
2439 alt {
Harald Welte955aa942019-05-03 01:29:29 +02002440 [] BSSGP[0].receive(tr_GMM_ATTACH_REJECT(?)) {
Alexander Couzensf9858652018-06-07 16:14:53 +02002441 setverdict(fail, "Received unexpected GMM Attach REJECT");
Daniel Willmannafce8662018-07-06 23:11:32 +02002442 mtc.stop;
Alexander Couzensf9858652018-06-07 16:14:53 +02002443 }
Harald Welte955aa942019-05-03 01:29:29 +02002444 [] BSSGP[0].receive(tr_GMM_ATTACH_ACCEPT(*, *, *)) -> value l3_mt {
2445 f_process_attach_accept(l3_mt.msgs.gprs_mm.attachAccept);
Alexander Couzens4444b5a2019-08-13 13:25:32 +02002446 f_send_l3(ts_GMM_ATTACH_COMPL);
Alexander Couzensf9858652018-06-07 16:14:53 +02002447 setverdict(pass);
2448 }
2449 }
2450}
Alexander Couzens03d12242018-08-07 16:13:52 +02002451
2452private function f_TC_attach_closed_add_vty(charstring id) runs on BSSGP_ConnHdlr {
2453
2454 f_TC_attach_closed_foreign(id);
2455 f_TC_attach_closed_imsi_added(id);
2456
2457}
2458
2459
Alexander Couzensf9858652018-06-07 16:14:53 +02002460testcase TC_attach_closed_add_vty() runs on test_CT {
2461 /* VTY-> SGSN: policy close
2462 * MS -> SGSN: Attach Request
2463 * MS <- SGSN: Identity Request IMSI
2464 * MS -> SGSN: Identity Response IMSI
2465 * MS <- SGSN: Attach Reject
2466 * VTY-> SGSN: policy imsi-acl add IMSI
2467 * MS -> SGSN: Attach Request
2468 * MS <- SGSN: Identity Request IMSI
2469 * MS -> SGSN: Identity Response IMSI
2470 * MS <- SGSN: Identity Request IMEI
2471 * MS -> SGSN: Identity Response IMEI
2472 * MS <- SGSN: Attach Accept
2473 */
2474 var BSSGP_ConnHdlr vc_conn;
2475 f_init();
2476 f_sleep(1.0);
2477 f_vty_config(SGSNVTY, "sgsn", "auth-policy closed");
2478 f_vty_config(SGSNVTY, "sgsn", "imsi-acl del 001010123456789");
Alexander Couzens03d12242018-08-07 16:13:52 +02002479 f_vty_config(SGSNVTY, "sgsn", "imsi-acl del 001010123456700");
2480 f_vty_config(SGSNVTY, "sgsn", "imsi-acl add 001010123456700");
Alexander Couzensf9858652018-06-07 16:14:53 +02002481 /* test with foreign IMSI: Must Reject */
Alexander Couzens03d12242018-08-07 16:13:52 +02002482 vc_conn := f_start_handler(refers(f_TC_attach_closed_add_vty), testcasename(), g_gb, 9);
Alexander Couzensf9858652018-06-07 16:14:53 +02002483 vc_conn.done;
Pau Espin Pedrolce0d6152019-08-27 19:07:27 +02002484 f_cleanup();
Alexander Couzensf9858652018-06-07 16:14:53 +02002485}
2486
Alexander Couzens0085bd72018-06-12 19:08:44 +02002487/* Attempt an attach, but never answer a Attach Complete */
2488private function f_TC_attach_check_complete_resend(charstring id) runs on BSSGP_ConnHdlr {
2489 var integer count_req := 0;
2490
Alexander Couzens4444b5a2019-08-13 13:25:32 +02002491 f_send_l3(ts_GMM_ATTACH_REQ(f_mi_get_lv(), f_random_RAI(), true, false, omit, omit));
Alexander Couzens0085bd72018-06-12 19:08:44 +02002492 f_gmm_auth();
Pau Espin Pedrol4b290a22019-09-10 19:49:41 +02002493 /* Expect SGSN to perform LU with HLR */
2494 f_gmm_gsup_lu_isd();
Alexander Couzens0085bd72018-06-12 19:08:44 +02002495
Alexander Couzensfa0a75f2018-08-07 15:45:04 +02002496 timer T := 10.0;
2497 T.start;
Alexander Couzens0085bd72018-06-12 19:08:44 +02002498 alt {
Alexander Couzensfa0a75f2018-08-07 15:45:04 +02002499 [] T.timeout {
Alexander Couzens0085bd72018-06-12 19:08:44 +02002500 /* break */
2501 }
Harald Welte955aa942019-05-03 01:29:29 +02002502 [] BSSGP[0].receive(tr_GMM_ATTACH_ACCEPT(*, *, *)) {
Alexander Couzens0085bd72018-06-12 19:08:44 +02002503 /* ignore */
2504 count_req := count_req + 1;
Alexander Couzensfa0a75f2018-08-07 15:45:04 +02002505 T.start;
Alexander Couzens0085bd72018-06-12 19:08:44 +02002506 repeat;
2507 }
2508 }
2509 if (count_req != 5) {
2510 setverdict(fail, "Did not received GMM Attach Complete.");
Daniel Willmannafce8662018-07-06 23:11:32 +02002511 mtc.stop;
Alexander Couzens0085bd72018-06-12 19:08:44 +02002512 }
2513 setverdict(pass);
2514}
2515
2516testcase TC_attach_check_complete_resend() runs on test_CT {
2517 /* MS -> SGSN: Attach Request IMSI
2518 * MS <- SGSN: Identity Request *
2519 * MS -> SGSN: Identity Response *
2520 * MS <- SGSN: Attach Complete 5x
2521 */
2522 var BSSGP_ConnHdlr vc_conn;
2523 f_init();
2524 f_sleep(1.0);
Alexander Couzens51114d12018-07-31 18:41:56 +02002525 vc_conn := f_start_handler(refers(f_TC_attach_check_complete_resend), testcasename(), g_gb, 36, 60.0);
Alexander Couzens0085bd72018-06-12 19:08:44 +02002526 vc_conn.done;
Pau Espin Pedrolce0d6152019-08-27 19:07:27 +02002527 f_cleanup();
Alexander Couzens0085bd72018-06-12 19:08:44 +02002528}
2529
Alexander Couzensbe76d9c2019-09-15 22:48:03 +02002530friend function f_routing_area_update(RoutingAreaIdentificationV ra, integer ran_index := 0) runs on BSSGP_ConnHdlr {
Harald Welte955aa942019-05-03 01:29:29 +02002531 var PDU_L3_SGSN_MS l3_mt;
Alexander Couzens5d56f522019-09-03 12:36:18 +02002532 var PDU_DTAP_PS_MT mt;
2533 var template OCT4 p_tmsi := omit;
Alexander Couzens5dce90d2018-07-31 03:16:37 +02002534
Alexander Couzensbe76d9c2019-09-15 22:48:03 +02002535 if (is_iu(ran_index)) {
Alexander Couzens5d56f522019-09-03 12:36:18 +02002536 p_tmsi := g_pars.p_tmsi;
2537 }
Alexander Couzens5dce90d2018-07-31 03:16:37 +02002538 /* then send RAU */
Alexander Couzensbe76d9c2019-09-15 22:48:03 +02002539 f_send_l3(ts_GMM_RAU_REQ(f_mi_get_lv(), GPRS_UPD_T_RA, g_pars.ra, false, omit, omit, p_tmsi), ran_index);
Alexander Couzens5dce90d2018-07-31 03:16:37 +02002540 alt {
Alexander Couzensbe76d9c2019-09-15 22:48:03 +02002541 [is_gb(ran_index)] BSSGP[ran_index].receive(tr_GMM_RAU_ACCEPT) -> value l3_mt {
2542 f_process_rau_accept(l3_mt.msgs.gprs_mm.routingAreaUpdateAccept, ran_index);
2543 f_send_l3(ts_GMM_RAU_COMPL, ran_index);
Alexander Couzens5dce90d2018-07-31 03:16:37 +02002544 setverdict(pass);
2545 }
Alexander Couzensbe76d9c2019-09-15 22:48:03 +02002546 [is_iu(ran_index)] BSSAP.receive(tr_PDU_DTAP_PS_MT(tr_GMM_RAU_ACCEPT)) -> value mt {
2547 f_process_rau_accept(mt.dtap.msgs.gprs_mm.routingAreaUpdateAccept, ran_index);
2548 f_send_l3(ts_GMM_RAU_COMPL, ran_index);
Alexander Couzens5d56f522019-09-03 12:36:18 +02002549 setverdict(pass);
2550 }
2551
Alexander Couzensbe76d9c2019-09-15 22:48:03 +02002552 [is_gb(ran_index)] BSSGP[ran_index].receive(tr_GMM_RAU_REJECT) {
Alexander Couzens5dce90d2018-07-31 03:16:37 +02002553 setverdict(fail, "Unexpected RAU Reject");
2554 mtc.stop;
2555 }
Alexander Couzensbe76d9c2019-09-15 22:48:03 +02002556 [is_iu(ran_index)] BSSAP.receive(tr_PDU_DTAP_PS_MT(tr_GMM_RAU_REJECT)) {
Alexander Couzens5d56f522019-09-03 12:36:18 +02002557 setverdict(fail, "Unexpected RAU Reject");
2558 mtc.stop;
2559 }
2560
Alexander Couzensbe76d9c2019-09-15 22:48:03 +02002561 [is_iu(ran_index)] BSSAP.receive(tr_RANAP_SecurityModeCmd(uia_algs := ?, uia_key := oct2bit(g_pars.vec.ik),
Alexander Couzens5d56f522019-09-03 12:36:18 +02002562 key_sts := ?)) {
2563 var IntegrityProtectionAlgorithm uia_chosen := 0; /* 0 = standard_UMTS_integrity_algorithm_UIA1 */
2564 BSSAP.send(ts_RANAP_SecurityModeComplete(uia_chosen));
Alexander Couzensed61ae82019-09-15 23:18:08 +02002565 BSSAP.receive(tr_RANAP_CommonId(imsi_hex2oct(g_pars.imsi)))
Daniel Willmann1c116112020-01-22 17:48:31 +01002566 repeat;
Alexander Couzens5d56f522019-09-03 12:36:18 +02002567 }
Alexander Couzensbe76d9c2019-09-15 22:48:03 +02002568 [is_gb(ran_index)] BSSGP[ran_index].receive { repeat; }
2569 [is_iu(ran_index)] BSSAP.receive { repeat; }
Alexander Couzens5dce90d2018-07-31 03:16:37 +02002570 }
2571}
2572
Alexander Couzensbfda9212018-07-31 03:17:33 +02002573private function f_TC_attach_rau_a_a(charstring id) runs on BSSGP_ConnHdlr {
Alexander Couzensbfda9212018-07-31 03:17:33 +02002574 /* first perform regular attach */
2575 f_TC_attach(id);
2576
2577 /* then send RAU */
2578 f_routing_area_update(g_pars.ra);
2579
2580 /* do another RAU */
2581 f_routing_area_update(g_pars.ra);
2582
2583 f_detach_mo(c_GMM_DTT_MO_GPRS, true, true);
2584}
2585
2586testcase TC_attach_rau_a_a() runs on test_CT {
2587 /* MS <-> SGSN: Successful Attach
2588 * MS -> SGSN: Routing Area Update Request
2589 * MS <- SGSN: Routing Area Update Accept
2590 * MS -> SGSN: Routing Area Update Request
2591 * MS <- SGSN: Routing Area Update Accept
2592 * MS -> SGSN: Detach (PowerOff)
2593 */
2594 var BSSGP_ConnHdlr vc_conn;
2595 f_init();
2596 f_sleep(1.0);
2597 vc_conn := f_start_handler(refers(f_TC_attach_rau_a_a), testcasename(), g_gb, 37);
2598 vc_conn.done;
Pau Espin Pedrolce0d6152019-08-27 19:07:27 +02002599 f_cleanup();
Alexander Couzensbfda9212018-07-31 03:17:33 +02002600}
2601
Alexander Couzensbe837bd2018-07-31 04:20:11 +02002602private function f_TC_attach_rau_a_b(charstring id) runs on BSSGP_ConnHdlr {
Alexander Couzensbe837bd2018-07-31 04:20:11 +02002603 f_TC_attach(id);
2604
2605 log("attach complete sending rau");
2606 f_routing_area_update(g_pars.ra, 0);
2607
2608 log("rau complete unregistering");
2609 f_bssgp_client_unregister(g_pars.imsi);
Harald Welte5339b2e2020-10-04 22:52:56 +02002610 f_bssgp_client_register(g_pars.imsi, g_pars.tlli, BSSGP_PROC[1]);
Alexander Couzensbe837bd2018-07-31 04:20:11 +02002611
2612 log("sending second RAU via different RA");
2613 f_routing_area_update(f_cellid_to_RAI(g_pars.bssgp_cell_id[1]), 1);
2614
2615 f_detach_mo(c_GMM_DTT_MO_GPRS, true, true, 1);
2616}
2617
2618testcase TC_attach_rau_a_b() runs on test_CT {
2619 /* MS <-> SGSN: Successful Attach
2620 * MS -> SGSN: Routing Area _a_ Update Request
2621 * MS <- SGSN: Routing Area _a_ Update Accept
2622 * MS -> SGSN: Routing Area _b_ Update Request
2623 * MS <- SGSN: Routing Area _b_ Update Accept
2624 * MS -> SGSN: Detach (PowerOff)
2625 */
2626 var BSSGP_ConnHdlr vc_conn;
2627 f_init();
2628 f_sleep(1.0);
2629 vc_conn := f_start_handler(refers(f_TC_attach_rau_a_b), testcasename(), g_gb, 38);
2630 vc_conn.done;
Pau Espin Pedrolce0d6152019-08-27 19:07:27 +02002631 f_cleanup();
Alexander Couzensbe837bd2018-07-31 04:20:11 +02002632}
2633
Alexander Couzenscf3c93d2018-08-07 19:48:27 +02002634private function f_TC_attach_gmm_attach_req_while_gmm_attach(charstring id) runs on BSSGP_ConnHdlr {
2635 var integer count_req := 0;
Vadim Yanitskiy98bb2d52020-03-28 00:57:21 +07002636 var MobileIdentityLV mi;
Alexander Couzenscf3c93d2018-08-07 19:48:27 +02002637 var RoutingAreaIdentificationV rand_rai := f_random_RAI();
Harald Welte955aa942019-05-03 01:29:29 +02002638 var PDU_L3_SGSN_MS l3_mt;
Alexander Couzenscf3c93d2018-08-07 19:48:27 +02002639
Alexander Couzens4444b5a2019-08-13 13:25:32 +02002640 f_send_l3(ts_GMM_ATTACH_REQ(f_mi_get_lv(), rand_rai, true, false, omit, omit));
Alexander Couzenscf3c93d2018-08-07 19:48:27 +02002641
2642 alt {
Harald Welte955aa942019-05-03 01:29:29 +02002643 [] BSSGP[0].receive(tr_GMM_ATTACH_REJECT(?)) {
Alexander Couzenscf3c93d2018-08-07 19:48:27 +02002644 setverdict(fail, "Unexpected GMM ATTACH REJECT");
2645 mtc.stop;
2646 }
Harald Welte955aa942019-05-03 01:29:29 +02002647 [] BSSGP[0].receive(tr_GMM_ID_REQ('001'B)) {
Alexander Couzenscf3c93d2018-08-07 19:48:27 +02002648 mi := valueof(ts_MI_IMSI_LV(g_pars.imsi));
Alexander Couzens4444b5a2019-08-13 13:25:32 +02002649 f_send_l3(ts_GMM_ID_RESP(mi));
Alexander Couzenscf3c93d2018-08-07 19:48:27 +02002650 repeat;
2651 }
Harald Welte955aa942019-05-03 01:29:29 +02002652 [] BSSGP[0].receive(tr_GMM_ID_REQ('010'B)) {
Alexander Couzenscf3c93d2018-08-07 19:48:27 +02002653 /* send out a second GMM_Attach Request.
2654 * If the SGSN follows the rules, this 2nd ATTACH REQ should be ignored, because
2655 * of the same content */
Alexander Couzens4444b5a2019-08-13 13:25:32 +02002656 f_send_l3(ts_GMM_ATTACH_REQ(f_mi_get_lv(), rand_rai, true, false, omit, omit));
Alexander Couzenscf3c93d2018-08-07 19:48:27 +02002657 mi := valueof(ts_MI_IMEI_LV(g_pars.imei));
Alexander Couzens4444b5a2019-08-13 13:25:32 +02002658 f_send_l3(ts_GMM_ID_RESP(mi));
Alexander Couzenscf3c93d2018-08-07 19:48:27 +02002659 }
2660 }
2661 f_sleep(1.0);
2662
2663 /* we've sent already a IMEI answer, we should NOT asked again for IMEI */
2664 alt {
Harald Welte955aa942019-05-03 01:29:29 +02002665 [] BSSGP[0].receive(tr_GMM_ID_REQ('001'B)) {
Alexander Couzenscf3c93d2018-08-07 19:48:27 +02002666 mi := valueof(ts_MI_IMSI_LV(g_pars.imsi));
Alexander Couzens4444b5a2019-08-13 13:25:32 +02002667 f_send_l3(ts_GMM_ID_RESP(mi));
Alexander Couzenscf3c93d2018-08-07 19:48:27 +02002668 repeat;
2669 }
Harald Welte955aa942019-05-03 01:29:29 +02002670 [] BSSGP[0].receive(tr_GMM_ID_REQ('010'B)) {
Alexander Couzenscf3c93d2018-08-07 19:48:27 +02002671 setverdict(fail, "Unexpected GMM ID REQ (IMEI).");
2672 mtc.stop;
2673 }
Harald Welte955aa942019-05-03 01:29:29 +02002674 [] BSSGP[0].receive(tr_GMM_ATTACH_REJECT(?)) {
Alexander Couzenscf3c93d2018-08-07 19:48:27 +02002675 setverdict(fail, "Unexpected GMM ATTACH REJECT");
2676 mtc.stop;
2677 }
Harald Welte955aa942019-05-03 01:29:29 +02002678 [] BSSGP[0].receive(tr_GMM_ATTACH_ACCEPT('001'B, ?, ?)) -> value l3_mt {
2679 f_process_attach_accept(l3_mt.msgs.gprs_mm.attachAccept);
Alexander Couzens4444b5a2019-08-13 13:25:32 +02002680 f_send_l3(ts_GMM_ATTACH_COMPL);
Alexander Couzenscf3c93d2018-08-07 19:48:27 +02002681 setverdict(pass);
2682 /* FIXME: Extract P-TMSI, if any. Only send Complete if necessary */
2683 }
2684 }
2685}
2686
2687testcase TC_attach_gmm_attach_req_while_gmm_attach() runs on test_CT {
2688 /* Testing if the SGSN ignore Attach Request with the exact same content */
2689 /* MS -> SGSN: Attach Request IMSI
2690 * MS <- SGSN: Identity Request IMSI (optional)
2691 * MS -> SGSN: Identity Response IMSI (optional)
2692 * MS <- SGSN: Identity Request IMEI
2693 * MS -> SGSN: Attach Request (2nd)
2694 * MS <- SGSN: Identity Response IMEI
2695 * MS <- SGSN: Attach Accept
2696 * MS -> SGSN: Attach Complete
2697 */
2698 var BSSGP_ConnHdlr vc_conn;
2699 f_init();
2700 f_sleep(1.0);
2701 f_vty_config(SGSNVTY, "sgsn", "auth-policy accept-all");
2702 vc_conn := f_start_handler(refers(f_TC_attach_gmm_attach_req_while_gmm_attach), testcasename(), g_gb, 39);
2703 vc_conn.done;
Pau Espin Pedrolce0d6152019-08-27 19:07:27 +02002704 f_cleanup();
Alexander Couzenscf3c93d2018-08-07 19:48:27 +02002705}
2706
Alexander Couzens0c6324f2018-09-14 16:37:04 +02002707private function f_TC_attach_usim_resync(charstring id) runs on BSSGP_ConnHdlr {
Alexander Couzens0c6324f2018-09-14 16:37:04 +02002708 var RoutingAreaIdentificationV old_ra := f_random_RAI();
2709
2710 var template PDU_L3_MS_SGSN attach_req := ts_GMM_ATTACH_REQ(f_mi_get_lv(), old_ra, false, false, omit, omit);
2711
2712 /* send Attach Request */
2713 /* indicate R99 capability of the MS to enable UMTS AKA in presence of
2714 * 3G auth vectors */
2715 attach_req.msgs.gprs_mm.attachRequest.msNetworkCapability.msNetworkCapabilityV.revisionLevelIndicatior := '1'B;
2716 /* The thing is, if the solSACapability is 'omit', then the
2717 * revisionLevelIndicatior is at the wrong place! */
2718 attach_req.msgs.gprs_mm.attachRequest.msNetworkCapability.msNetworkCapabilityV.solSACapability := '0'B;
Alexander Couzens4444b5a2019-08-13 13:25:32 +02002719 f_send_l3(attach_req);
Alexander Couzens0c6324f2018-09-14 16:37:04 +02002720
2721 /* do the auth */
2722 var PDU_L3_MS_SGSN l3_mo;
2723 var PDU_L3_SGSN_MS l3_mt;
2724 var default di := activate(as_mm_identity());
2725
2726 var GSUP_IE auth_tuple;
2727 var template AuthenticationParameterAUTNTLV autn;
2728
2729 g_pars.vec := f_gen_auth_vec_3g();
2730 autn := {
2731 elementIdentifier := '28'O,
2732 lengthIndicator := lengthof(g_pars.vec.autn),
2733 autnValue := g_pars.vec.autn
2734 };
2735 auth_tuple := valueof(ts_GSUP_IE_AuthTuple2G3G(g_pars.vec.rand,
2736 g_pars.vec.sres,
2737 g_pars.vec.kc,
2738 g_pars.vec.ik,
2739 g_pars.vec.ck,
2740 g_pars.vec.autn,
2741 g_pars.vec.res));
2742 log("GSUP sends 2G and 3G auth tuples", auth_tuple);
2743 GSUP.receive(tr_GSUP_SAI_REQ(g_pars.imsi));
2744 GSUP.send(ts_GSUP_SAI_RES(g_pars.imsi, auth_tuple));
2745
2746 var template PDU_L3_SGSN_MS auth_ciph_req := tr_GMM_AUTH_REQ(g_pars.vec.rand);
2747 auth_ciph_req.msgs.gprs_mm.authenticationAndCipheringRequest.authenticationParameterAUTN := autn;
Harald Welte955aa942019-05-03 01:29:29 +02002748 BSSGP[0].receive(auth_ciph_req) -> value l3_mt;
Alexander Couzens0c6324f2018-09-14 16:37:04 +02002749
2750 /* send the gmm auth failure with resync IE */
Alexander Couzens4444b5a2019-08-13 13:25:32 +02002751 f_send_l3(ts_GMM_AUTH_FAIL_UMTS_AKA_RESYNC(g_pars.vec.auts));
Alexander Couzens0c6324f2018-09-14 16:37:04 +02002752
2753 /* wait for the GSUP resync request */
2754 GSUP.receive(tr_GSUP_SAI_REQ_UMTS_AKA_RESYNC(
2755 g_pars.imsi,
2756 g_pars.vec.auts,
2757 g_pars.vec.rand));
2758
2759 /* generate new key material */
2760 g_pars.vec := f_gen_auth_vec_3g();
2761 autn := {
2762 elementIdentifier := '28'O,
2763 lengthIndicator := lengthof(g_pars.vec.autn),
2764 autnValue := g_pars.vec.autn
2765 };
2766
2767 auth_tuple := valueof(ts_GSUP_IE_AuthTuple2G3G(g_pars.vec.rand,
2768 g_pars.vec.sres,
2769 g_pars.vec.kc,
2770 g_pars.vec.ik,
2771 g_pars.vec.ck,
2772 g_pars.vec.autn,
2773 g_pars.vec.res));
2774 /* send new key material */
2775 GSUP.send(ts_GSUP_SAI_RES(g_pars.imsi, auth_tuple));
2776
2777 /* wait for the new Auth Request */
2778 auth_ciph_req := tr_GMM_AUTH_REQ(g_pars.vec.rand);
2779 auth_ciph_req.msgs.gprs_mm.authenticationAndCipheringRequest.authenticationParameterAUTN := autn;
Harald Welte955aa942019-05-03 01:29:29 +02002780 BSSGP[0].receive(auth_ciph_req) -> value l3_mt;
Alexander Couzens0c6324f2018-09-14 16:37:04 +02002781 var BIT4 ac_ref := l3_mt.msgs.gprs_mm.authenticationAndCipheringRequest.acReferenceNumber.valueField;
2782 var template PDU_L3_MS_SGSN auth_ciph_resp := ts_GMM_AUTH_RESP_2G(ac_ref, g_pars.vec.sres);
2783 auth_ciph_resp := ts_GMM_AUTH_RESP_2G(ac_ref, g_pars.vec.sres);
2784 auth_ciph_resp.msgs.gprs_mm.authenticationAndCipheringResponse.authenticationParResp := {
2785 valueField := substr(g_pars.vec.res, 0, 4)
2786 };
2787 auth_ciph_resp.msgs.gprs_mm.authenticationAndCipheringResponse.authenticationRespParExt := {
2788 elementIdentifier := '21'O,
2789 lengthIndicator := lengthof(g_pars.vec.res) - 4,
2790 valueField := substr(g_pars.vec.res, 4, lengthof(g_pars.vec.res) - 4)
2791 };
2792 l3_mo := valueof(auth_ciph_resp);
2793 if (ispresent(l3_mt.msgs.gprs_mm.authenticationAndCipheringRequest.imeisvRequest) and
2794 l3_mt.msgs.gprs_mm.authenticationAndCipheringRequest.imeisvRequest.valueField == '001'B) {
2795 l3_mo.msgs.gprs_mm.authenticationAndCipheringResponse.imeisv :=
2796 valueof(ts_MI_IMEISV_TLV(g_pars.imei & '0'H));
2797 }
Alexander Couzens4444b5a2019-08-13 13:25:32 +02002798 f_send_l3(l3_mo);
Alexander Couzens0c6324f2018-09-14 16:37:04 +02002799 deactivate(di);
2800
2801 /* Expect SGSN to perform LU with HLR */
2802 f_gmm_gsup_lu_isd();
2803
Harald Welte955aa942019-05-03 01:29:29 +02002804 BSSGP[0].receive(tr_GMM_ATTACH_ACCEPT('001'B, ?, ?)) -> value l3_mt {
2805 f_process_attach_accept(l3_mt.msgs.gprs_mm.attachAccept);
Alexander Couzens0c6324f2018-09-14 16:37:04 +02002806 }
Alexander Couzens4444b5a2019-08-13 13:25:32 +02002807 f_send_l3(ts_GMM_ATTACH_COMPL);
Alexander Couzens0c6324f2018-09-14 16:37:04 +02002808 setverdict(pass);
2809}
2810
2811testcase TC_attach_usim_resync() runs on test_CT {
2812 /* MS -> SGSN: Attach Request
2813 * MS <- SGSN: Identity Request IMSI
2814 * MS -> SGSN: Identity Response IMSI
2815 * MS <- SGSN: Identity Request IMEI
2816 * MS -> SGSN: Identity Response IMEI
2817 * HLR<- SGSN: SAI Request
2818 * HLR-> SGSN: SAI Response
2819 * MS <- SGSN: Auth Request
2820 * MS -> SGSN: Auth Failure (with AUTS)
2821 * HLR<- SGSN: SAI Request (with AUTS & RAND)
2822 * HLR-> SGSN: SAI Response (new key material)
2823 * MS <- SGSN: Auth Request (new key material)
2824 * MS -> SGSN: Auth Response
2825 * MS <- SGSN: Attach Accept
2826 * MS -> SGSN: Attach Complete
2827 */
2828 var BSSGP_ConnHdlr vc_conn;
2829 f_init();
2830 f_sleep(1.0);
2831 vc_conn := f_start_handler(refers(f_TC_attach_usim_resync), testcasename(), g_gb, 40);
2832 vc_conn.done;
Pau Espin Pedrolce0d6152019-08-27 19:07:27 +02002833 f_cleanup();
Alexander Couzens0c6324f2018-09-14 16:37:04 +02002834}
2835
Eric Wildc555be52021-05-15 19:48:22 +02002836private function f_TC_attach_usim_crypt(OCT1 netcap_a2345, BIT3 auth_req_ciph) runs on BSSGP_ConnHdlr {
2837 var RoutingAreaIdentificationV old_ra := f_random_RAI();
2838
2839 var template PDU_L3_MS_SGSN attach_req := ts_GMM_ATTACH_REQ(f_mi_get_lv(), old_ra, false, false, omit, omit);
2840 attach_req.msgs.gprs_mm.attachRequest.msNetworkCapability.msNetworkCapabilityV.spare_octets := netcap_a2345; /* GEA2345... */
2841
2842 /* send Attach Request */
2843 /* indicate R99 capability of the MS to enable UMTS AKA in presence of
2844 * 3G auth vectors */
2845 attach_req.msgs.gprs_mm.attachRequest.msNetworkCapability.msNetworkCapabilityV.revisionLevelIndicatior := '1'B;
2846 /* The thing is, if the solSACapability is 'omit', then the
2847 * revisionLevelIndicatior is at the wrong place! */
2848 attach_req.msgs.gprs_mm.attachRequest.msNetworkCapability.msNetworkCapabilityV.solSACapability := '0'B;
2849 f_send_l3(attach_req);
2850
2851 /* do the auth */
2852 var PDU_L3_MS_SGSN l3_mo;
2853 var PDU_L3_SGSN_MS l3_mt;
2854 var default di := activate(as_mm_identity());
2855
2856 var GSUP_IE auth_tuple;
2857 var template AuthenticationParameterAUTNTLV autn;
2858
2859 g_pars.vec := f_gen_auth_vec_3g();
2860 autn := {
2861 elementIdentifier := '28'O,
2862 lengthIndicator := lengthof(g_pars.vec.autn),
2863 autnValue := g_pars.vec.autn
2864 };
2865 auth_tuple := valueof(ts_GSUP_IE_AuthTuple2G3G(g_pars.vec.rand,
2866 g_pars.vec.sres,
2867 g_pars.vec.kc,
2868 g_pars.vec.ik,
2869 g_pars.vec.ck,
2870 g_pars.vec.autn,
2871 g_pars.vec.res));
2872 log("GSUP sends 2G and 3G auth tuples", auth_tuple);
2873 GSUP.receive(tr_GSUP_SAI_REQ(g_pars.imsi));
2874 GSUP.send(ts_GSUP_SAI_RES(g_pars.imsi, auth_tuple));
2875
2876 var template PDU_L3_SGSN_MS auth_ciph_req := tr_GMM_AUTH_REQ(g_pars.vec.rand, auth_req_ciph);
2877 auth_ciph_req.msgs.gprs_mm.authenticationAndCipheringRequest.authenticationParameterAUTN := autn;
2878 BSSGP[0].receive(auth_ciph_req) -> value l3_mt;
2879
2880 setverdict(pass);
2881 deactivate(di);
2882}
2883
2884private function f_TC_attach_usim_a54_a54(charstring id) runs on BSSGP_ConnHdlr {
2885 f_TC_attach_usim_crypt('10'O, '100'B);
2886}
2887
2888private function f_TC_attach_usim_a54_a53(charstring id) runs on BSSGP_ConnHdlr {
2889 f_TC_attach_usim_crypt('20'O, '011'B);
2890}
2891
2892private function f_TC_attach_usim_a53_a54(charstring id) runs on BSSGP_ConnHdlr {
2893 f_TC_attach_usim_crypt('30'O, '011'B);
2894}
2895
2896private function f_TC_attach_usim_a50_a54(charstring id) runs on BSSGP_ConnHdlr {
2897 f_TC_attach_usim_crypt('30'O, '000'B);
2898}
2899
2900private function f_TC_attach_usim_a54_a50(charstring id) runs on BSSGP_ConnHdlr {
2901 f_TC_attach_usim_crypt('00'O, '000'B);
2902}
2903
2904testcase TC_attach_usim_a54_a54() runs on test_CT {
2905 var BSSGP_ConnHdlr vc_conn;
2906 f_init();
2907 f_sleep(1.0);
Vadim Yanitskiy60fcc632021-07-04 01:02:29 +02002908 f_vty_config(SGSNVTY, "sgsn", "encryption gea 0 3 4");
Eric Wildc555be52021-05-15 19:48:22 +02002909 vc_conn := f_start_handler(refers(f_TC_attach_usim_a54_a54), testcasename(), g_gb, 40);
2910 vc_conn.done;
2911 f_cleanup();
2912}
2913
2914testcase TC_attach_usim_a54_a53() runs on test_CT {
2915 var BSSGP_ConnHdlr vc_conn;
2916 f_init();
2917 f_sleep(1.0);
Vadim Yanitskiy60fcc632021-07-04 01:02:29 +02002918 f_vty_config(SGSNVTY, "sgsn", "encryption gea 0 3 4");
Eric Wildc555be52021-05-15 19:48:22 +02002919 vc_conn := f_start_handler(refers(f_TC_attach_usim_a54_a53), testcasename(), g_gb, 40);
2920 vc_conn.done;
2921 f_cleanup();
2922}
2923
2924testcase TC_attach_usim_a53_a54() runs on test_CT {
2925 var BSSGP_ConnHdlr vc_conn;
2926 f_init();
2927 f_sleep(1.0);
Vadim Yanitskiy60fcc632021-07-04 01:02:29 +02002928 f_vty_config(SGSNVTY, "sgsn", "encryption gea 0 3");
Eric Wildc555be52021-05-15 19:48:22 +02002929 vc_conn := f_start_handler(refers(f_TC_attach_usim_a53_a54), testcasename(), g_gb, 40);
2930 vc_conn.done;
2931 f_cleanup();
2932}
2933
2934testcase TC_attach_usim_a50_a54() runs on test_CT {
2935 var BSSGP_ConnHdlr vc_conn;
2936 f_init();
2937 f_sleep(1.0);
Vadim Yanitskiy60fcc632021-07-04 01:02:29 +02002938 f_vty_config(SGSNVTY, "sgsn", "encryption gea 0");
Eric Wildc555be52021-05-15 19:48:22 +02002939 vc_conn := f_start_handler(refers(f_TC_attach_usim_a50_a54), testcasename(), g_gb, 40);
2940 vc_conn.done;
2941 f_cleanup();
2942}
2943
2944testcase TC_attach_usim_a54_a50() runs on test_CT {
2945 var BSSGP_ConnHdlr vc_conn;
2946 f_init();
2947 f_sleep(1.0);
Vadim Yanitskiy60fcc632021-07-04 01:02:29 +02002948 f_vty_config(SGSNVTY, "sgsn", "encryption gea 0 3 4");
Eric Wildc555be52021-05-15 19:48:22 +02002949 vc_conn := f_start_handler(refers(f_TC_attach_usim_a54_a50), testcasename(), g_gb, 40);
2950 vc_conn.done;
2951 f_cleanup();
2952}
Harald Weltea05b8072019-04-23 22:35:05 +02002953
2954/* Send LLC NULL to see if the SGSN survives it (OS#3952) */
2955private function f_TC_llc_null(charstring id) runs on BSSGP_ConnHdlr {
2956 f_gmm_attach(false, false);
2957 f_sleep(1.0);
2958 f_send_llc(ts_LLC_NULL('0'B, c_LLC_SAPI_LLGMM, LLC_CR_UL_CMD));
2959 /* try to detach to check if SGSN is still alive */
2960 f_detach_mo(c_GMM_DTT_MO_GPRS, true, true);
2961}
2962testcase TC_llc_null() runs on test_CT {
2963 var BSSGP_ConnHdlr vc_conn;
2964 f_init();
2965 f_sleep(1.0);
2966 vc_conn := f_start_handler(refers(f_TC_llc_null), testcasename(), g_gb, 41);
2967 vc_conn.done;
Pau Espin Pedrolce0d6152019-08-27 19:07:27 +02002968 f_cleanup();
Harald Weltea05b8072019-04-23 22:35:05 +02002969}
2970
Harald Welte645a1512019-04-23 23:18:23 +02002971/* Send LLC SABM to see if the SGSN rejects it properly with DM */
2972private function f_TC_llc_sabm_dm_llgmm(charstring id) runs on BSSGP_ConnHdlr {
2973 f_gmm_attach(false, false);
2974 f_sleep(1.0);
2975 f_send_llc(ts_LLC_SABM({}, '1'B, c_LLC_SAPI_LLGMM, LLC_CR_UL_CMD));
Harald Welte955aa942019-05-03 01:29:29 +02002976 BSSGP[0].receive(tr_LLC_DM(?, c_LLC_SAPI_LLGMM, LLC_CR_DL_RSP));
Harald Welte645a1512019-04-23 23:18:23 +02002977 setverdict(pass);
2978}
2979testcase TC_llc_sabm_dm_llgmm() runs on test_CT {
2980 var BSSGP_ConnHdlr vc_conn;
2981 f_init();
2982 f_sleep(1.0);
2983 vc_conn := f_start_handler(refers(f_TC_llc_sabm_dm_llgmm), testcasename(), g_gb, 42);
2984 vc_conn.done;
Pau Espin Pedrolce0d6152019-08-27 19:07:27 +02002985 f_cleanup();
Harald Welte645a1512019-04-23 23:18:23 +02002986}
2987
2988/* Send LLC SABM to see if the SGSN rejects it properly with DM */
2989private function f_TC_llc_sabm_dm_ll5(charstring id) runs on BSSGP_ConnHdlr {
2990 f_gmm_attach(false, false);
2991 f_sleep(1.0);
2992 f_send_llc(ts_LLC_SABM({}, '1'B, c_LLC_SAPI_LL5, LLC_CR_UL_CMD));
Harald Welte955aa942019-05-03 01:29:29 +02002993 BSSGP[0].receive(tr_LLC_DM(?, c_LLC_SAPI_LL5, LLC_CR_DL_RSP));
Harald Welte645a1512019-04-23 23:18:23 +02002994 setverdict(pass);
2995}
2996testcase TC_llc_sabm_dm_ll5() runs on test_CT {
2997 var BSSGP_ConnHdlr vc_conn;
2998 f_init();
2999 f_sleep(1.0);
3000 vc_conn := f_start_handler(refers(f_TC_llc_sabm_dm_ll5), testcasename(), g_gb, 43);
3001 vc_conn.done;
Pau Espin Pedrolce0d6152019-08-27 19:07:27 +02003002 f_cleanup();
Harald Welte645a1512019-04-23 23:18:23 +02003003}
3004
Harald Welte2aaac1b2019-05-02 10:02:53 +02003005/* test XID handshake with empty L3 info: expect empty return (some phones require that, OS#3426 */
3006private function f_TC_xid_empty_l3(charstring id) runs on BSSGP_ConnHdlr {
3007 var PdpActPars apars := valueof(t_PdpActPars(mp_ggsn_ip));
3008 var template (value) XID_Information xid;
3009 var template XID_Information xid_rx;
3010
3011 /* first perform regular attach */
3012 f_TC_attach(id);
3013 /* then activate PDP context */
3014 f_pdp_ctx_act(apars);
3015
3016 /* start MO XID */
3017 xid := { ts_XID_L3(''O) };
3018 xid_rx := { tr_XID_L3(''O) };
3019 f_send_llc(ts_LLC_XID_MO_CMD(xid, apars.sapi));
3020 alt {
Harald Welte955aa942019-05-03 01:29:29 +02003021 [] BSSGP[0].receive(tr_LLC_XID(xid_rx, apars.sapi));
Harald Welte2aaac1b2019-05-02 10:02:53 +02003022 [] as_xid(apars);
3023 }
3024 setverdict(pass);
3025}
3026testcase TC_xid_empty_l3() runs on test_CT {
3027 var BSSGP_ConnHdlr vc_conn;
3028 f_init();
3029 f_sleep(1.0);
3030 vc_conn := f_start_handler(refers(f_TC_xid_empty_l3), testcasename(), g_gb, 44);
3031 vc_conn.done;
Pau Espin Pedrolce0d6152019-08-27 19:07:27 +02003032 f_cleanup();
Harald Welte2aaac1b2019-05-02 10:02:53 +02003033}
3034
3035private function f_TC_xid_n201u(charstring id) runs on BSSGP_ConnHdlr {
3036 var PdpActPars apars := valueof(t_PdpActPars(mp_ggsn_ip));
3037 var template (value) XID_Information xid;
3038 var template XID_Information xid_rx;
3039
3040 /* first perform regular attach */
3041 f_TC_attach(id);
3042 /* then activate PDP context */
3043 f_pdp_ctx_act(apars);
3044
3045 /* start MO XID */
3046 xid := { ts_XID_N201U(1234) };
3047 xid_rx := { tr_XID_N201U(1234) };
3048 f_send_llc(ts_LLC_XID_MO_CMD(xid, apars.sapi));
3049 alt {
Harald Welte955aa942019-05-03 01:29:29 +02003050 [] BSSGP[0].receive(tr_LLC_XID_MT_RSP(xid_rx, apars.sapi));
Harald Welte2aaac1b2019-05-02 10:02:53 +02003051 [] as_xid(apars);
3052 }
3053 setverdict(pass);
3054}
3055testcase TC_xid_n201u() runs on test_CT {
3056 var BSSGP_ConnHdlr vc_conn;
3057 f_init();
3058 f_sleep(1.0);
3059 vc_conn := f_start_handler(refers(f_TC_xid_n201u), testcasename(), g_gb, 45);
3060 vc_conn.done;
Pau Espin Pedrolce0d6152019-08-27 19:07:27 +02003061 f_cleanup();
Harald Welte2aaac1b2019-05-02 10:02:53 +02003062}
3063
Alexander Couzens6bee0872019-05-11 01:48:50 +02003064private function f_TC_attach_pdp_act_gmm_detach(charstring id) runs on BSSGP_ConnHdlr {
3065 var PdpActPars apars := valueof(t_PdpActPars(mp_ggsn_ip));
3066
3067 /* first perform regular attach */
3068 f_TC_attach(id);
3069 /* then activate PDP context */
3070 f_pdp_ctx_act(apars);
3071 /* do a normal detach */
3072 f_detach_mo(c_GMM_DTT_MO_GPRS, false, true);
3073}
3074
3075testcase TC_attach_pdp_act_gmm_detach() runs on test_CT {
3076 /* MS -> SGSN: Attach Request
3077 * MS <-> SGSN: [..]
3078 * MS -> SGSN: Attach Complete
3079 * MS -> SGSN: PDP Activate Request
3080 * MS <- SGSN: PDP Activate Accept
3081 * MS -> SGSN: GMM Detach Request
3082 * MS <- SGSN: GMM Detach Accept
3083 */
3084 var BSSGP_ConnHdlr vc_conn;
3085 f_init();
3086 vc_conn := f_start_handler(refers(f_TC_attach_pdp_act_gmm_detach), testcasename(), g_gb, 26);
3087 vc_conn.done;
Pau Espin Pedrolce0d6152019-08-27 19:07:27 +02003088 f_cleanup();
Alexander Couzens6bee0872019-05-11 01:48:50 +02003089}
Harald Welte645a1512019-04-23 23:18:23 +02003090
Pau Espin Pedrolce571b52019-11-08 18:32:28 +01003091private function f_TC_attach_req_id_req_ra_update(charstring id) runs on BSSGP_ConnHdlr {
3092 var RoutingAreaIdentificationV old_ra := f_random_RAI();
3093 var RoutingAreaIdentificationV new_ra := f_random_RAI();
3094 while (old_ra == new_ra) { new_ra := f_random_RAI(); };
3095 var template PDU_L3_MS_SGSN attach_req := ts_GMM_ATTACH_REQ(f_mi_get_lv(), old_ra, false, false, omit, omit);
3096 var PDU_L3_SGSN_MS l3_mt;
3097
3098 f_send_l3(attach_req, 0);
3099
3100 BSSGP[0].receive(tr_GMM_ID_REQ(?));
3101
3102 f_send_l3(ts_GMM_RAU_REQ(f_mi_get_lv(), GPRS_UPD_T_RA, new_ra, false, omit, omit));
3103 alt {
3104 [] BSSGP[0].receive(tr_GMM_RAU_REJECT('0a'O)) {
3105 setverdict(pass);
3106 }
3107 [] BSSGP[0].receive { repeat; }
3108 }
3109}
3110
3111/* This test triggers crash in osmo-sgsn before osmo-sgsn.git I64fa5cf1b427d3abb99e553e584897261a827ce6.
3112 * See OS#3957 and OS#4245 for more information.
3113 */
3114testcase TC_attach_req_id_req_ra_update() runs on test_CT {
3115 /*
3116 * MS --> SGSN: Attach Req (TMSI, RAI=901-70-356-101)
3117 * MS <-- SGSN: Identity Request (IMEI)
3118 * MS --> SGSN: RA Updating (RAI=901-70-2758-208)
3119 */
3120 var BSSGP_ConnHdlr vc_conn;
3121 f_init();
3122 vc_conn := f_start_handler(refers(f_TC_attach_req_id_req_ra_update), testcasename(), g_gb, 47);
3123 vc_conn.done;
3124 f_cleanup();
3125}
3126
Harald Welte8e5932e2020-06-17 22:12:54 +02003127private altstep as_nopaging_ps(integer ran_idx := 0) runs on BSSGP_ConnHdlr {
3128var PDU_BSSGP rx;
3129[] BSSGP_SIG[ran_idx].receive(tr_BSSGP_PS_PAGING(?)) -> value rx {
3130 setverdict(fail, "Received unexpected PS PAGING: ", rx);
3131 mtc.stop;
3132 }
3133}
3134
3135/* SUSPEND, then DL traffic: should not pass + no paging expected */
3136private function f_TC_suspend_nopaging(charstring id) runs on BSSGP_ConnHdlr {
3137 var PdpActPars apars := valueof(t_PdpActPars(mp_ggsn_ip));
3138 var default d;
3139
3140 /* first perform regular attach */
3141 f_TC_attach(id);
3142 /* then activate PDP context */
3143 f_pdp_ctx_act(apars);
3144 /* then transceive a downlink PDU */
3145 f_gtpu_xceive_mt(apars, f_rnd_octstring(100));
3146
3147 /* now suspend GPRS */
3148 f_bssgp_suspend();
3149
3150 d := activate(as_nopaging_ps());
3151
3152 /* at this point we don't expect any downlink traffic at all, neither actual LLC/SNDCP data,
3153 * nor any related paging requests */
3154 f_gtpu_xceive_mt(apars, f_rnd_octstring(100), expect_fwd := false);
3155
3156 deactivate(d);
3157}
3158testcase TC_suspend_nopaging() runs on test_CT {
3159 var BSSGP_ConnHdlr vc_conn;
3160 f_init();
3161 f_sleep(1.0);
3162 vc_conn := f_start_handler(refers(f_TC_suspend_nopaging), testcasename(), g_gb, 48);
3163 vc_conn.done;
3164 f_cleanup();
3165}
3166
3167
3168/* SUSPEND, then RESUME: data expected to flow after explicit resume */
3169private function f_TC_suspend_resume(charstring id) runs on BSSGP_ConnHdlr {
3170 var PdpActPars apars := valueof(t_PdpActPars(mp_ggsn_ip));
3171 var OCT1 susp_ref;
3172 var default d;
3173
3174 /* first perform regular attach */
3175 f_TC_attach(id);
3176 /* then activate PDP context */
3177 f_pdp_ctx_act(apars);
3178 /* then transceive a downlink PDU */
3179 f_gtpu_xceive_mt(apars, f_rnd_octstring(100));
3180
3181 /* now suspend GPRS */
3182 susp_ref := f_bssgp_suspend();
3183
3184 d := activate(as_nopaging_ps());
3185
3186 /* at this point we don't expect any downlink traffic at all, neither actual LLC/SNDCP data,
3187 * nor any related paging requests */
3188 f_gtpu_xceive_mt(apars, f_rnd_octstring(100), expect_fwd := false);
3189
3190 deactivate(d);
3191
3192 /* resume GPRS */
3193 f_bssgp_resume(susp_ref);
3194
3195 /* now data should be flowing again */
3196 f_gtpu_xceive_mt(apars, f_rnd_octstring(100));
3197}
3198testcase TC_suspend_resume() runs on test_CT {
3199 var BSSGP_ConnHdlr vc_conn;
3200 f_init();
3201 f_sleep(1.0);
3202 vc_conn := f_start_handler(refers(f_TC_suspend_resume), testcasename(), g_gb, 49);
3203 vc_conn.done;
3204 f_cleanup();
3205}
3206
3207/* SUSPEND, then RAU: data expected to flow after implicit resume */
3208private function f_TC_suspend_rau(charstring id) runs on BSSGP_ConnHdlr {
3209 var PdpActPars apars := valueof(t_PdpActPars(mp_ggsn_ip));
3210 var default d;
3211
3212 /* first perform regular attach */
3213 f_TC_attach(id);
3214 /* then activate PDP context */
3215 f_pdp_ctx_act(apars);
3216 /* then transceive a downlink PDU */
3217 f_gtpu_xceive_mt(apars, f_rnd_octstring(100));
3218
3219 /* now suspend GPRS */
3220 f_bssgp_suspend();
3221
3222 d := activate(as_nopaging_ps());
3223
3224 /* at this point we don't expect any downlink traffic at all, neither actual LLC/SNDCP data,
3225 * nor any related paging requests */
3226 f_gtpu_xceive_mt(apars, f_rnd_octstring(100), expect_fwd := false);
3227
3228 deactivate(d);
3229
3230 /* perform RAU (implicit RESUME) */
3231 f_routing_area_update(g_pars.ra);
3232
Harald Welted5836dc2021-03-20 15:40:00 +01003233 /* give SGSN some time to actually receve + process the RAU Complete we sent */
3234 f_sleep(0.5);
3235
Harald Welte8e5932e2020-06-17 22:12:54 +02003236 /* now data should be flowing again */
3237 f_gtpu_xceive_mt(apars, f_rnd_octstring(100));
3238
3239}
3240testcase TC_suspend_rau() runs on test_CT {
3241 var BSSGP_ConnHdlr vc_conn;
3242 f_init();
3243 f_sleep(1.0);
3244 vc_conn := f_start_handler(refers(f_TC_suspend_rau), testcasename(), g_gb, 50);
3245 vc_conn.done;
3246 f_cleanup();
3247}
3248
3249
3250/* wait for T3314 expiration and check that PS PAGING is created on DL PDU */
3251private function f_TC_paging_ps(charstring id) runs on BSSGP_ConnHdlr {
3252 var PdpActPars apars := valueof(t_PdpActPars(mp_ggsn_ip));
3253 var default d;
3254
3255 /* first perform regular attach */
3256 f_TC_attach(id);
3257 /* then activate PDP context */
3258 f_pdp_ctx_act(apars);
3259 /* then transceive a downlink PDU */
3260 f_gtpu_xceive_mt(apars, f_rnd_octstring(100));
3261
3262 /* now wait for T3314 expiration (test_CT below has reduced it to 3s) */
3263 f_sleep(5.0);
3264
3265 /* now data should be flowing again, but with PS PAGING */
3266 f_gtpu_xceive_mt(apars, f_rnd_octstring(100));
3267 BSSGP_SIG[0].receive(tr_BSSGP_PS_PAGING(?));
3268
3269 /* FIXME: simulate paging response */
3270 /* FIXME: verify PDU actually arrives only after paging response was successful */
3271
3272}
3273testcase TC_paging_ps() runs on test_CT {
3274 var BSSGP_ConnHdlr vc_conn;
3275 f_init();
3276 f_vty_config(SGSNVTY, "sgsn", "timer 3314 3");
3277 f_sleep(1.0);
3278 vc_conn := f_start_handler(refers(f_TC_paging_ps), testcasename(), g_gb, 51);
3279 vc_conn.done;
3280 f_vty_config(SGSNVTY, "sgsn", "timer 3314 default");
3281 f_cleanup();
3282}
3283
Philipp Maier7df55e02020-12-14 23:46:04 +01003284/* Run a RIM single report procedure over the sgsn. Since the SGSN will only do a transparent routing of the
3285 * RIM messages this basically tests if the message is correctly transfered from one GB interface to the
3286 * other and vice versa. */
3287testcase TC_bssgp_rim_single_report() runs on test_CT {
3288 var BSSGP_ConnHdlr vc_conn;
3289 f_init();
Philipp Maier7df55e02020-12-14 23:46:04 +01003290
3291 timer T := 2.0;
3292
3293 var template RIM_Routing_Address dst_addr;
3294 var template RIM_Routing_Address src_addr;
3295 var template RAN_Information_Request_RIM_Container req_cont;
3296 var template RAN_Information_RIM_Container res_cont;
3297 var template PDU_BSSGP bssgp_rim_pdu;
3298 var template PDU_BSSGP bssgp_rim_pdu_expect;
3299
3300 dst_addr := t_RIM_Routing_Address_cid(g_gb[1].cfg.bvc[0].cell_id);
3301 src_addr := t_RIM_Routing_Address_cid(g_gb[0].cfg.bvc[0].cell_id);
Harald Welte8e5932e2020-06-17 22:12:54 +02003302
3303
Philipp Maier7df55e02020-12-14 23:46:04 +01003304 /* Send NACC Ran information request to SGSN at GB interface #0. We epect the SGSN to forward this request
3305 * based on the cell id in dst_addr to GB interface #1. */
3306 req_cont := ts_RAN_Information_Request_RIM_Container(ts_RIM_Application_Identity(RIM_APP_ID_NACC),
3307 ts_RIM_Sequence_Number(1),
3308 ts_RIM_PDU_Indications(false, RIM_PDU_TYPE_SING_REP),
3309 ts_RIM_Protocol_Version_Number(1),
3310 tsu_RAN_Information_Request_Application_Container_NACC(g_gb[1].cfg.bvc[0].cell_id),
3311 omit);
3312 bssgp_rim_pdu := ts_RAN_INFORMATION_REQUEST(ts_RIM_Routing_Information(RIM_ADDR_GERAN_CELL_ID, dst_addr),
3313 ts_RIM_Routing_Information(RIM_ADDR_GERAN_CELL_ID, src_addr),
3314 req_cont);
3315 bssgp_rim_pdu_expect := tr_RAN_INFORMATION_REQUEST(tr_RIM_Routing_Information(RIM_ADDR_GERAN_CELL_ID, dst_addr),
3316 tr_RIM_Routing_Information(RIM_ADDR_GERAN_CELL_ID, src_addr),
3317 tr_RAN_Information_Request_RIM_Container);
3318 RIM[0].send(bssgp_rim_pdu);
3319 T.start;
3320 alt {
Vadim Yanitskiy418e8062021-02-28 16:27:12 +01003321 [] RIM[1].receive(bssgp_rim_pdu_expect) {
3322 setverdict(pass);
3323 }
Vadim Yanitskiy7bc13ea2021-02-28 16:26:03 +01003324 [] RIM[1].receive {
3325 setverdict(fail, "Unexpected BSSGP RIM PDU received");
Philipp Maier7df55e02020-12-14 23:46:04 +01003326 }
Vadim Yanitskiy7bc13ea2021-02-28 16:26:03 +01003327 [] T.timeout {
3328 setverdict(fail, "No BSSGP RIM PDU received");
3329 mtc.stop;
Philipp Maier7df55e02020-12-14 23:46:04 +01003330 }
3331 }
Harald Welte8e5932e2020-06-17 22:12:54 +02003332
Philipp Maier7df55e02020-12-14 23:46:04 +01003333 /* Now also emulate also the response as well and send it back on GB interface #1. Expect the result on
3334 * GB interface #0 */
Philipp Maier7df55e02020-12-14 23:46:04 +01003335 res_cont := ts_RAN_Information_RIM_Container(ts_RIM_Application_Identity(RIM_APP_ID_NACC),
3336 ts_RIM_Sequence_Number(2),
3337 ts_RIM_PDU_Indications(false, RIM_PDU_TYPE_SING_REP),
3338 ts_RIM_Protocol_Version_Number(1),
Pau Espin Pedrol8c74cbb2021-05-04 15:26:56 +02003339 tsu_ApplContainer_or_ApplErrContainer_NACC(tsu_ApplContainer_NACC(g_gb[0].cfg.bvc[0].cell_id, false, 3, si_default)),
Philipp Maier7df55e02020-12-14 23:46:04 +01003340 omit);
3341 bssgp_rim_pdu := ts_PDU_BSSGP_RAN_INFORMATION(ts_RIM_Routing_Information(RIM_ADDR_GERAN_CELL_ID, src_addr),
3342 ts_RIM_Routing_Information(RIM_ADDR_GERAN_CELL_ID, dst_addr),
3343 res_cont);
3344 bssgp_rim_pdu_expect := tr_PDU_BSSGP_RAN_INFORMATION(tr_RIM_Routing_Information(RIM_ADDR_GERAN_CELL_ID, src_addr),
3345 tr_RIM_Routing_Information(RIM_ADDR_GERAN_CELL_ID, dst_addr),
3346 ?);
3347 RIM[1].send(bssgp_rim_pdu);
3348 T.start;
3349 alt {
Vadim Yanitskiy418e8062021-02-28 16:27:12 +01003350 [] RIM[0].receive(bssgp_rim_pdu_expect) {
3351 setverdict(pass);
3352 }
Vadim Yanitskiy7bc13ea2021-02-28 16:26:03 +01003353 [] RIM[0].receive {
3354 setverdict(fail, "Unexpected BSSGP RIM PDU received");
Philipp Maier7df55e02020-12-14 23:46:04 +01003355 }
Vadim Yanitskiy7bc13ea2021-02-28 16:26:03 +01003356 [] T.timeout {
3357 setverdict(fail, "No BSSGP RIM PDU received");
3358 mtc.stop;
Philipp Maier7df55e02020-12-14 23:46:04 +01003359 }
3360 }
3361
3362 f_cleanup();
3363}
Harald Welte8e5932e2020-06-17 22:12:54 +02003364
Pau Espin Pedrol8c74cbb2021-05-04 15:26:56 +02003365testcase TC_rim_eutran_to_geran() runs on test_CT {
3366 var BSSGP_ConnHdlr vc_conn;
3367 f_init();
3368 /* connect RIM related port */
3369 connect(vc_GTP:CLIENT_DEFAULT, self:GTPC);
3370
3371 var GtpPeer peer := {
3372 connId := 1,
3373 remName := mp_sgsn_gtp_ip,
3374 remPort := GTP1C_PORT
3375 }
3376
3377 var template (value) RIM_Routing_Address_GTPC gtpc_dst_addr, gtpc_src_addr;
3378 var template (value) RAN_Information_Request_RIM_Container_GTPC gtpc_rim_req_cont;
3379 var template (value) PDU_BSSGP_RAN_INFORMATION_REQUEST_GTPC gtpc_bssgp_cont;
3380 var template (value) Gtp1cUnitdata gtpc_pdu;
3381
3382 gtpc_dst_addr := t_GTPC_RIM_Routing_Address_cid(g_gb[1].cfg.bvc[0].cell_id);
3383 gtpc_src_addr := t_GTPC_RIM_Routing_Address_enbid(g_gb[1].cfg.bvc[0].cell_id, tac := 3, gnbid := '12345678123456'O);
3384
3385 gtpc_rim_req_cont := ts_GTPC_RAN_Information_Request_RIM_Container(ts_GTPC_RIM_Application_Identity(RIM_APP_ID_NACC),
3386 ts_GTPC_RIM_Sequence_Number(1),
3387 ts_GTPC_RIM_PDU_Indications(false, RIM_PDU_TYPE_SING_REP),
3388 ts_GTPC_RIM_Protocol_Version_Number(1),
3389 tsu_GTPC_RAN_Information_Request_Application_Container_NACC(g_gb[1].cfg.bvc[0].cell_id),
3390 omit);
3391 gtpc_bssgp_cont := ts_GTPC_RAN_Information_Request(ts_GTPC_RIM_Routing_Information(RIM_ADDR_GERAN_CELL_ID, gtpc_dst_addr),
3392 ts_GTPC_RIM_Routing_Information(RIM_ADDR_EUTRAN_NODEB_ID, gtpc_src_addr),
3393 gtpc_rim_req_cont);
3394 gtpc_pdu := ts_GTPC_RANInfoRelay(peer, ts_RANTransparentContainer_RAN_INFO_REQ(gtpc_bssgp_cont));
3395 GTPC.send(gtpc_pdu);
3396
3397 var template RIM_Routing_Address bssgp_dst_addr, bssgp_src_addr;
3398 var template PDU_BSSGP bssgp_rim_pdu_expect;
3399 bssgp_dst_addr := t_RIM_Routing_Address_cid(g_gb[1].cfg.bvc[0].cell_id);
3400 bssgp_src_addr := t_RIM_Routing_Address_enbid(g_gb[1].cfg.bvc[0].cell_id, tac := 3, gnbid := '12345678123456'O);
3401 bssgp_rim_pdu_expect := tr_RAN_INFORMATION_REQUEST(tr_RIM_Routing_Information(RIM_ADDR_GERAN_CELL_ID, bssgp_dst_addr),
3402 tr_RIM_Routing_Information(RIM_ADDR_EUTRAN_NODEB_ID, bssgp_src_addr),
3403 tr_RAN_Information_Request_RIM_Container);
3404 timer T := 2.0;
3405 T.start;
3406 alt {
3407 [] RIM[1].receive(bssgp_rim_pdu_expect) {
3408 setverdict(pass);
3409 T.stop;
3410 }
3411 [] RIM[1].receive {
3412 setverdict(fail, "Unexpected BSSGP RIM PDU received");
3413 }
3414 [] T.timeout {
3415 setverdict(fail, "No BSSGP RIM PDU received");
3416 mtc.stop;
3417 }
3418 }
3419
3420 /* Now also emulate also the response as well and send it back on GB
3421 interface #1. Expect the result on * GTPC */
3422 var template RAN_Information_RIM_Container res_cont;
3423 var template PDU_BSSGP bssgp_rim_pdu;
3424 res_cont := ts_RAN_Information_RIM_Container(ts_RIM_Application_Identity(RIM_APP_ID_NACC),
3425 ts_RIM_Sequence_Number(2),
3426 ts_RIM_PDU_Indications(false, RIM_PDU_TYPE_SING_REP),
3427 ts_RIM_Protocol_Version_Number(1),
3428 tsu_ApplContainer_or_ApplErrContainer_NACC(tsu_ApplContainer_NACC(g_gb[1].cfg.bvc[0].cell_id, false, 3, si_default)),
3429 omit);
3430 bssgp_rim_pdu := ts_PDU_BSSGP_RAN_INFORMATION(ts_RIM_Routing_Information(RIM_ADDR_EUTRAN_NODEB_ID, bssgp_src_addr),
3431 ts_RIM_Routing_Information(RIM_ADDR_GERAN_CELL_ID, bssgp_dst_addr),
3432 res_cont);
3433 RIM[1].send(bssgp_rim_pdu);
3434
3435 var template RAN_Information_RIM_Container_GTPC rim_cont;
3436 var template PDU_BSSGP_RAN_INFORMATION_GTPC gtpc_bssgp_cont_ack;
3437 var template Gtp1cUnitdata gtpc_pdu_exp;
3438 rim_cont := tr_GTPC_RAN_Information_RIM_Container(ts_GTPC_RIM_Application_Identity(RIM_APP_ID_NACC),
3439 ts_GTPC_RIM_Sequence_Number(2),
3440 ts_GTPC_RIM_PDU_Indications(false, RIM_PDU_TYPE_SING_REP),
3441 ts_GTPC_RIM_Protocol_Version_Number(1),
3442 tru_GTPC_ApplContainer_or_ApplErrContainer_NACC(tru_GTPC_ApplContainer_NACC(g_gb[1].cfg.bvc[0].cell_id, false, 3, si_default)),
3443 omit);
3444 gtpc_bssgp_cont_ack := tr_GTPC_RAN_Information(tr_GTPC_RIM_Routing_Information(RIM_ADDR_EUTRAN_NODEB_ID, gtpc_src_addr),
3445 tr_GTPC_RIM_Routing_Information(RIM_ADDR_GERAN_CELL_ID, gtpc_dst_addr),
3446 rim_cont);
3447 gtpc_pdu_exp := tr_GTPC_RANInfoRelay(peer, tr_RANTransparentContainer_RAN_INFO(gtpc_bssgp_cont_ack));
3448
3449 T.start;
3450 alt {
3451 [] GTPC.receive(gtpc_pdu_exp) {
3452 setverdict(pass);
3453 T.stop;
3454 }
3455 [] GTPC.receive {
3456 setverdict(fail, "Unexpected GTPC RIM PDU received");
3457 }
3458 [] T.timeout {
3459 setverdict(fail, "No GTPC RIM PDU received");
3460 mtc.stop;
3461 }
3462 }
3463
3464 f_cleanup();
3465}
3466
Pau Espin Pedrol7c052162021-02-12 17:43:35 +01003467/* Test if the SGSN routes traffic to new cell after the MS attached to it */
3468private function f_TC_cell_change_different_rai_ci_attach(charstring id) runs on BSSGP_ConnHdlr {
3469 var PdpActPars apars := valueof(t_PdpActPars(mp_ggsn_ip));
3470
3471 /* first perform regular attach */
3472 f_gmm_attach(false, false, ran_index := 0);
3473 /* then activate PDP context */
3474 f_pdp_ctx_act(apars, ran_index := 0);
3475 /* then transceive a downlink PDU */
3476 f_gtpu_xceive_mt(apars, f_rnd_octstring(100), ran_index := 0);
3477 f_gtpu_xceive_mo(apars, f_rnd_octstring(200), ran_index := 0);
3478
3479 /* Now attach on different cell: */
3480 f_bssgp_client_unregister(g_pars.imsi, BSSGP_PROC[0]);
3481 f_bssgp_client_register(g_pars.imsi, g_pars.tlli, BSSGP_PROC[1]);
3482 g_pars.net.expect_auth := false;
3483 f_gmm_attach(false, false, ran_index := 1, old_ra := f_cellid_to_RAI(g_pars.bssgp_cell_id[0]));
3484 f_gtpu_xceive_mt(apars, f_rnd_octstring(100), ran_index := 1);
3485 f_gtpu_xceive_mo(apars, f_rnd_octstring(200), ran_index := 1, n_u := 1);
3486}
3487testcase TC_cell_change_different_rai_ci_attach() runs on test_CT {
3488 var BSSGP_ConnHdlr vc_conn;
3489 f_init();
3490 vc_conn := f_start_handler(refers(f_TC_cell_change_different_rai_ci_attach), testcasename(), g_gb, 68);
3491 vc_conn.done;
3492 f_cleanup();
3493}
3494
3495/* Test if the SGSN routes traffic to new cell after the MS attached to it */
3496/* Assumption: g_gb[1] and g_gb[2] configured with same RAC */
3497private function f_TC_cell_change_different_ci_attach(charstring id) runs on BSSGP_ConnHdlr {
3498 var PdpActPars apars := valueof(t_PdpActPars(mp_ggsn_ip));
3499
3500 f_bssgp_client_unregister(g_pars.imsi, BSSGP_PROC[0]);
3501 f_bssgp_client_register(g_pars.imsi, g_pars.tlli, BSSGP_PROC[1]);
3502
3503 /* first perform regular attach */
3504 f_gmm_attach(false, false, ran_index := 1);
3505 /* then activate PDP context */
3506 f_pdp_ctx_act(apars, ran_index := 1);
3507 /* then transceive a downlink PDU */
3508 f_gtpu_xceive_mt(apars, f_rnd_octstring(100), ran_index := 1);
3509 f_gtpu_xceive_mo(apars, f_rnd_octstring(200), ran_index := 1);
3510
3511 /* Now attach on different cell: */
3512 f_bssgp_client_unregister(g_pars.imsi, BSSGP_PROC[1]);
3513 f_bssgp_client_register(g_pars.imsi, g_pars.tlli, BSSGP_PROC[2]);
3514 g_pars.net.expect_auth := false;
3515 f_gmm_attach(false, false, ran_index := 2, old_ra := f_cellid_to_RAI(g_pars.bssgp_cell_id[1]));
3516 f_gtpu_xceive_mt(apars, f_rnd_octstring(100), ran_index := 2);
3517 f_gtpu_xceive_mo(apars, f_rnd_octstring(200), ran_index := 2, n_u := 1);
3518}
3519testcase TC_cell_change_different_ci_attach() runs on test_CT {
3520 var BSSGP_ConnHdlr vc_conn;
3521 f_init();
3522 vc_conn := f_start_handler(refers(f_TC_cell_change_different_ci_attach), testcasename(), g_gb, 69);
3523 vc_conn.done;
3524 f_cleanup();
3525}
3526
3527/* Test if the SGSN silently drops MO data message coming from new BVCI if RAC changed (eg. cell change) */
3528private function f_TC_cell_change_different_rai_ci_data(charstring id) runs on BSSGP_ConnHdlr {
3529 var PdpActPars apars := valueof(t_PdpActPars(mp_ggsn_ip));
3530
3531 /* first perform regular attach */
3532 f_gmm_attach(false, false, ran_index := 0);
3533 /* then activate PDP context */
3534 f_pdp_ctx_act(apars, ran_index := 0);
3535 /* then transceive a downlink PDU */
3536 f_gtpu_xceive_mt(apars, f_rnd_octstring(100), ran_index := 0);
3537 f_gtpu_xceive_mo(apars, f_rnd_octstring(200), ran_index := 0);
3538
3539 /* Send some data over new bvci, it should be silently discarded since
3540 * RAC changed and SGSN expects a RAU to occur in that case */
3541 f_bssgp_client_register(g_pars.imsi, g_pars.tlli, BSSGP_PROC[1]);
3542 var octetstring payload := f_rnd_octstring(200);
3543 var PDU_SN sndcp := valueof(ts_SN_UD(apars.nsapi, payload));
3544 BSSGP[1].send(ts_LLC_UI(enc_PDU_SN(sndcp), apars.sapi, '0'B, 1));
3545 var GtpPeer peer := valueof(ts_GtpPeerU(apars.sgsn_ip_u));
3546 timer T := 2.0;
3547 T.start;
3548 alt {
3549 [] GTP.receive(tr_GTPU_GPDU(peer, apars.ggsn_tei_u, payload)) {
3550 setverdict(fail, "Unexpected GTP message");
3551 }
3552 [] T.timeout { setverdict(pass); }
3553 }
3554
3555 /* Expect SGSN to continue routing DL data to last known NSEI+BVCI */
3556 f_bssgp_client_unregister(g_pars.imsi, BSSGP_PROC[1]);
3557 f_gtpu_xceive_mt(apars, f_rnd_octstring(100), ran_index := 0);
3558}
3559testcase TC_cell_change_different_rai_ci_data() runs on test_CT {
3560 var BSSGP_ConnHdlr vc_conn;
3561 f_init();
3562 vc_conn := f_start_handler(refers(f_TC_cell_change_different_rai_ci_data), testcasename(), g_gb, 70);
3563 vc_conn.done;
3564 f_cleanup();
3565}
3566
3567/* Test if the SGSN routes traffic to new cell after the MS switched cell without re-attaching */
3568/* Assumption: g_gb[1] and g_gb[2] configured with same RAC */
3569private function f_TC_cell_change_different_ci_data(charstring id) runs on BSSGP_ConnHdlr {
3570 var PdpActPars apars := valueof(t_PdpActPars(mp_ggsn_ip));
3571
3572 f_bssgp_client_unregister(g_pars.imsi, BSSGP_PROC[0]);
3573 f_bssgp_client_register(g_pars.imsi, g_pars.tlli, BSSGP_PROC[1]);
3574
3575 /* first perform regular attach */
3576 f_gmm_attach(false, false, ran_index := 1);
3577 /* then activate PDP context */
3578 f_pdp_ctx_act(apars, ran_index := 1);
3579 /* then transceive a downlink PDU */
3580 f_gtpu_xceive_mt(apars, f_rnd_octstring(100), ran_index := 1);
3581 f_gtpu_xceive_mo(apars, f_rnd_octstring(200), ran_index := 1);
3582
3583 /* Now attach on different cell: */
3584 f_bssgp_client_unregister(g_pars.imsi, BSSGP_PROC[1]);
3585 f_bssgp_client_register(g_pars.imsi, g_pars.tlli, BSSGP_PROC[2]);
3586
3587 f_gtpu_xceive_mo(apars, f_rnd_octstring(200), ran_index := 2, n_u := 1);
3588 f_gtpu_xceive_mt(apars, f_rnd_octstring(100), ran_index := 2);
3589}
3590testcase TC_cell_change_different_ci_data() runs on test_CT {
3591 var BSSGP_ConnHdlr vc_conn;
3592 f_init();
3593 vc_conn := f_start_handler(refers(f_TC_cell_change_different_ci_data), testcasename(), g_gb, 71);
3594 vc_conn.done;
3595 f_cleanup();
3596}
3597
Harald Welte5ac31492018-02-15 20:39:13 +01003598control {
Harald Welte5b7c8122018-02-16 21:48:17 +01003599 execute( TC_attach() );
Neels Hofmeyr8df7d152018-03-14 19:03:28 +01003600 execute( TC_attach_mnc3() );
Neels Hofmeyr0ecb2e32018-04-30 15:13:55 +02003601 execute( TC_attach_umts_aka_umts_res() );
3602 execute( TC_attach_umts_aka_gsm_sres() );
Harald Welte5b7c8122018-02-16 21:48:17 +01003603 execute( TC_attach_auth_id_timeout() );
3604 execute( TC_attach_auth_sai_timeout() );
Harald Weltefe253882018-02-17 09:25:00 +01003605 execute( TC_attach_auth_sai_reject() );
Harald Welte5b7c8122018-02-16 21:48:17 +01003606 execute( TC_attach_gsup_lu_timeout() );
Harald Welteb7c14e92018-02-17 09:29:16 +01003607 execute( TC_attach_gsup_lu_reject() );
Harald Welte3823e2e2018-02-16 21:53:48 +01003608 execute( TC_attach_combined() );
Harald Welte76dee092018-02-16 22:12:59 +01003609 execute( TC_attach_accept_all() );
Harald Welteb2124b22018-02-16 22:26:56 +01003610 execute( TC_attach_closed() );
Alexander Couzens667dd7f2018-06-12 16:24:01 +02003611 execute( TC_attach_no_imei_response() );
Alexander Couzens53f20562018-06-12 16:24:12 +02003612 execute( TC_attach_no_imsi_response() );
Alexander Couzensd81876a2018-08-07 12:43:16 +02003613 execute( TC_attach_closed_add_vty(), 20.0 );
3614 execute( TC_attach_check_subscriber_list(), 20.0 );
3615 execute( TC_attach_detach_check_subscriber_list(), 20.0 );
Alexander Couzens0085bd72018-06-12 19:08:44 +02003616 execute( TC_attach_check_complete_resend() );
Alexander Couzensd81876a2018-08-07 12:43:16 +02003617 execute( TC_hlr_location_cancel_request_update(), 20.0 );
3618 execute( TC_hlr_location_cancel_request_withdraw(), 20.0 );
3619 execute( TC_hlr_location_cancel_request_unknown_subscriber_withdraw(), 20.0 );
3620 execute( TC_hlr_location_cancel_request_unknown_subscriber_update(), 20.0 );
Harald Welte04683d02018-02-16 22:43:45 +01003621 execute( TC_rau_unknown() );
Harald Welte91636de2018-02-17 10:16:14 +01003622 execute( TC_attach_rau() );
Alexander Couzensbfda9212018-07-31 03:17:33 +02003623 execute( TC_attach_rau_a_a() );
Alexander Couzensbe837bd2018-07-31 04:20:11 +02003624 execute( TC_attach_rau_a_b() );
Alexander Couzens0c6324f2018-09-14 16:37:04 +02003625 execute( TC_attach_usim_resync() );
Eric Wildc555be52021-05-15 19:48:22 +02003626 execute( TC_attach_usim_a54_a54() );
3627 execute( TC_attach_usim_a54_a53() );
3628 execute( TC_attach_usim_a53_a54() );
3629 execute( TC_attach_usim_a50_a54() );
3630 execute( TC_attach_usim_a54_a50() );
Harald Welte6abb9fe2018-02-17 15:24:48 +01003631 execute( TC_detach_unknown_nopoweroff() );
3632 execute( TC_detach_unknown_poweroff() );
3633 execute( TC_detach_nopoweroff() );
3634 execute( TC_detach_poweroff() );
Harald Welteeded9ad2018-02-17 20:57:34 +01003635 execute( TC_attach_pdp_act() );
Harald Welte835b15f2018-02-18 14:39:11 +01003636 execute( TC_pdp_act_unattached() );
Harald Welte37692d82018-02-18 15:21:34 +01003637 execute( TC_attach_pdp_act_user() );
Harald Welte5b5ca1b2018-02-18 21:25:03 +01003638 execute( TC_attach_pdp_act_ggsn_reject() );
Harald Welte6f203162018-02-18 22:04:55 +01003639 execute( TC_attach_pdp_act_user_deact_mo() );
Harald Welte57b9b7f2018-02-18 22:28:13 +01003640 execute( TC_attach_pdp_act_user_deact_mt() );
Pau Espin Pedrol2a3302a2019-08-15 16:01:20 +02003641 execute( TC_attach_pdp_act_deact_dup() );
Alexander Couzens187ad5d2018-05-02 19:31:10 +02003642 execute( TC_attach_second_attempt() );
Pau Espin Pedrolfcec9142019-08-28 17:33:46 +02003643 execute( TC_attach_echo_timeout() );
Pau Espin Pedrol94013452018-07-17 15:50:21 +02003644 execute( TC_attach_restart_ctr_echo() );
3645 execute( TC_attach_restart_ctr_create() );
Pau Espin Pedrol72edc8a2018-07-16 15:10:08 +02003646 execute( TC_attach_pdp_act_deact_mt_t3395_expire() );
Pau Espin Pedrole6f071f2019-05-29 13:02:42 +02003647 execute( TC_attach_pdp_act_deact_gtp_retrans() );
3648 execute( TC_attach_pdp_act_deact_gtp_retrans_resp() );
Pau Espin Pedrol482dde62018-07-18 13:47:42 +02003649 execute( TC_attach_pdp_act_user_error_ind_ggsn() );
Alexander Couzens6bee0872019-05-11 01:48:50 +02003650 execute( TC_attach_pdp_act_gmm_detach() );
Alexander Couzenscf3c93d2018-08-07 19:48:27 +02003651 execute( TC_attach_gmm_attach_req_while_gmm_attach() );
Harald Weltea05b8072019-04-23 22:35:05 +02003652
Harald Welte2aaac1b2019-05-02 10:02:53 +02003653 execute( TC_xid_empty_l3() );
3654 execute( TC_xid_n201u() );
3655
Harald Weltea05b8072019-04-23 22:35:05 +02003656 execute( TC_llc_null() );
Harald Welte645a1512019-04-23 23:18:23 +02003657 execute( TC_llc_sabm_dm_llgmm() );
3658 execute( TC_llc_sabm_dm_ll5() );
Pau Espin Pedrolce571b52019-11-08 18:32:28 +01003659
Harald Welte8e5932e2020-06-17 22:12:54 +02003660 execute( TC_suspend_nopaging() );
3661 execute( TC_suspend_resume() );
3662 execute( TC_suspend_rau() );
3663 execute( TC_paging_ps() );
3664
Philipp Maier7df55e02020-12-14 23:46:04 +01003665 execute( TC_bssgp_rim_single_report() );
Pau Espin Pedrol8c74cbb2021-05-04 15:26:56 +02003666 execute( TC_rim_eutran_to_geran() );
Philipp Maier7df55e02020-12-14 23:46:04 +01003667
Pau Espin Pedrol7c052162021-02-12 17:43:35 +01003668 execute( TC_cell_change_different_rai_ci_attach() );
3669 execute( TC_cell_change_different_rai_ci_data() );
3670 execute( TC_cell_change_different_ci_attach() );
3671 execute( TC_cell_change_different_ci_data() );
3672
Pau Espin Pedrolce571b52019-11-08 18:32:28 +01003673 /* At the end, may crash osmo-sgsn, see OS#3957, OS#4245 */
3674 execute( TC_attach_req_id_req_ra_update() );
Harald Welte5ac31492018-02-15 20:39:13 +01003675}
Harald Welte96a33b02018-02-04 10:36:22 +01003676
3677
3678
3679}