blob: db7d54b58d529b8749bf650488a29a7539a7091a [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 Welte96a33b02018-02-04 10:36:22 +010014import from General_Types all;
15import from Osmocom_Types all;
Harald Welte37692d82018-02-18 15:21:34 +010016import from Native_Functions all;
Harald Welte96a33b02018-02-04 10:36:22 +010017import from NS_Types all;
18import from NS_Emulation all;
19import from BSSGP_Types all;
20import from BSSGP_Emulation all;
Harald Welte5ac31492018-02-15 20:39:13 +010021import from Osmocom_Gb_Types all;
Harald Welte26fbb6e2019-04-14 17:32:46 +020022import from SCCPasp_Types all;
Harald Welte5ac31492018-02-15 20:39:13 +010023
24import from MobileL3_CommonIE_Types all;
25import from MobileL3_GMM_SM_Types all;
26import from MobileL3_Types all;
27import from L3_Templates all;
28import from L3_Common all;
29
30import from GSUP_Emulation all;
31import from GSUP_Types all;
32import from IPA_Emulation all;
33
Harald Welte26fbb6e2019-04-14 17:32:46 +020034import from RAN_Adapter all;
35import from RAN_Emulation all;
36import from RANAP_Templates all;
37import from RANAP_PDU_Descriptions all;
38import from RANAP_IEs all;
39
Harald Welteeded9ad2018-02-17 20:57:34 +010040import from GTP_Emulation all;
41import from GTP_Templates all;
42import from GTP_CodecPort all;
43import from GTPC_Types all;
44import from GTPU_Types all;
45
Harald Weltea2526a82018-02-18 19:03:36 +010046import from LLC_Types all;
47import from LLC_Templates all;
48
49import from SNDCP_Types all;
50
Harald Weltebd194722018-02-16 22:11:08 +010051import from TELNETasp_PortType all;
52import from Osmocom_VTY_Functions all;
53
Neels Hofmeyr8df7d152018-03-14 19:03:28 +010054import from GSM_RR_Types all;
55
Neels Hofmeyr0ecb2e32018-04-30 15:13:55 +020056import from MobileL3_MM_Types all;
57
Harald Welteeded9ad2018-02-17 20:57:34 +010058
Harald Welte5ac31492018-02-15 20:39:13 +010059modulepar {
60 /* IP/port on which we run our internal GSUP/HLR emulation */
61 charstring mp_hlr_ip := "127.0.0.1";
62 integer mp_hlr_port := 4222;
Harald Welteeded9ad2018-02-17 20:57:34 +010063 charstring mp_ggsn_ip := "127.0.0.2";
Pau Espin Pedrolfcec9142019-08-28 17:33:46 +020064 integer mp_echo_interval := 5; /* in seconds. Only used in test enabling g_use_echo */
Alexander Couzens2c12b242018-07-31 00:30:11 +020065
Alexander Couzensf3c1b412018-08-24 00:42:51 +020066 NSConfigurations mp_nsconfig := {
67 {
68 local_udp_port := 21010,
69 local_ip := "127.0.0.1",
70 remote_udp_port := 23000,
71 remote_ip := "127.0.0.1",
72 nsvci := 97,
Harald Welte5e514fa2018-07-05 00:01:45 +020073 nsei := 96,
74 role_sgsn := false,
75 handle_sns := false
Alexander Couzensf3c1b412018-08-24 00:42:51 +020076 },
77 {
78 local_udp_port := 21011,
79 local_ip := "127.0.0.1",
80 remote_udp_port := 23000,
81 remote_ip := "127.0.0.1",
82 nsvci := 98,
Harald Welte5e514fa2018-07-05 00:01:45 +020083 nsei := 97,
84 role_sgsn := false,
85 handle_sns := false
Alexander Couzensf3c1b412018-08-24 00:42:51 +020086 },
87 {
88 local_udp_port := 21012,
89 local_ip := "127.0.0.1",
90 remote_udp_port := 23000,
91 remote_ip := "127.0.0.1",
92 nsvci := 99,
Harald Welte5e514fa2018-07-05 00:01:45 +020093 nsei := 98,
94 role_sgsn := false,
95 handle_sns := false
Alexander Couzensf3c1b412018-08-24 00:42:51 +020096 }
Alexander Couzens2c12b242018-07-31 00:30:11 +020097 };
Harald Welte26fbb6e2019-04-14 17:32:46 +020098
99 RAN_Configurations mp_ranap_cfg := {
100 {
101 transport := RANAP_TRANSPORT_IuCS,
102 sccp_service_type := "mtp3_itu",
103 sctp_addr := { 23908, "127.0.0.1", 2905, "127.0.0.1" },
104 own_pc := 195,
105 own_ssn := 142,
106 peer_pc := 188, /* 0.23.4 */
107 peer_ssn := 142,
108 sio := '83'O,
109 rctx := 2
110 }
111 }
Harald Welte5ac31492018-02-15 20:39:13 +0100112};
113
114type record GbInstance {
115 NS_CT vc_NS,
116 BSSGP_CT vc_BSSGP,
117 BssgpConfig cfg
118};
Harald Welte96a33b02018-02-04 10:36:22 +0100119
Harald Welte2fa771f2019-05-02 20:13:53 +0200120const integer NUM_GB := 3;
121type record length(NUM_GB) of GbInstance GbInstances;
122type record length(NUM_GB) of NSConfiguration NSConfigurations;
123type record length(NUM_GB) of BssgpCellId BssgpCellIds;
Alexander Couzens51114d12018-07-31 18:41:56 +0200124
Harald Welte26fbb6e2019-04-14 17:32:46 +0200125const integer NUM_RNC := 1;
126type record of RAN_Configuration RAN_Configurations;
127
Harald Welte96a33b02018-02-04 10:36:22 +0100128type component test_CT {
Alexander Couzens51114d12018-07-31 18:41:56 +0200129 var GbInstances g_gb;
Harald Welte26fbb6e2019-04-14 17:32:46 +0200130 var RAN_Adapter g_ranap[NUM_RNC];
Harald Welte96a33b02018-02-04 10:36:22 +0100131
Harald Welte5ac31492018-02-15 20:39:13 +0100132 var GSUP_Emulation_CT vc_GSUP;
133 var IPA_Emulation_CT vc_GSUP_IPA;
134 /* only to get events from IPA underneath GSUP */
135 port IPA_CTRL_PT GSUP_IPA_EVENT;
Harald Welte96a33b02018-02-04 10:36:22 +0100136
Harald Welteeded9ad2018-02-17 20:57:34 +0100137 var GTP_Emulation_CT vc_GTP;
138
Harald Weltebd194722018-02-16 22:11:08 +0100139 port TELNETasp_PT SGSNVTY;
140
Harald Welte96a33b02018-02-04 10:36:22 +0100141 var boolean g_initialized := false;
Pau Espin Pedroldc27e482018-07-10 14:02:49 +0200142 var boolean g_use_echo := false;
Harald Welte96a33b02018-02-04 10:36:22 +0100143};
144
Harald Welte26fbb6e2019-04-14 17:32:46 +0200145type component BSSGP_ConnHdlr extends BSSGP_Client_CT, GSUP_ConnHdlr, GTP_ConnHdlr, RAN_ConnHdlr {
Harald Welte5ac31492018-02-15 20:39:13 +0100146 var BSSGP_ConnHdlrPars g_pars;
Harald Welte62e29582018-02-16 21:17:11 +0100147 timer g_Tguard;
Alexander Couzenscdfb7512018-07-31 15:37:14 +0200148 var LLC_Entities llc;
Harald Welte5ac31492018-02-15 20:39:13 +0100149}
150
151type record SGSN_ConnHdlrNetworkPars {
152 boolean expect_ptmsi,
153 boolean expect_auth,
154 boolean expect_ciph
155};
156
157type record BSSGP_ConnHdlrPars {
158 /* IMEI of the simulated ME */
159 hexstring imei,
Alexander Couzens8f0fb002018-05-02 19:30:55 +0200160 /* IMSI of the simulated MS */
Harald Welte5ac31492018-02-15 20:39:13 +0100161 hexstring imsi,
162 /* MSISDN of the simulated MS (probably unused) */
163 hexstring msisdn,
164 /* P-TMSI allocated to the simulated MS */
165 OCT4 p_tmsi optional,
Harald Welte04683d02018-02-16 22:43:45 +0100166 OCT3 p_tmsi_sig optional,
Harald Welte5ac31492018-02-15 20:39:13 +0100167 /* TLLI of the simulated MS */
168 OCT4 tlli,
Harald Weltef70997d2018-02-17 10:11:19 +0100169 OCT4 tlli_old optional,
Harald Welte5ac31492018-02-15 20:39:13 +0100170 RoutingAreaIdentificationV ra optional,
Alexander Couzens51114d12018-07-31 18:41:56 +0200171 BssgpCellIds bssgp_cell_id,
Harald Welte5ac31492018-02-15 20:39:13 +0100172 AuthVector vec optional,
Harald Welte62e29582018-02-16 21:17:11 +0100173 SGSN_ConnHdlrNetworkPars net,
Harald Welte26fbb6e2019-04-14 17:32:46 +0200174 float t_guard,
175 /* only in IuPS / RANAP case */
176 SCCP_PAR_Address sccp_addr_local,
177 SCCP_PAR_Address sccp_addr_peer
Harald Welte5ac31492018-02-15 20:39:13 +0100178};
179
Alexander Couzens89508702018-07-31 04:16:10 +0200180private function f_cellid_to_RAI(in BssgpCellId cell_id) return RoutingAreaIdentificationV {
Alexander Couzensc7dddbd2019-04-11 19:18:35 +0200181 /* mcc_mnc is encoded as of 24.008 10.5.5.15 */
Alexander Couzens89508702018-07-31 04:16:10 +0200182 var BcdMccMnc mcc_mnc := cell_id.ra_id.lai.mcc_mnc;
183
184 var RoutingAreaIdentificationV ret := {
185 mccDigit1 := mcc_mnc[0],
186 mccDigit2 := mcc_mnc[1],
187 mccDigit3 := mcc_mnc[2],
Alexander Couzensc7dddbd2019-04-11 19:18:35 +0200188 mncDigit3 := mcc_mnc[3],
189 mncDigit1 := mcc_mnc[4],
190 mncDigit2 := mcc_mnc[5],
Alexander Couzens89508702018-07-31 04:16:10 +0200191 lac := int2oct(cell_id.ra_id.lai.lac, 16),
192 rac := int2oct(cell_id.ra_id.rac, 8)
193 }
194 return ret;
195};
196
Alexander Couzens51114d12018-07-31 18:41:56 +0200197private function f_init_gb(inout GbInstance gb, charstring id, integer offset) runs on test_CT {
198 gb.vc_NS := NS_CT.create(id & "-NS" & int2str(offset));
199 gb.vc_BSSGP := BSSGP_CT.create(id & "-BSSGP" & int2str(offset));
Harald Welte5ac31492018-02-15 20:39:13 +0100200 /* connect lower end of BSSGP emulation with NS upper port */
201 connect(gb.vc_BSSGP:BSCP, gb.vc_NS:NS_SP);
202 /* connect lower end of NS emulation to NS codec port (on top of IPL4) */
203 map(gb.vc_NS:NSCP, system:NS_CODEC_PORT);
204
Alexander Couzensf3c1b412018-08-24 00:42:51 +0200205 gb.vc_NS.start(NSStart(mp_nsconfig[offset]));
Harald Welte5ac31492018-02-15 20:39:13 +0100206 gb.vc_BSSGP.start(BssgpStart(gb.cfg));
207}
208
209private function f_init_gsup(charstring id) runs on test_CT {
210 id := id & "-GSUP";
211 var GsupOps ops := {
212 create_cb := refers(GSUP_Emulation.ExpectedCreateCallback)
213 };
214
215 vc_GSUP_IPA := IPA_Emulation_CT.create(id & "-IPA");
216 vc_GSUP := GSUP_Emulation_CT.create(id);
217
218 map(vc_GSUP_IPA:IPA_PORT, system:IPA_CODEC_PT);
219 connect(vc_GSUP:GSUP, vc_GSUP_IPA:IPA_GSUP_PORT);
220 /* we use this hack to get events like ASP_IPA_EVENT_UP */
221 connect(vc_GSUP_IPA:IPA_CTRL_PORT, self:GSUP_IPA_EVENT);
222
223 vc_GSUP.start(GSUP_Emulation.main(ops, id));
224 vc_GSUP_IPA.start(IPA_Emulation.main_server(mp_hlr_ip, mp_hlr_port));
225
226 /* wait for incoming connection to GSUP port before proceeding */
227 timer T := 10.0;
228 T.start;
229 alt {
230 [] GSUP_IPA_EVENT.receive(t_ASP_IPA_EVT_UD(ASP_IPA_EVENT_UP)) { }
231 [] T.timeout {
232 setverdict(fail, "No connection to GSUP Port");
Daniel Willmannafce8662018-07-06 23:11:32 +0200233 mtc.stop;
Harald Welte5ac31492018-02-15 20:39:13 +0100234 }
235 }
236}
237
Harald Welteeded9ad2018-02-17 20:57:34 +0100238private function f_init_gtp(charstring id) runs on test_CT {
239 id := id & "-GTP";
240
241 var GtpEmulationCfg gtp_cfg := {
242 gtpc_bind_ip := mp_ggsn_ip,
243 gtpc_bind_port := GTP1C_PORT,
244 gtpu_bind_ip := mp_ggsn_ip,
245 gtpu_bind_port := GTP1U_PORT,
246 sgsn_role := false
247 };
248
249 vc_GTP := GTP_Emulation_CT.create(id);
250 vc_GTP.start(GTP_Emulation.main(gtp_cfg));
251}
252
Harald Weltebd194722018-02-16 22:11:08 +0100253private function f_init_vty() runs on test_CT {
254 map(self:SGSNVTY, system:SGSNVTY);
255 f_vty_set_prompts(SGSNVTY);
256 f_vty_transceive(SGSNVTY, "enable");
Alexander Couzens1d1744f2018-08-07 11:56:14 +0200257 f_vty_transceive(SGSNVTY, "reset sgsn state");
Harald Weltebd194722018-02-16 22:11:08 +0100258 f_vty_config(SGSNVTY, "sgsn", "auth-policy remote");
259}
260
Pau Espin Pedroldc27e482018-07-10 14:02:49 +0200261private function f_vty_enable_echo_interval(boolean enable) runs on test_CT {
262 if (enable) {
Pau Espin Pedrolfcec9142019-08-28 17:33:46 +0200263 f_vty_config(SGSNVTY, "sgsn", "ggsn 0 echo-interval " & int2str(mp_echo_interval));
Pau Espin Pedroldc27e482018-07-10 14:02:49 +0200264 } else {
265 f_vty_config(SGSNVTY, "sgsn", "ggsn 0 no echo-interval");
266 }
267}
268
Harald Weltebd194722018-02-16 22:11:08 +0100269
Alexander Couzensc7dddbd2019-04-11 19:18:35 +0200270/* mcc_mnc is 24.008 10.5.5.15 encoded. 262 42 */
271function f_init(BcdMccMnc mcc_mnc := '262F42'H) runs on test_CT {
Harald Welte26fbb6e2019-04-14 17:32:46 +0200272 var integer i;
273
Harald Welte96a33b02018-02-04 10:36:22 +0100274 if (g_initialized == true) {
275 return;
276 }
277 g_initialized := true;
Harald Welte5ac31492018-02-15 20:39:13 +0100278 g_gb[0].cfg := {
279 nsei := 96,
280 bvci := 196,
281 cell_id := {
282 ra_id := {
283 lai := {
Neels Hofmeyr8df7d152018-03-14 19:03:28 +0100284 mcc_mnc := mcc_mnc, lac := 13135},
Harald Welte5ac31492018-02-15 20:39:13 +0100285 rac := 0
286 },
287 cell_id := 20960
288 },
289 sgsn_role := false
290 };
Alexander Couzens5e2ba752018-07-03 15:13:07 +0200291 g_gb[1].cfg := {
292 nsei := 97,
293 bvci := 210,
294 cell_id := {
295 ra_id := {
296 lai := {
297 mcc_mnc := mcc_mnc, lac := 13200},
298 rac := 0
299 },
300 cell_id := 20961
301 },
302 sgsn_role := false
303 };
304 g_gb[2].cfg := {
305 nsei := 98,
306 bvci := 220,
307 cell_id := {
308 ra_id := {
309 lai := {
310 mcc_mnc := mcc_mnc, lac := 13300},
311 rac := 0
312 },
313 cell_id := 20962
314 },
315 sgsn_role := false
316 };
Harald Welte96a33b02018-02-04 10:36:22 +0100317
Alexander Couzens1d1744f2018-08-07 11:56:14 +0200318 f_init_vty();
Alexander Couzens51114d12018-07-31 18:41:56 +0200319 f_init_gb(g_gb[0], "SGSN_Test-Gb0", 0);
320 f_init_gb(g_gb[1], "SGSN_Test-Gb1", 1);
321 f_init_gb(g_gb[2], "SGSN_Test-Gb2", 2);
Harald Welte26fbb6e2019-04-14 17:32:46 +0200322
323 for (i := 0; i < NUM_RNC; i := i+1) {
324 f_ran_adapter_init(g_ranap[i], mp_ranap_cfg[i], "SGSN_Test_" & int2str(i), RNC_RanOps);
325 f_ran_adapter_start(g_ranap[i]);
326 }
Harald Welte5ac31492018-02-15 20:39:13 +0100327 f_init_gsup("SGSN_Test");
Harald Welteeded9ad2018-02-17 20:57:34 +0100328 f_init_gtp("SGSN_Test");
Pau Espin Pedroldc27e482018-07-10 14:02:49 +0200329 f_vty_enable_echo_interval(g_use_echo);
Harald Welte5ac31492018-02-15 20:39:13 +0100330}
Harald Welte96a33b02018-02-04 10:36:22 +0100331
Harald Welte26fbb6e2019-04-14 17:32:46 +0200332private function RncUnitdataCallback(RANAP_PDU ranap)
333runs on RAN_Emulation_CT return template RANAP_PDU {
334 var template RANAP_PDU resp := omit;
335
336 log ("RANAP_RncUnitDataCallback");
337 /* answer all RESET with RESET ACK */
338 if (match(ranap, tr_RANAP_Reset)) {
339 log("RANAP_RncUnitdataCallback: Responding to RESET with RESET-ACK");
340 var CN_DomainIndicator dom;
341 dom := ranap.initiatingMessage.value_.Reset.protocolIEs[1].value_.cN_DomainIndicator;
342 resp := ts_RANAP_ResetAck(dom);
343 }
344 return resp;
345}
346
347const RanOps RNC_RanOps := {
348 ranap_create_cb := refers(RAN_Emulation.RanapExpectedCreateCallback),
349 ranap_unitdata_cb := refers(RncUnitdataCallback),
350 ps_domain := true,
351 decode_dtap := true,
352 role_ms := true,
353 protocol := RAN_PROTOCOL_RANAP,
354 transport := RANAP_TRANSPORT_IuCS,
355 use_osmux := false,
356 sccp_addr_local := omit,
357 sccp_addr_peer := omit
358};
359
Harald Welte5ac31492018-02-15 20:39:13 +0100360type function void_fn(charstring id) runs on BSSGP_ConnHdlr;
361
362/* helper function to create, connect and start a BSSGP_ConnHdlr component */
Alexander Couzens51114d12018-07-31 18:41:56 +0200363function f_start_handler(void_fn fn, charstring id, GbInstances gb, integer imsi_suffix,
Harald Welte62e29582018-02-16 21:17:11 +0100364 float t_guard := 30.0)
Harald Welte5ac31492018-02-15 20:39:13 +0100365runs on test_CT return BSSGP_ConnHdlr {
366 var BSSGP_ConnHdlr vc_conn;
367 var SGSN_ConnHdlrNetworkPars net_pars := {
368 expect_ptmsi := true,
369 expect_auth := true,
370 expect_ciph := false
371 };
372 var BSSGP_ConnHdlrPars pars := {
373 imei := f_gen_imei(imsi_suffix),
374 imsi := f_gen_imsi(imsi_suffix),
375 msisdn := f_gen_msisdn(imsi_suffix),
376 p_tmsi := omit,
Harald Welte04683d02018-02-16 22:43:45 +0100377 p_tmsi_sig := omit,
Harald Welte14a0f942018-02-16 20:42:23 +0100378 tlli := f_gprs_tlli_random(),
Harald Weltef70997d2018-02-17 10:11:19 +0100379 tlli_old := omit,
Harald Welte5ac31492018-02-15 20:39:13 +0100380 ra := omit,
Alexander Couzens51114d12018-07-31 18:41:56 +0200381 bssgp_cell_id := { gb[0].cfg.cell_id, gb[1].cfg.cell_id, gb[2].cfg.cell_id },
Harald Welte5ac31492018-02-15 20:39:13 +0100382 vec := omit,
Harald Welte62e29582018-02-16 21:17:11 +0100383 net := net_pars,
Harald Welte26fbb6e2019-04-14 17:32:46 +0200384 t_guard := t_guard,
385 sccp_addr_local := g_ranap[0].sccp_addr_own,
386 sccp_addr_peer := g_ranap[0].sccp_addr_peer
Harald Welte5ac31492018-02-15 20:39:13 +0100387 };
388
389 vc_conn := BSSGP_ConnHdlr.create(id);
Alexander Couzens51114d12018-07-31 18:41:56 +0200390 connect(vc_conn:BSSGP[0], gb[0].vc_BSSGP:BSSGP_SP);
391 connect(vc_conn:BSSGP_PROC[0], gb[0].vc_BSSGP:BSSGP_PROC);
392 connect(vc_conn:BSSGP[1], gb[1].vc_BSSGP:BSSGP_SP);
393 connect(vc_conn:BSSGP_PROC[1], gb[1].vc_BSSGP:BSSGP_PROC);
394 connect(vc_conn:BSSGP[2], gb[2].vc_BSSGP:BSSGP_SP);
395 connect(vc_conn:BSSGP_PROC[2], gb[2].vc_BSSGP:BSSGP_PROC);
Harald Welte5ac31492018-02-15 20:39:13 +0100396
Harald Welte26fbb6e2019-04-14 17:32:46 +0200397 /* FIXME: support multiple RNCs */
398 connect(vc_conn:BSSAP, g_ranap[0].vc_RAN:CLIENT);
399 connect(vc_conn:BSSAP_PROC, g_ranap[0].vc_RAN:PROC);
400
Harald Welte5ac31492018-02-15 20:39:13 +0100401 connect(vc_conn:GSUP, vc_GSUP:GSUP_CLIENT);
402 connect(vc_conn:GSUP_PROC, vc_GSUP:GSUP_PROC);
403
Harald Welteeded9ad2018-02-17 20:57:34 +0100404 connect(vc_conn:GTP, vc_GTP:CLIENT);
405 connect(vc_conn:GTP_PROC, vc_GTP:CLIENT_PROC);
406
Harald Welte5ac31492018-02-15 20:39:13 +0100407 vc_conn.start(f_handler_init(fn, id, pars));
408 return vc_conn;
409}
410
Harald Welte62e29582018-02-16 21:17:11 +0100411private altstep as_Tguard() runs on BSSGP_ConnHdlr {
412 [] g_Tguard.timeout {
413 setverdict(fail, "Tguard timeout");
Daniel Willmannafce8662018-07-06 23:11:32 +0200414 mtc.stop;
Harald Welte62e29582018-02-16 21:17:11 +0100415 }
416}
417
Harald Welte5ac31492018-02-15 20:39:13 +0100418/* first function called in every ConnHdlr */
419private function f_handler_init(void_fn fn, charstring id, BSSGP_ConnHdlrPars pars)
420runs on BSSGP_ConnHdlr {
421 /* do some common stuff like setting up g_pars */
422 g_pars := pars;
423
Alexander Couzenscdfb7512018-07-31 15:37:14 +0200424 llc := f_llc_create(false);
425
Harald Welte5ac31492018-02-15 20:39:13 +0100426 /* register with BSSGP core */
Alexander Couzens51114d12018-07-31 18:41:56 +0200427 f_bssgp_client_register(g_pars.imsi, g_pars.tlli, g_pars.bssgp_cell_id[0]);
Harald Welte5ac31492018-02-15 20:39:13 +0100428 /* tell GSUP dispatcher to send this IMSI to us */
429 f_create_gsup_expect(hex2str(g_pars.imsi));
Harald Welteeded9ad2018-02-17 20:57:34 +0100430 /* tell GTP dispatcher to send this IMSI to us */
431 f_gtp_register_imsi(g_pars.imsi);
Harald Welte5ac31492018-02-15 20:39:13 +0100432
Harald Welte62e29582018-02-16 21:17:11 +0100433 g_Tguard.start(pars.t_guard);
434 activate(as_Tguard());
435
Harald Welte5ac31492018-02-15 20:39:13 +0100436 /* call the user-supplied test case function */
437 fn.apply(id);
438 f_bssgp_client_unregister(g_pars.imsi);
Harald Welte96a33b02018-02-04 10:36:22 +0100439}
440
441/* TODO:
Harald Welte96a33b02018-02-04 10:36:22 +0100442 * Detach without Attach
443 * SM procedures without attach / RAU
444 * ATTACH / RAU
445 ** with / without authentication
446 ** with / without P-TMSI allocation
Harald Welte96a33b02018-02-04 10:36:22 +0100447 * re-transmissions of LLC frames
448 * PDP Context activation
449 ** with different GGSN config in SGSN VTY
450 ** with different PDP context type (v4/v6/v46)
451 ** timeout from GGSN
Harald Welte6f203162018-02-18 22:04:55 +0100452 ** multiple / secondary PDP context
Harald Welte96a33b02018-02-04 10:36:22 +0100453 */
454
455testcase TC_wait_ns_up() runs on test_CT {
456 f_init();
457 f_sleep(20.0);
458}
459
Harald Weltea05b8072019-04-23 22:35:05 +0200460function f_send_llc(template (value) PDU_LLC llc_pdu, integer gb_index := 0) runs on BSSGP_ConnHdlr {
461 var octetstring llc_enc := enc_PDU_LLC(valueof(llc_pdu));
462 BSSGP[gb_index].send(ts_BSSGP_UL_UD(g_pars.tlli, g_pars.bssgp_cell_id[gb_index], llc_enc));
463}
464
Alexander Couzenscdfb7512018-07-31 15:37:14 +0200465function f_send_l3_gmm_llc(template PDU_L3_MS_SGSN l3_mo, integer gb_index := 0) runs on BSSGP_ConnHdlr {
466 var octetstring l3_enc := enc_PDU_L3_MS_SGSN(valueof(l3_mo));
467 var BIT4 sapi := f_llc_sapi_by_l3_mo(valueof(l3_mo));
468 var integer n_u := f_llc_get_n_u_tx(llc[bit2int(sapi)]);
Alexander Couzensad352222019-05-11 02:06:04 +0200469 f_send_llc(ts_LLC_UI(l3_enc, sapi, '0'B, n_u), gb_index);
Alexander Couzenscdfb7512018-07-31 15:37:14 +0200470}
471
Harald Welteca362462019-05-02 20:11:21 +0200472altstep as_mm_identity(integer gb_idx := 0) runs on BSSGP_ConnHdlr {
Neels Hofmeyr8df7d152018-03-14 19:03:28 +0100473 var MobileL3_CommonIE_Types.MobileIdentityLV mi;
Harald Welte955aa942019-05-03 01:29:29 +0200474 [] BSSGP[gb_idx].receive(tr_GMM_ID_REQ('001'B)) {
Harald Welte5ac31492018-02-15 20:39:13 +0100475 mi := valueof(ts_MI_IMSI_LV(g_pars.imsi));
Harald Welteca362462019-05-02 20:11:21 +0200476 f_send_l3_gmm_llc(ts_GMM_ID_RESP(mi), gb_idx);
Harald Welte5ac31492018-02-15 20:39:13 +0100477 repeat;
478 }
Harald Welte955aa942019-05-03 01:29:29 +0200479 [] BSSGP[gb_idx].receive(tr_GMM_ID_REQ('010'B)) {
Harald Welte5ac31492018-02-15 20:39:13 +0100480 mi := valueof(ts_MI_IMEI_LV(g_pars.imei));
Harald Welteca362462019-05-02 20:11:21 +0200481 f_send_l3_gmm_llc(ts_GMM_ID_RESP(mi), gb_idx);
Harald Welte5ac31492018-02-15 20:39:13 +0100482 repeat;
483 }
484}
Harald Welte96a33b02018-02-04 10:36:22 +0100485
Harald Welteca362462019-05-02 20:11:21 +0200486/* receive a L3 (GMM/SM) message over whatever is the appropriate lower-layer bearer */
487function f_receive_l3(template PDU_L3_SGSN_MS rx_tpl := ?, integer gb_idx := 0)
488runs on BSSGP_ConnHdlr return PDU_L3_SGSN_MS {
Harald Welteca362462019-05-02 20:11:21 +0200489 var PDU_L3_SGSN_MS l3_mt;
490 alt {
Harald Welte955aa942019-05-03 01:29:29 +0200491 [] BSSGP[gb_idx].receive(rx_tpl) -> value l3_mt { }
Harald Welteca362462019-05-02 20:11:21 +0200492 }
493 return l3_mt;
494}
495
Neels Hofmeyr0ecb2e32018-04-30 15:13:55 +0200496/* perform GMM authentication (if expected).
497 * Note, for umts_aka_challenge to work, the revisionLevelIndicatior needs to
498 * be 1 to mark R99 capability, in the GMM Attach Request, see f_gmm_attach(). */
Harald Welteca362462019-05-02 20:11:21 +0200499function f_gmm_auth (boolean umts_aka_challenge := false, boolean force_gsm_sres := false, integer gb_idx := 0) runs on BSSGP_ConnHdlr {
Harald Welte5ac31492018-02-15 20:39:13 +0100500 var PDU_L3_MS_SGSN l3_mo;
501 var PDU_L3_SGSN_MS l3_mt;
Harald Welteca362462019-05-02 20:11:21 +0200502 var default di := activate(as_mm_identity(gb_idx));
Harald Welte5ac31492018-02-15 20:39:13 +0100503 if (g_pars.net.expect_auth) {
Neels Hofmeyr0ecb2e32018-04-30 15:13:55 +0200504 var GSUP_IE auth_tuple;
505 var template AuthenticationParameterAUTNTLV autn;
506
507 if (umts_aka_challenge) {
508 g_pars.vec := f_gen_auth_vec_3g();
509 autn := {
510 elementIdentifier := '28'O,
511 lengthIndicator := lengthof(g_pars.vec.autn),
512 autnValue := g_pars.vec.autn
513 };
514
515 auth_tuple := valueof(ts_GSUP_IE_AuthTuple2G3G(g_pars.vec.rand,
516 g_pars.vec.sres,
517 g_pars.vec.kc,
518 g_pars.vec.ik,
519 g_pars.vec.ck,
520 g_pars.vec.autn,
521 g_pars.vec.res));
522 log("GSUP sends 2G and 3G auth tuples", auth_tuple);
523 } else {
524 g_pars.vec := f_gen_auth_vec_2g();
525 autn := omit;
526 auth_tuple := valueof(ts_GSUP_IE_AuthTuple2G(g_pars.vec.rand,
527 g_pars.vec.sres,
528 g_pars.vec.kc));
529 log("GSUP sends only 2G auth tuple", auth_tuple);
530 }
Harald Welteca362462019-05-02 20:11:21 +0200531
Harald Welte5ac31492018-02-15 20:39:13 +0100532 GSUP.receive(tr_GSUP_SAI_REQ(g_pars.imsi));
533 GSUP.send(ts_GSUP_SAI_RES(g_pars.imsi, auth_tuple));
Neels Hofmeyr0ecb2e32018-04-30 15:13:55 +0200534
535 var template PDU_L3_SGSN_MS auth_ciph_req := tr_GMM_AUTH_REQ(g_pars.vec.rand);
536 auth_ciph_req.msgs.gprs_mm.authenticationAndCipheringRequest.authenticationParameterAUTN := autn;
Harald Welteca362462019-05-02 20:11:21 +0200537 l3_mt := f_receive_l3(auth_ciph_req, gb_idx);
Harald Welte5ac31492018-02-15 20:39:13 +0100538 var BIT4 ac_ref := l3_mt.msgs.gprs_mm.authenticationAndCipheringRequest.acReferenceNumber.valueField;
Neels Hofmeyr0ecb2e32018-04-30 15:13:55 +0200539 var template PDU_L3_MS_SGSN auth_ciph_resp := ts_GMM_AUTH_RESP_2G(ac_ref, g_pars.vec.sres);
540
541 if (umts_aka_challenge and not force_gsm_sres) {
542 /* set UMTS response instead */
543 auth_ciph_resp.msgs.gprs_mm.authenticationAndCipheringResponse.authenticationParResp := {
544 valueField := substr(g_pars.vec.res, 0, 4)
545 };
546 auth_ciph_resp.msgs.gprs_mm.authenticationAndCipheringResponse.authenticationRespParExt := {
547 elementIdentifier := '21'O,
548 lengthIndicator := lengthof(g_pars.vec.res) - 4,
549 valueField := substr(g_pars.vec.res, 4, lengthof(g_pars.vec.res) - 4)
550 };
551 }
552
553 l3_mo := valueof(auth_ciph_resp);
Harald Welte5ac31492018-02-15 20:39:13 +0100554 if (ispresent(l3_mt.msgs.gprs_mm.authenticationAndCipheringRequest.imeisvRequest) and
555 l3_mt.msgs.gprs_mm.authenticationAndCipheringRequest.imeisvRequest.valueField == '001'B) {
556 l3_mo.msgs.gprs_mm.authenticationAndCipheringResponse.imeisv :=
557 valueof(ts_MI_IMEISV_TLV(g_pars.imei & '0'H));
558 }
Harald Welteca362462019-05-02 20:11:21 +0200559 f_send_l3_gmm_llc(l3_mo, gb_idx);
Harald Welte76dee092018-02-16 22:12:59 +0100560 } else {
561 /* wait for identity procedure */
562 f_sleep(1.0);
Harald Welte5ac31492018-02-15 20:39:13 +0100563 }
Harald Welte76dee092018-02-16 22:12:59 +0100564
Harald Welte5ac31492018-02-15 20:39:13 +0100565 deactivate(di);
566}
567
Alexander Couzens90fe6a22018-07-31 19:37:32 +0200568function f_upd_ptmsi_and_tlli(OCT4 p_tmsi, integer bssgp_index := 0) runs on BSSGP_ConnHdlr {
Harald Weltef70997d2018-02-17 10:11:19 +0100569 g_pars.p_tmsi := p_tmsi;
570 /* update TLLI */
571 g_pars.tlli_old := g_pars.tlli;
572 g_pars.tlli := g_pars.p_tmsi or4b 'c0000000'O;
Alexander Couzens90fe6a22018-07-31 19:37:32 +0200573 f_bssgp_client_llgmm_assign(g_pars.tlli_old, g_pars.tlli, BSSGP_PROC[bssgp_index]);
Harald Weltef70997d2018-02-17 10:11:19 +0100574}
575
Harald Welte04683d02018-02-16 22:43:45 +0100576function f_process_attach_accept(PDU_GMM_AttachAccept aa) runs on BSSGP_ConnHdlr {
577 /* mandatory IE */
Neels Hofmeyr8df7d152018-03-14 19:03:28 +0100578 var hexstring aa_plmn := f_RAI_to_plmn_hexstr(aa.routingAreaIdentification);
Alexander Couzens51114d12018-07-31 18:41:56 +0200579 if (not (g_pars.bssgp_cell_id[0].ra_id.lai.mcc_mnc == aa_plmn)) {
Neels Hofmeyr8df7d152018-03-14 19:03:28 +0100580 setverdict(fail, "mismatching PLMN in Attach Accept: " & hex2str(aa_plmn)
Alexander Couzens51114d12018-07-31 18:41:56 +0200581 & "; expected " & hex2str(g_pars.bssgp_cell_id[0].ra_id.lai.mcc_mnc));
Daniel Willmannafce8662018-07-06 23:11:32 +0200582 mtc.stop;
Neels Hofmeyr8df7d152018-03-14 19:03:28 +0100583 }
Harald Welte04683d02018-02-16 22:43:45 +0100584 g_pars.ra := aa.routingAreaIdentification;
585 if (ispresent(aa.allocatedPTMSI)) {
586 if (not g_pars.net.expect_ptmsi) {
587 setverdict(fail, "unexpected P-TMSI allocation");
Daniel Willmannafce8662018-07-06 23:11:32 +0200588 mtc.stop;
Harald Welte04683d02018-02-16 22:43:45 +0100589 }
Harald Weltef70997d2018-02-17 10:11:19 +0100590 f_upd_ptmsi_and_tlli(aa.allocatedPTMSI.mobileIdentityLV.mobileIdentityV.oddEvenInd_identity.tmsi_ptmsi.octets);
Harald Welte04683d02018-02-16 22:43:45 +0100591 }
592 if (ispresent(aa.msIdentity)) {
593 setverdict(fail, "unexpected TMSI allocation in non-combined attach");
Daniel Willmannafce8662018-07-06 23:11:32 +0200594 mtc.stop;
Harald Welte04683d02018-02-16 22:43:45 +0100595 }
596 /* P-TMSI.sig */
597 if (ispresent(aa.ptmsiSignature)) {
598 g_pars.p_tmsi_sig := aa.ptmsiSignature.valueField;
599 }
600 /* updateTimer */
601 // aa.readyTimer
602 /* T3302, T3319, T3323, T3312_ext, T3324 */
603}
604
Alexander Couzens90fe6a22018-07-31 19:37:32 +0200605function f_process_rau_accept(PDU_GMM_RoutingAreaUpdateAccept ra, integer bssgp_index := 0) runs on BSSGP_ConnHdlr {
Harald Welte91636de2018-02-17 10:16:14 +0100606 /* mandatory IE */
607 g_pars.ra := ra.routingAreaId;
608 if (ispresent(ra.allocatedPTMSI)) {
609 if (not g_pars.net.expect_ptmsi) {
610 setverdict(fail, "unexpected P-TMSI allocation");
Daniel Willmannafce8662018-07-06 23:11:32 +0200611 mtc.stop;
Harald Welte91636de2018-02-17 10:16:14 +0100612 }
Alexander Couzens90fe6a22018-07-31 19:37:32 +0200613 f_upd_ptmsi_and_tlli(ra.allocatedPTMSI.mobileIdentityLV.mobileIdentityV.oddEvenInd_identity.tmsi_ptmsi.octets, bssgp_index);
Harald Welte91636de2018-02-17 10:16:14 +0100614 }
615 if (ispresent(ra.msIdentity)) {
616 setverdict(fail, "unexpected TMSI allocation in non-combined attach");
Daniel Willmannafce8662018-07-06 23:11:32 +0200617 mtc.stop;
Harald Welte91636de2018-02-17 10:16:14 +0100618 }
619 /* P-TMSI.sig */
620 if (ispresent(ra.ptmsiSignature)) {
621 g_pars.p_tmsi_sig := ra.ptmsiSignature.valueField;
622 }
623 /* updateTimer */
624 // aa.readyTimer
625 /* T3302, T3319, T3323, T3312_ext, T3324 */
626}
627
628
Harald Welte5a4fa042018-02-16 20:59:21 +0100629function f_random_RAI(HEX0_3n mcc := '262'H, HEX0_3n mnc := '42'H) return RoutingAreaIdentificationV {
630 return f_RAI(mcc, mnc, f_rnd_octstring(2), f_rnd_octstring(1));
631}
632
Harald Welte23178c52018-02-17 09:36:33 +0100633/* return a MobileIdentityLV: P-TMSI if we have one, IMSI otherwise */
Neels Hofmeyr8df7d152018-03-14 19:03:28 +0100634private function f_mi_get_lv() runs on BSSGP_ConnHdlr return MobileL3_CommonIE_Types.MobileIdentityLV {
Harald Welte23178c52018-02-17 09:36:33 +0100635 if (ispresent(g_pars.p_tmsi)) {
636 return valueof(ts_MI_TMSI_LV(g_pars.p_tmsi));
637 } else {
638 return valueof(ts_MI_IMSI_LV(g_pars.imsi));
639 }
640}
641
Harald Welte311ec272018-02-17 09:40:03 +0100642private function f_gmm_gsup_lu_isd() runs on BSSGP_ConnHdlr {
Harald Welteeded9ad2018-02-17 20:57:34 +0100643 var GSUP_PDU gsup;
Harald Welte311ec272018-02-17 09:40:03 +0100644 /* Expect MSC to perform LU with HLR */
645 GSUP.receive(tr_GSUP_UL_REQ(g_pars.imsi));
Harald Welteeded9ad2018-02-17 20:57:34 +0100646 gsup := valueof(ts_GSUP_ISD_REQ(g_pars.imsi, g_pars.msisdn));
647 gsup.ies := gsup.ies & { valueof(ts_GSUP_IE_PdpInfo(char2oct("*"), '0121'O, ''O)) };
648 GSUP.send(gsup);
Harald Welte311ec272018-02-17 09:40:03 +0100649 GSUP.receive(tr_GSUP_ISD_RES(g_pars.imsi));
650 GSUP.send(ts_GSUP_UL_RES(g_pars.imsi));
651}
652
Harald Welteca362462019-05-02 20:11:21 +0200653friend function f_gmm_attach(boolean umts_aka_challenge, boolean force_gsm_sres, integer gb_idx := 0) runs on BSSGP_ConnHdlr {
Harald Welte5a4fa042018-02-16 20:59:21 +0100654 var RoutingAreaIdentificationV old_ra := f_random_RAI();
Neels Hofmeyr0ecb2e32018-04-30 15:13:55 +0200655 var template PDU_L3_MS_SGSN attach_req := ts_GMM_ATTACH_REQ(f_mi_get_lv(), old_ra, false, false, omit, omit);
Harald Welteca362462019-05-02 20:11:21 +0200656 var PDU_L3_SGSN_MS l3_mt;
Harald Welte5ac31492018-02-15 20:39:13 +0100657
Neels Hofmeyr0ecb2e32018-04-30 15:13:55 +0200658 /* indicate R99 capability of the MS to enable UMTS AKA in presence of
659 * 3G auth vectors */
660 attach_req.msgs.gprs_mm.attachRequest.msNetworkCapability.msNetworkCapabilityV.revisionLevelIndicatior := '1'B;
661 /* The thing is, if the solSACapability is 'omit', then the
662 * revisionLevelIndicatior is at the wrong place! */
663 attach_req.msgs.gprs_mm.attachRequest.msNetworkCapability.msNetworkCapabilityV.solSACapability := '0'B;
664
Harald Welteca362462019-05-02 20:11:21 +0200665 f_send_l3_gmm_llc(attach_req, gb_idx);
666 f_gmm_auth(umts_aka_challenge, force_gsm_sres, gb_idx);
Alexander Couzens5844d5b2018-05-14 06:30:56 +0200667 /* Expect SGSN to perform LU with HLR */
Harald Welte311ec272018-02-17 09:40:03 +0100668 f_gmm_gsup_lu_isd();
Harald Welte5ac31492018-02-15 20:39:13 +0100669
Harald Welteca362462019-05-02 20:11:21 +0200670 l3_mt := f_receive_l3(tr_GMM_ATTACH_ACCEPT('001'B, ?, ?), gb_idx);
671 f_process_attach_accept(l3_mt.msgs.gprs_mm.attachAccept);
672
Harald Welte04683d02018-02-16 22:43:45 +0100673 /* FIXME: Extract P-TMSI, if any. Only send Complete if necessary */
Harald Welteca362462019-05-02 20:11:21 +0200674 f_send_l3_gmm_llc(ts_GMM_ATTACH_COMPL, gb_idx);
Neels Hofmeyr0ecb2e32018-04-30 15:13:55 +0200675}
676
677private function f_TC_attach(charstring id) runs on BSSGP_ConnHdlr {
678 f_gmm_attach(false, false);
Harald Welte5a4fa042018-02-16 20:59:21 +0100679 setverdict(pass);
Harald Welte5ac31492018-02-15 20:39:13 +0100680}
681
682testcase TC_attach() runs on test_CT {
683 var BSSGP_ConnHdlr vc_conn;
684 f_init();
685 f_sleep(1.0);
Alexander Couzens51114d12018-07-31 18:41:56 +0200686 vc_conn := f_start_handler(refers(f_TC_attach), testcasename(), g_gb, 1);
Harald Welte5ac31492018-02-15 20:39:13 +0100687 vc_conn.done;
688}
689
Neels Hofmeyr8df7d152018-03-14 19:03:28 +0100690testcase TC_attach_mnc3() runs on test_CT {
691 var BSSGP_ConnHdlr vc_conn;
692 f_init('023042'H);
693 f_sleep(1.0);
Alexander Couzens51114d12018-07-31 18:41:56 +0200694 vc_conn := f_start_handler(refers(f_TC_attach), testcasename(), g_gb, 1001);
Neels Hofmeyr8df7d152018-03-14 19:03:28 +0100695 vc_conn.done;
696}
697
Neels Hofmeyr0ecb2e32018-04-30 15:13:55 +0200698private function f_TC_attach_umts_aka_umts_res(charstring id) runs on BSSGP_ConnHdlr {
699 f_gmm_attach(true, false);
700 setverdict(pass);
701}
702testcase TC_attach_umts_aka_umts_res() runs on test_CT {
703 var BSSGP_ConnHdlr vc_conn;
704 f_init();
705 f_sleep(1.0);
Alexander Couzens51114d12018-07-31 18:41:56 +0200706 vc_conn := f_start_handler(refers(f_TC_attach_umts_aka_umts_res), testcasename(), g_gb, 1002);
Neels Hofmeyr0ecb2e32018-04-30 15:13:55 +0200707 vc_conn.done;
708}
709
710private function f_TC_attach_umts_aka_gsm_sres(charstring id) runs on BSSGP_ConnHdlr {
711 f_gmm_attach(true, true);
712 setverdict(pass);
713}
714testcase TC_attach_umts_aka_gsm_sres() runs on test_CT {
715 var BSSGP_ConnHdlr vc_conn;
716 f_init();
717 f_sleep(1.0);
Alexander Couzens51114d12018-07-31 18:41:56 +0200718 vc_conn := f_start_handler(refers(f_TC_attach_umts_aka_gsm_sres), testcasename(), g_gb, 1003);
Neels Hofmeyr0ecb2e32018-04-30 15:13:55 +0200719 vc_conn.done;
720}
721
Harald Welte5b7c8122018-02-16 21:48:17 +0100722/* MS never responds to ID REQ, expect ATTACH REJECT */
723private function f_TC_attach_auth_id_timeout(charstring id) runs on BSSGP_ConnHdlr {
Harald Welte5b7c8122018-02-16 21:48:17 +0100724 var RoutingAreaIdentificationV old_ra := f_random_RAI();
725
Alexander Couzenscdfb7512018-07-31 15:37:14 +0200726 f_send_l3_gmm_llc(ts_GMM_ATTACH_REQ(f_mi_get_lv(), old_ra, false, false, omit, omit));
Harald Welte5b7c8122018-02-16 21:48:17 +0100727 alt {
Harald Welte955aa942019-05-03 01:29:29 +0200728 [] BSSGP[0].receive(tr_GMM_ID_REQ(?)) {
Harald Welte5b7c8122018-02-16 21:48:17 +0100729 /* don't send ID Response */
730 repeat;
731 }
Harald Welte955aa942019-05-03 01:29:29 +0200732 [] BSSGP[0].receive(tr_GMM_ATTACH_REJECT('09'O)) {
Harald Welte5b7c8122018-02-16 21:48:17 +0100733 setverdict(pass);
734 }
Harald Welte955aa942019-05-03 01:29:29 +0200735 [] BSSGP[0].receive(tr_GMM_ATTACH_REJECT(?)) {
Harald Welte5b7c8122018-02-16 21:48:17 +0100736 setverdict(fail, "Wrong Attach Reject Cause");
Daniel Willmannafce8662018-07-06 23:11:32 +0200737 mtc.stop;
Harald Welte5b7c8122018-02-16 21:48:17 +0100738 }
739 }
740}
741testcase TC_attach_auth_id_timeout() runs on test_CT {
742 var BSSGP_ConnHdlr vc_conn;
743 f_init();
Alexander Couzens51114d12018-07-31 18:41:56 +0200744 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 +0100745 vc_conn.done;
746}
747
748/* HLR never responds to SAI REQ, expect ATTACH REJECT */
749private function f_TC_attach_auth_sai_timeout(charstring id) runs on BSSGP_ConnHdlr {
Harald Welte5b7c8122018-02-16 21:48:17 +0100750 var RoutingAreaIdentificationV old_ra := f_random_RAI();
751
Alexander Couzenscdfb7512018-07-31 15:37:14 +0200752 f_send_l3_gmm_llc(ts_GMM_ATTACH_REQ(f_mi_get_lv(), old_ra, false, false, omit, omit));
Harald Welte5b7c8122018-02-16 21:48:17 +0100753 alt {
754 [] as_mm_identity();
755 [] GSUP.receive(tr_GSUP_SAI_REQ(g_pars.imsi)); { }
756 }
757 /* don't send SAI-response from HLR */
Harald Welte955aa942019-05-03 01:29:29 +0200758 BSSGP[0].receive(tr_GMM_ATTACH_REJECT(?));
Harald Welte5b7c8122018-02-16 21:48:17 +0100759 setverdict(pass);
760}
761testcase TC_attach_auth_sai_timeout() runs on test_CT {
762 var BSSGP_ConnHdlr vc_conn;
763 f_init();
Alexander Couzens51114d12018-07-31 18:41:56 +0200764 vc_conn := f_start_handler(refers(f_TC_attach_auth_sai_timeout), testcasename(), g_gb, 3);
Harald Welte5b7c8122018-02-16 21:48:17 +0100765 vc_conn.done;
766}
767
Harald Weltefe253882018-02-17 09:25:00 +0100768/* HLR rejects SAI, expect ATTACH REJECT */
769private function f_TC_attach_auth_sai_reject(charstring id) runs on BSSGP_ConnHdlr {
Harald Weltefe253882018-02-17 09:25:00 +0100770 var RoutingAreaIdentificationV old_ra := f_random_RAI();
771
Alexander Couzenscdfb7512018-07-31 15:37:14 +0200772 f_send_l3_gmm_llc(ts_GMM_ATTACH_REQ(f_mi_get_lv(), old_ra, false, false, omit, omit));
Harald Weltefe253882018-02-17 09:25:00 +0100773 alt {
774 [] as_mm_identity();
775 [] GSUP.receive(tr_GSUP_SAI_REQ(g_pars.imsi)); {
776 GSUP.send(ts_GSUP_SAI_ERR(g_pars.imsi, 23));
777 }
778 }
Harald Welte955aa942019-05-03 01:29:29 +0200779 BSSGP[0].receive(tr_GMM_ATTACH_REJECT(?));
Harald Weltefe253882018-02-17 09:25:00 +0100780 setverdict(pass);
781}
782testcase TC_attach_auth_sai_reject() runs on test_CT {
783 var BSSGP_ConnHdlr vc_conn;
784 f_init();
Alexander Couzens51114d12018-07-31 18:41:56 +0200785 vc_conn := f_start_handler(refers(f_TC_attach_auth_sai_reject), testcasename(), g_gb, 4);
Harald Weltefe253882018-02-17 09:25:00 +0100786 vc_conn.done;
787}
788
Harald Welte5b7c8122018-02-16 21:48:17 +0100789/* HLR never responds to UL REQ, expect ATTACH REJECT */
790private function f_TC_attach_gsup_lu_timeout(charstring id) runs on BSSGP_ConnHdlr {
Harald Welte955aa942019-05-03 01:29:29 +0200791 var PDU_L3_SGSN_MS l3_mt;
Harald Welte5b7c8122018-02-16 21:48:17 +0100792 var RoutingAreaIdentificationV old_ra := f_random_RAI();
793
Alexander Couzenscdfb7512018-07-31 15:37:14 +0200794 f_send_l3_gmm_llc(ts_GMM_ATTACH_REQ(f_mi_get_lv(), old_ra, false, false, omit, omit));
Harald Welte5b7c8122018-02-16 21:48:17 +0100795 f_gmm_auth();
796 /* Expect MSC to perform LU with HLR */
797 GSUP.receive(tr_GSUP_UL_REQ(g_pars.imsi));
798 /* Never follow-up with ISD_REQ or UL_RES */
799 alt {
Harald Welte955aa942019-05-03 01:29:29 +0200800 [] BSSGP[0].receive(tr_GMM_ATTACH_REJECT(?)) {
Harald Welte5b7c8122018-02-16 21:48:17 +0100801 setverdict(pass);
802 }
Harald Welte955aa942019-05-03 01:29:29 +0200803 [] BSSGP[0].receive(tr_GMM_ATTACH_ACCEPT('001'B, ?, ?)) -> value l3_mt {
804 f_process_attach_accept(l3_mt.msgs.gprs_mm.attachAccept);
Harald Welte5b7c8122018-02-16 21:48:17 +0100805 setverdict(fail);
Daniel Willmannafce8662018-07-06 23:11:32 +0200806 mtc.stop;
Harald Welte5b7c8122018-02-16 21:48:17 +0100807 }
808 }
809}
810testcase TC_attach_gsup_lu_timeout() runs on test_CT {
811 var BSSGP_ConnHdlr vc_conn;
812 f_init();
813 f_sleep(1.0);
Alexander Couzens51114d12018-07-31 18:41:56 +0200814 vc_conn := f_start_handler(refers(f_TC_attach_gsup_lu_timeout), testcasename(), g_gb, 5);
Harald Welte5b7c8122018-02-16 21:48:17 +0100815 vc_conn.done;
816}
817
Harald Welteb7c14e92018-02-17 09:29:16 +0100818/* HLR rejects UL REQ, expect ATTACH REJECT */
819private function f_TC_attach_gsup_lu_reject(charstring id) runs on BSSGP_ConnHdlr {
Harald Welte955aa942019-05-03 01:29:29 +0200820 var PDU_L3_SGSN_MS l3_mt;
Harald Welteb7c14e92018-02-17 09:29:16 +0100821 var RoutingAreaIdentificationV old_ra := f_random_RAI();
822
Alexander Couzenscdfb7512018-07-31 15:37:14 +0200823 f_send_l3_gmm_llc(ts_GMM_ATTACH_REQ(f_mi_get_lv(), old_ra, false, false, omit, omit));
Harald Welteb7c14e92018-02-17 09:29:16 +0100824 f_gmm_auth();
825 /* Expect MSC to perform LU with HLR */
826 GSUP.receive(tr_GSUP_UL_REQ(g_pars.imsi)) {
827 GSUP.send(ts_GSUP_UL_ERR(g_pars.imsi, 0));
828 }
829 alt {
Harald Welte955aa942019-05-03 01:29:29 +0200830 [] BSSGP[0].receive(tr_GMM_ATTACH_REJECT(?)) {
Harald Welteb7c14e92018-02-17 09:29:16 +0100831 setverdict(pass);
832 }
Harald Welte955aa942019-05-03 01:29:29 +0200833 [] BSSGP[0].receive(tr_GMM_ATTACH_ACCEPT('001'B, ?, ?)) -> value l3_mt {
834 f_process_attach_accept(l3_mt.msgs.gprs_mm.attachAccept);
Harald Welteb7c14e92018-02-17 09:29:16 +0100835 setverdict(fail);
Daniel Willmannafce8662018-07-06 23:11:32 +0200836 mtc.stop;
Harald Welteb7c14e92018-02-17 09:29:16 +0100837 }
838 }
839}
840testcase TC_attach_gsup_lu_reject() runs on test_CT {
841 var BSSGP_ConnHdlr vc_conn;
842 f_init();
843 f_sleep(1.0);
Alexander Couzens51114d12018-07-31 18:41:56 +0200844 vc_conn := f_start_handler(refers(f_TC_attach_gsup_lu_reject), testcasename(), g_gb, 6);
Harald Welteb7c14e92018-02-17 09:29:16 +0100845 vc_conn.done;
846}
847
848
Harald Welte3823e2e2018-02-16 21:53:48 +0100849/* Attempt of combined GPRS + IMSI attach: network should ACK only GPRS attach */
850private function f_TC_attach_combined(charstring id) runs on BSSGP_ConnHdlr {
Harald Welte955aa942019-05-03 01:29:29 +0200851 var PDU_L3_SGSN_MS l3_mt;
Harald Welte3823e2e2018-02-16 21:53:48 +0100852 var RoutingAreaIdentificationV old_ra := f_random_RAI();
853
Alexander Couzenscdfb7512018-07-31 15:37:14 +0200854 f_send_l3_gmm_llc(ts_GMM_ATTACH_REQ(f_mi_get_lv(), old_ra, true, false, omit, omit));
Harald Welte3823e2e2018-02-16 21:53:48 +0100855 f_gmm_auth();
856 /* Expect MSC to perform LU with HLR */
Harald Welte311ec272018-02-17 09:40:03 +0100857 f_gmm_gsup_lu_isd();
Harald Welte3823e2e2018-02-16 21:53:48 +0100858
Harald Welte955aa942019-05-03 01:29:29 +0200859 BSSGP[0].receive(tr_GMM_ATTACH_ACCEPT('001'B, ?, ?)) -> value l3_mt {
860 f_process_attach_accept(l3_mt.msgs.gprs_mm.attachAccept);
Harald Welte04683d02018-02-16 22:43:45 +0100861 }
Alexander Couzenscdfb7512018-07-31 15:37:14 +0200862 f_send_l3_gmm_llc(ts_GMM_ATTACH_COMPL);
Harald Welte3823e2e2018-02-16 21:53:48 +0100863 setverdict(pass);
864}
Harald Welte3823e2e2018-02-16 21:53:48 +0100865testcase TC_attach_combined() runs on test_CT {
866 var BSSGP_ConnHdlr vc_conn;
867 f_init();
868 f_sleep(1.0);
Alexander Couzens51114d12018-07-31 18:41:56 +0200869 vc_conn := f_start_handler(refers(f_TC_attach_combined), testcasename(), g_gb, 7);
Harald Welte3823e2e2018-02-16 21:53:48 +0100870 vc_conn.done;
871}
872
Harald Welte76dee092018-02-16 22:12:59 +0100873/* Attempt of GPRS ATTACH in 'accept all' mode */
874private function f_TC_attach_accept_all(charstring id) runs on BSSGP_ConnHdlr {
Harald Welte955aa942019-05-03 01:29:29 +0200875 var PDU_L3_SGSN_MS l3_mt;
Harald Welte76dee092018-02-16 22:12:59 +0100876 var RoutingAreaIdentificationV old_ra := f_random_RAI();
877
878 g_pars.net.expect_auth := false;
879
Alexander Couzenscdfb7512018-07-31 15:37:14 +0200880 f_send_l3_gmm_llc(ts_GMM_ATTACH_REQ(f_mi_get_lv(), old_ra, false, false, omit, omit));
Harald Welte76dee092018-02-16 22:12:59 +0100881 f_gmm_auth();
Harald Welte955aa942019-05-03 01:29:29 +0200882 BSSGP[0].receive(tr_GMM_ATTACH_ACCEPT('001'B, ?, ?)) -> value l3_mt {
883 f_process_attach_accept(l3_mt.msgs.gprs_mm.attachAccept);
Harald Welte04683d02018-02-16 22:43:45 +0100884 }
Alexander Couzenscdfb7512018-07-31 15:37:14 +0200885 f_send_l3_gmm_llc(ts_GMM_ATTACH_COMPL);
Harald Welte76dee092018-02-16 22:12:59 +0100886 setverdict(pass);
887}
888testcase TC_attach_accept_all() runs on test_CT {
889 var BSSGP_ConnHdlr vc_conn;
890 f_init();
891 f_sleep(1.0);
892 f_vty_config(SGSNVTY, "sgsn", "auth-policy accept-all");
Alexander Couzens51114d12018-07-31 18:41:56 +0200893 vc_conn := f_start_handler(refers(f_TC_attach_accept_all), testcasename(), g_gb, 8);
Harald Welte76dee092018-02-16 22:12:59 +0100894 vc_conn.done;
895}
Harald Welte5b7c8122018-02-16 21:48:17 +0100896
Harald Welteb2124b22018-02-16 22:26:56 +0100897/* Attempt of GPRS ATTACH in 'accept all' mode */
898private function f_TC_attach_closed_foreign(charstring id) runs on BSSGP_ConnHdlr {
Harald Welteb2124b22018-02-16 22:26:56 +0100899 var RoutingAreaIdentificationV old_ra := f_random_RAI();
900
901 /* Simulate a foreign IMSI */
902 g_pars.imsi := '001010123456789'H;
Alexander Couzens51114d12018-07-31 18:41:56 +0200903 f_bssgp_client_register(g_pars.imsi, g_pars.tlli, g_pars.bssgp_cell_id[0]);
Harald Welteb2124b22018-02-16 22:26:56 +0100904
905 g_pars.net.expect_auth := false;
906
Alexander Couzenscdfb7512018-07-31 15:37:14 +0200907 f_send_l3_gmm_llc(ts_GMM_ATTACH_REQ(f_mi_get_lv(), old_ra, false, false, omit, omit));
Harald Welteb2124b22018-02-16 22:26:56 +0100908 alt {
909 [] as_mm_identity();
Harald Welte955aa942019-05-03 01:29:29 +0200910 [] BSSGP[0].receive(tr_GMM_ATTACH_REJECT('07'O)) {
Harald Welteb2124b22018-02-16 22:26:56 +0100911 setverdict(pass);
912 }
Harald Welte955aa942019-05-03 01:29:29 +0200913 [] BSSGP[0].receive(tr_GMM_ATTACH_REJECT(?)) {
Harald Welteb2124b22018-02-16 22:26:56 +0100914 setverdict(pass);
915 }
Harald Welte955aa942019-05-03 01:29:29 +0200916 [] BSSGP[0].receive(tr_GMM_ATTACH_ACCEPT(*, *, *)) {
Alexander Couzens0ca0d9c2018-06-12 14:01:34 +0200917 setverdict(fail);
Daniel Willmannafce8662018-07-06 23:11:32 +0200918 mtc.stop;
Alexander Couzens0ca0d9c2018-06-12 14:01:34 +0200919 }
Harald Welteb2124b22018-02-16 22:26:56 +0100920 }
921}
922testcase TC_attach_closed() runs on test_CT {
923 var BSSGP_ConnHdlr vc_conn;
924 f_init();
925 f_sleep(1.0);
926 f_vty_config(SGSNVTY, "sgsn", "auth-policy closed");
927 /* test with foreign IMSI: Must Reject */
Alexander Couzens51114d12018-07-31 18:41:56 +0200928 vc_conn := f_start_handler(refers(f_TC_attach_closed_foreign), testcasename(), g_gb, 9);
Harald Welteb2124b22018-02-16 22:26:56 +0100929 vc_conn.done;
930 /* test with home IMSI: Must Accept */
Alexander Couzens51114d12018-07-31 18:41:56 +0200931 vc_conn := f_start_handler(refers(f_TC_attach_accept_all), testcasename(), g_gb, 10);
Harald Welteb2124b22018-02-16 22:26:56 +0100932 vc_conn.done;
933}
934
Harald Welte04683d02018-02-16 22:43:45 +0100935/* Routing Area Update from Unknown TLLI -> REJECT */
936private function f_TC_rau_unknown(charstring id) runs on BSSGP_ConnHdlr {
Harald Welte04683d02018-02-16 22:43:45 +0100937 var RoutingAreaIdentificationV old_ra := f_random_RAI();
938
Alexander Couzenscdfb7512018-07-31 15:37:14 +0200939 f_send_l3_gmm_llc(ts_GMM_RAU_REQ(f_mi_get_lv(), GPRS_UPD_T_RA, old_ra, false, omit, omit));
Harald Welte04683d02018-02-16 22:43:45 +0100940 alt {
Harald Welte955aa942019-05-03 01:29:29 +0200941 [] BSSGP[0].receive(tr_GMM_RAU_REJECT('0a'O)) {
Harald Welte04683d02018-02-16 22:43:45 +0100942 setverdict(pass);
943 }
944 /* FIXME: Expect XID RESET? */
Alexander Couzens0e510e62018-07-28 23:06:00 +0200945 [] BSSGP[0].receive { repeat; }
Harald Welte04683d02018-02-16 22:43:45 +0100946 }
947}
948testcase TC_rau_unknown() runs on test_CT {
949 var BSSGP_ConnHdlr vc_conn;
950 f_init();
951 f_sleep(1.0);
Alexander Couzens51114d12018-07-31 18:41:56 +0200952 vc_conn := f_start_handler(refers(f_TC_rau_unknown), testcasename(), g_gb, 11);
Harald Welte04683d02018-02-16 22:43:45 +0100953 vc_conn.done;
954}
955
Harald Welte91636de2018-02-17 10:16:14 +0100956private function f_TC_attach_rau(charstring id) runs on BSSGP_ConnHdlr {
Harald Welte91636de2018-02-17 10:16:14 +0100957 /* first perform regular attach */
958 f_TC_attach(id);
959
Alexander Couzens5dce90d2018-07-31 03:16:37 +0200960 f_routing_area_update(g_pars.ra);
961
Harald Welte91636de2018-02-17 10:16:14 +0100962}
963testcase TC_attach_rau() runs on test_CT {
964 var BSSGP_ConnHdlr vc_conn;
965 f_init();
966 f_sleep(1.0);
Alexander Couzens51114d12018-07-31 18:41:56 +0200967 vc_conn := f_start_handler(refers(f_TC_attach_rau), testcasename(), g_gb, 12);
Harald Welte91636de2018-02-17 10:16:14 +0100968 vc_conn.done;
969}
Harald Welte04683d02018-02-16 22:43:45 +0100970
Harald Welte6abb9fe2018-02-17 15:24:48 +0100971/* general GPRS DETACH helper */
Alexander Couzens90fe6a22018-07-31 19:37:32 +0200972function f_detach_mo(BIT3 detach_type, boolean power_off, boolean expect_purge, integer bssgp_index := 0) runs on BSSGP_ConnHdlr {
Harald Welte955aa942019-05-03 01:29:29 +0200973 var PDU_L3_SGSN_MS l3_mt;
Harald Welte6abb9fe2018-02-17 15:24:48 +0100974 timer T := 5.0;
Alexander Couzens90fe6a22018-07-31 19:37:32 +0200975 f_send_l3_gmm_llc(ts_GMM_DET_REQ_MO(detach_type, power_off), bssgp_index);
Harald Welte6abb9fe2018-02-17 15:24:48 +0100976 if (expect_purge) {
977 GSUP.receive(tr_GSUP_PURGE_MS_REQ(g_pars.imsi, OSMO_GSUP_CN_DOMAIN_PS));
978 GSUP.send(ts_GSUP_PURGE_MS_RES(g_pars.imsi));
979 }
980 T.start;
981 alt {
982 [not expect_purge] GSUP.receive(tr_GSUP_PURGE_MS_REQ(?)) {
983 setverdict(fail, "Unexpected GSUP PURGE MS for unregistered TLLI");
Daniel Willmannafce8662018-07-06 23:11:32 +0200984 mtc.stop;
Harald Welte6abb9fe2018-02-17 15:24:48 +0100985 }
Harald Welte955aa942019-05-03 01:29:29 +0200986 [power_off] BSSGP[bssgp_index].receive(tr_GMM_DET_ACCEPT_MT) -> value l3_mt {
Harald Welte6abb9fe2018-02-17 15:24:48 +0100987 g_pars.ra := omit;
Alexander Couzens8e0fd462019-05-11 01:20:55 +0200988 setverdict(fail, "Unexpected DETACH ACCEPT in power-off DETACH");
Daniel Willmannafce8662018-07-06 23:11:32 +0200989 mtc.stop;
Harald Welte6abb9fe2018-02-17 15:24:48 +0100990 /* TODO: check if any PDP contexts are deactivated on network side? */
991 }
992 [power_off] T.timeout {
993 setverdict(pass);
994 }
Harald Welte955aa942019-05-03 01:29:29 +0200995 [not power_off] BSSGP[bssgp_index].receive(tr_GMM_DET_ACCEPT_MT) -> value l3_mt {
Harald Welte6abb9fe2018-02-17 15:24:48 +0100996 g_pars.ra := omit;
997 setverdict(pass);
998 /* TODO: check if any PDP contexts are deactivated on network side? */
999 }
Harald Welte955aa942019-05-03 01:29:29 +02001000 [] BSSGP[bssgp_index].receive(PDU_L3_SGSN_MS:?) -> value l3_mt {
Alexander Couzens4630e742019-05-11 01:50:10 +02001001 if (power_off) {
1002 setverdict(fail, "Unexpected Layer 3 package received in power-off DETACH");
1003 } else {
1004 setverdict(fail, "Unexpected Layer 3 package received in normal DETACH");
1005 }
1006 mtc.stop;
1007 }
Alexander Couzens90fe6a22018-07-31 19:37:32 +02001008 [] BSSGP[bssgp_index].receive { repeat; }
Harald Welte6abb9fe2018-02-17 15:24:48 +01001009 }
1010}
1011
1012/* IMSI DETACH (non-power-off) for unknown TLLI */
1013private function f_TC_detach_unknown_nopoweroff(charstring id) runs on BSSGP_ConnHdlr {
1014 f_detach_mo(c_GMM_DTT_MO_GPRS, false, false);
1015}
1016testcase TC_detach_unknown_nopoweroff() runs on test_CT {
1017 var BSSGP_ConnHdlr vc_conn;
1018 f_init();
1019 f_sleep(1.0);
Alexander Couzens51114d12018-07-31 18:41:56 +02001020 vc_conn := f_start_handler(refers(f_TC_detach_unknown_nopoweroff), testcasename(), g_gb, 13);
Harald Welte6abb9fe2018-02-17 15:24:48 +01001021 vc_conn.done;
1022}
1023
1024/* IMSI DETACH (power-off) for unknown TLLI */
1025private function f_TC_detach_unknown_poweroff(charstring id) runs on BSSGP_ConnHdlr {
1026 f_detach_mo(c_GMM_DTT_MO_GPRS, true, false);
1027}
1028testcase TC_detach_unknown_poweroff() runs on test_CT {
1029 var BSSGP_ConnHdlr vc_conn;
1030 f_init();
1031 f_sleep(1.0);
Alexander Couzens51114d12018-07-31 18:41:56 +02001032 vc_conn := f_start_handler(refers(f_TC_detach_unknown_poweroff), testcasename(), g_gb, 14);
Harald Welte6abb9fe2018-02-17 15:24:48 +01001033 vc_conn.done;
1034}
1035
1036/* IMSI DETACH (non-power-off) for known TLLI */
1037private function f_TC_detach_nopoweroff(charstring id) runs on BSSGP_ConnHdlr {
1038 /* first perform regular attach */
1039 f_TC_attach(id);
1040
1041 f_detach_mo(c_GMM_DTT_MO_GPRS, false, true);
1042}
1043testcase TC_detach_nopoweroff() runs on test_CT {
1044 var BSSGP_ConnHdlr vc_conn;
1045 f_init();
1046 f_sleep(1.0);
Alexander Couzens51114d12018-07-31 18:41:56 +02001047 vc_conn := f_start_handler(refers(f_TC_detach_nopoweroff), testcasename(), g_gb, 15);
Harald Welte6abb9fe2018-02-17 15:24:48 +01001048 vc_conn.done;
1049}
1050
1051/* IMSI DETACH (power-off) for known TLLI */
1052private function f_TC_detach_poweroff(charstring id) runs on BSSGP_ConnHdlr {
1053 /* first perform regular attach */
1054 f_TC_attach(id);
1055
1056 f_detach_mo(c_GMM_DTT_MO_GPRS, true, true);
1057}
1058testcase TC_detach_poweroff() runs on test_CT {
1059 var BSSGP_ConnHdlr vc_conn;
1060 f_init();
1061 f_sleep(1.0);
Alexander Couzens51114d12018-07-31 18:41:56 +02001062 vc_conn := f_start_handler(refers(f_TC_detach_poweroff), testcasename(), g_gb, 16);
Harald Welte6abb9fe2018-02-17 15:24:48 +01001063 vc_conn.done;
1064}
1065
Harald Welteeded9ad2018-02-17 20:57:34 +01001066type record PdpActPars {
Harald Welte822f9102018-02-18 20:39:06 +01001067 BIT3 tid, /* L3 Transaction ID */
1068 BIT4 nsapi, /* SNDCP NSAPI */
1069 BIT4 sapi, /* LLC SAPI */
1070 QoSV qos, /* QoS parameters */
1071 PDPAddressV addr, /* IP address */
1072 octetstring apn optional, /* APN name */
1073 ProtocolConfigOptionsV pco optional, /* protoco config opts */
1074 OCT1 exp_rej_cause optional, /* expected SM reject cause */
Harald Welte1d6ae932018-02-18 21:24:44 +01001075 OCT1 gtp_resp_cause, /* GTP response cause */
Harald Welte822f9102018-02-18 20:39:06 +01001076 OCT4 chg_id, /* GTP Charging Identifier */
Harald Welte6abb9fe2018-02-17 15:24:48 +01001077
Harald Welte822f9102018-02-18 20:39:06 +01001078 OCT4 ggsn_tei_c, /* GGSN TEI Control*/
1079 OCT4 ggsn_tei_u, /* GGSN TEI User */
1080 octetstring ggsn_ip_c, /* GGSN IP Control */
1081 octetstring ggsn_ip_u, /* GGSN IP User */
Pau Espin Pedroldc27e482018-07-10 14:02:49 +02001082 OCT1 ggsn_restart_ctr, /* GGSN Restart Counter */
Harald Welteeded9ad2018-02-17 20:57:34 +01001083
Harald Welte822f9102018-02-18 20:39:06 +01001084 OCT4 sgsn_tei_c optional, /* SGSN TEI Control */
1085 OCT4 sgsn_tei_u optional, /* SGSN TEI User */
1086 octetstring sgsn_ip_c optional, /* SGSN IP Control */
1087 octetstring sgsn_ip_u optional /* SGSN IP USer */
Harald Welteeded9ad2018-02-17 20:57:34 +01001088};
1089
Harald Welte5b5ca1b2018-02-18 21:25:03 +01001090
1091private function f_process_gtp_ctx_act_req(inout PdpActPars apars, PDU_GTPC gtpc) runs on BSSGP_ConnHdlr {
1092 var GTPC_PDUs gtpc_rx := gtpc.gtpc_pdu;
1093 apars.sgsn_tei_c := gtpc_rx.createPDPContextRequest.teidControlPlane.teidControlPlane;
1094 apars.sgsn_tei_u := gtpc_rx.createPDPContextRequest.teidDataI.teidDataI;
1095 apars.sgsn_ip_c := gtpc_rx.createPDPContextRequest.sgsn_addr_signalling.addressf;
1096 apars.sgsn_ip_u := gtpc_rx.createPDPContextRequest.sgsn_addr_traffic.addressf;
1097 f_gtp_register_teid(apars.ggsn_tei_c);
1098 f_gtp_register_teid(apars.ggsn_tei_u);
1099}
1100
Harald Weltef7191672019-05-02 20:37:23 +02001101function f_pdp_ctx_act(inout PdpActPars apars, boolean send_recovery := false, integer gb_idx := 0)
1102runs on BSSGP_ConnHdlr {
Harald Welteeded9ad2018-02-17 20:57:34 +01001103 var boolean exp_rej := ispresent(apars.exp_rej_cause);
1104 var Gtp1cUnitdata g_ud;
Pau Espin Pedrol94013452018-07-17 15:50:21 +02001105 var template Recovery_gtpc recovery := omit;
1106
1107 if (send_recovery) {
1108 recovery := ts_Recovery(apars.ggsn_restart_ctr);
1109 }
Harald Welteeded9ad2018-02-17 20:57:34 +01001110
Alexander Couzenscdfb7512018-07-31 15:37:14 +02001111 f_send_l3_gmm_llc(ts_SM_ACT_PDP_REQ(apars.tid, apars.nsapi, apars.sapi, apars.qos, apars.addr,
Harald Weltef7191672019-05-02 20:37:23 +02001112 apars.apn, apars.pco), gb_idx);
Harald Welte5b5ca1b2018-02-18 21:25:03 +01001113 GTP.receive(tr_GTPC_MsgType(?, createPDPContextRequest, ?)) -> value g_ud {
1114 f_process_gtp_ctx_act_req(apars, g_ud.gtpc);
1115 var integer seq_nr := oct2int(g_ud.gtpc.opt_part.sequenceNumber);
1116 GTP.send(ts_GTPC_CreatePdpResp(g_ud.peer, seq_nr,
1117 apars.sgsn_tei_c, apars.gtp_resp_cause,
1118 apars.ggsn_tei_c, apars.ggsn_tei_u,
1119 apars.nsapi,
Pau Espin Pedrol94013452018-07-17 15:50:21 +02001120 apars.ggsn_ip_c, apars.ggsn_ip_u, apars.chg_id,
1121 omit, recovery));
Harald Welteeded9ad2018-02-17 20:57:34 +01001122 }
1123 alt {
Harald Welte955aa942019-05-03 01:29:29 +02001124 [exp_rej] BSSGP[gb_idx].receive(tr_SM_ACT_PDP_REJ(apars.tid, apars.exp_rej_cause)) {
Harald Welteeded9ad2018-02-17 20:57:34 +01001125 setverdict(pass);
1126 }
Harald Welte955aa942019-05-03 01:29:29 +02001127 [exp_rej] BSSGP[gb_idx].receive(tr_SM_ACT_PDP_ACCEPT) {
Harald Welteeded9ad2018-02-17 20:57:34 +01001128 setverdict(fail, "Unexpected PDP CTX ACT ACC");
Daniel Willmannafce8662018-07-06 23:11:32 +02001129 mtc.stop;
Harald Welteeded9ad2018-02-17 20:57:34 +01001130 }
Harald Welte955aa942019-05-03 01:29:29 +02001131 [not exp_rej] BSSGP[gb_idx].receive(tr_SM_ACT_PDP_REJ(apars.tid, ?)) {
Harald Welteeded9ad2018-02-17 20:57:34 +01001132 setverdict(fail, "Unexpected PDP CTX ACT FAIL");
Daniel Willmannafce8662018-07-06 23:11:32 +02001133 mtc.stop;
Harald Welteeded9ad2018-02-17 20:57:34 +01001134 }
Harald Welte955aa942019-05-03 01:29:29 +02001135 [not exp_rej] BSSGP[gb_idx].receive(tr_SM_ACT_PDP_REJ(apars.tid, ?)) {
Harald Weltef7191672019-05-02 20:37:23 +02001136 setverdict(fail, "Unexpected PDP CTX ACT FAIL");
1137 mtc.stop;
1138 }
Harald Welte955aa942019-05-03 01:29:29 +02001139 [not exp_rej] BSSGP[gb_idx].receive(tr_SM_ACT_PDP_ACCEPT(apars.tid, apars.sapi)) {
Harald Welteeded9ad2018-02-17 20:57:34 +01001140 setverdict(pass);
1141 }
Harald Weltef7191672019-05-02 20:37:23 +02001142 [] as_xid(apars, gb_idx);
Harald Welteeded9ad2018-02-17 20:57:34 +01001143 }
1144}
1145
Harald Weltef7191672019-05-02 20:37:23 +02001146function f_pdp_ctx_deact_mo(inout PdpActPars apars, OCT1 cause, integer gb_idx := 0)
1147runs on BSSGP_ConnHdlr {
Harald Welte6f203162018-02-18 22:04:55 +01001148 var boolean exp_rej := ispresent(apars.exp_rej_cause);
1149 var Gtp1cUnitdata g_ud;
1150
Harald Weltef7191672019-05-02 20:37:23 +02001151 f_send_l3_gmm_llc(ts_SM_DEACT_PDP_REQ_MO(apars.tid, cause, false, omit), gb_idx);
Harald Welte6f203162018-02-18 22:04:55 +01001152 GTP.receive(tr_GTPC_MsgType(?, deletePDPContextRequest, apars.ggsn_tei_c)) -> value g_ud {
1153 var integer seq_nr := oct2int(g_ud.gtpc.opt_part.sequenceNumber);
Harald Weltef7191672019-05-02 20:37:23 +02001154 BSSGP[gb_idx].clear;
Harald Welte6f203162018-02-18 22:04:55 +01001155 GTP.send(ts_GTPC_DeletePdpResp(g_ud.peer, seq_nr, apars.sgsn_tei_c, '7F'O));
1156 }
1157 alt {
Harald Welte955aa942019-05-03 01:29:29 +02001158 [] BSSGP[gb_idx].receive(tr_SM_DEACT_PDP_ACCEPT_MT(apars.tid)) {
Harald Welte6f203162018-02-18 22:04:55 +01001159 setverdict(pass);
1160 }
Harald Weltef7191672019-05-02 20:37:23 +02001161 [] as_xid(apars, gb_idx);
Harald Welte6f203162018-02-18 22:04:55 +01001162 }
1163}
1164
Harald Weltef7191672019-05-02 20:37:23 +02001165function f_pdp_ctx_deact_mt(inout PdpActPars apars, boolean error_ind := false, integer gb_idx := 0)
1166runs on BSSGP_ConnHdlr {
Harald Welte57b9b7f2018-02-18 22:28:13 +01001167 var Gtp1cUnitdata g_ud;
1168 var integer seq_nr := 23;
1169 var GtpPeer peer := valueof(ts_GtpPeerC(apars.sgsn_ip_c));
1170
Harald Weltef7191672019-05-02 20:37:23 +02001171 BSSGP[gb_idx].clear;
Pau Espin Pedrol482dde62018-07-18 13:47:42 +02001172 if (error_ind) {
1173 GTP.send(ts_GTPU_ErrorIndication(peer, 0 /* seq */, apars.ggsn_tei_u, apars.ggsn_ip_u));
1174 } else {
1175 GTP.send(ts_GTPC_DeletePDP(peer, seq_nr, apars.sgsn_tei_c, apars.nsapi, '1'B));
1176 }
Alexander Couzens5e71c142018-08-07 17:21:24 +02001177
1178 timer T := 5.0;
1179 T.start;
1180
Pau Espin Pedrol482dde62018-07-18 13:47:42 +02001181 alt {
Harald Welte955aa942019-05-03 01:29:29 +02001182 [] BSSGP[gb_idx].receive(tr_SM_DEACT_PDP_REQ_MT(apars.tid, ?, true)) {
Harald Weltef7191672019-05-02 20:37:23 +02001183 f_send_l3_gmm_llc(ts_SM_DEACT_PDP_ACCEPT_MO(apars.tid), gb_idx);
Harald Welte57b9b7f2018-02-18 22:28:13 +01001184 }
Alexander Couzens5e71c142018-08-07 17:21:24 +02001185 [not error_ind] GTP.receive(tr_GTPC_MsgType(?, deletePDPContextResponse, apars.ggsn_tei_c)) {
1186 repeat;
1187 }
1188 [] T.timeout {
1189 setverdict(fail, "Waiting for SM_DEACT_PDP_REQ_MT");
1190 }
Harald Welte57b9b7f2018-02-18 22:28:13 +01001191 }
1192}
1193
Harald Welte6f203162018-02-18 22:04:55 +01001194
Harald Welteeded9ad2018-02-17 20:57:34 +01001195/* Table 10.5.156/3GPP TS 24.008 */
1196template (value) QoSV t_QosDefault := {
1197 reliabilityClass := '011'B, /* unacknowledged GTP+LLC, acknowledged RLC */
1198 delayClass := '100'B, /* best effort */
1199 spare1 := '00'B,
1200 precedenceClass := '010'B, /* normal */
1201 spare2 := '0'B,
1202 peakThroughput := '0000'B, /* subscribed */
1203 meanThroughput := '00000'B, /* subscribed */
1204 spare3 := '000'B,
1205 deliverErroneusSDU := omit,
1206 deliveryOrder := omit,
1207 trafficClass := omit,
1208 maxSDUSize := omit,
1209 maxBitrateUplink := omit,
1210 maxBitrateDownlink := omit,
1211 sduErrorRatio := omit,
1212 residualBER := omit,
1213 trafficHandlingPriority := omit,
1214 transferDelay := omit,
1215 guaranteedBitRateUplink := omit,
1216 guaranteedBitRateDownlink := omit,
1217 sourceStatisticsDescriptor := omit,
1218 signallingIndication := omit,
1219 spare4 := omit,
1220 maxBitrateDownlinkExt := omit,
1221 guaranteedBitRateDownlinkExt := omit,
1222 maxBitrateUplinkExt := omit,
1223 guaranteedBitRateUplinkExt := omit,
1224 maxBitrateDownlinkExt2 := omit,
1225 guaranteedBitRateDownlinkExt2 := omit,
1226 maxBitrateUplinkExt2 := omit,
1227 guaranteedBitRateUplinkExt2 := omit
1228}
1229
1230/* 10.5.6.4 / 3GPP TS 24.008 */
1231template (value) PDPAddressV t_AddrIPv4dyn := {
1232 pdpTypeOrg := '0001'B, /* IETF */
1233 spare := '0000'B,
1234 pdpTypeNum := '21'O, /* IPv4 */
1235 addressInfo := omit
1236}
1237template (value) PDPAddressV t_AddrIPv6dyn := {
1238 pdpTypeOrg := '0001'B, /* IETF */
1239 spare := '0000'B,
1240 pdpTypeNum := '53'O, /* IPv6 */
1241 addressInfo := omit
1242}
1243
Harald Welte37692d82018-02-18 15:21:34 +01001244template (value) PdpActPars t_PdpActPars(charstring ggsn_ip) := {
Harald Welteeded9ad2018-02-17 20:57:34 +01001245 tid := '000'B,
1246 nsapi := '0101'B, /* < 5 are reserved */
1247 sapi := '0011'B, /* 3/5/9/11 */
1248 qos := t_QosDefault,
1249 addr := t_AddrIPv4dyn,
1250 apn := omit,
1251 pco := omit,
1252 exp_rej_cause := omit,
Harald Welte1d6ae932018-02-18 21:24:44 +01001253 gtp_resp_cause := int2oct(128, 1),
1254 chg_id := f_rnd_octstring(4),
Harald Welteeded9ad2018-02-17 20:57:34 +01001255
1256 /* FIXME: make below dynamic !! */
Harald Welte1d6ae932018-02-18 21:24:44 +01001257 ggsn_tei_c := f_rnd_octstring(4),
1258 ggsn_tei_u := f_rnd_octstring(4),
Harald Welte37692d82018-02-18 15:21:34 +01001259 ggsn_ip_c := f_inet_addr(ggsn_ip),
1260 ggsn_ip_u := f_inet_addr(ggsn_ip),
Pau Espin Pedroldc27e482018-07-10 14:02:49 +02001261 ggsn_restart_ctr := int2oct(2, 1),
Harald Welteeded9ad2018-02-17 20:57:34 +01001262
Harald Welteeded9ad2018-02-17 20:57:34 +01001263 sgsn_tei_c := omit,
Harald Weltef8af5d62018-02-18 15:06:42 +01001264 sgsn_tei_u := omit,
1265 sgsn_ip_c := omit,
1266 sgsn_ip_u := omit
Harald Welteeded9ad2018-02-17 20:57:34 +01001267}
1268
Harald Welte37692d82018-02-18 15:21:34 +01001269template (value) GtpPeer ts_GtpPeerU(octetstring ip) := {
1270 connId := 1,
1271 remName := f_inet_ntoa(ip),
1272 remPort := GTP1U_PORT
1273}
1274
1275template (value) GtpPeer ts_GtpPeerC(octetstring ip) := {
1276 connId := 1,
1277 remName := f_inet_ntoa(ip),
1278 remPort := GTP1C_PORT
1279}
1280
1281private function f_gtpu_send(inout PdpActPars apars, octetstring payload) runs on BSSGP_ConnHdlr {
1282 var GtpPeer peer := valueof(ts_GtpPeerU(apars.sgsn_ip_u));
1283 GTP.send(ts_GTP1U_GPDU(peer, 0 /*seq*/, apars.sgsn_tei_u, payload));
1284}
1285
Harald Weltef7191672019-05-02 20:37:23 +02001286private altstep as_xid(PdpActPars apars, integer gb_idx := 0) runs on BSSGP_ConnHdlr {
Harald Welte955aa942019-05-03 01:29:29 +02001287 [] BSSGP[gb_idx].receive(tr_LLC_XID_MT_CMD(?, apars.sapi)) {
Harald Welte37692d82018-02-18 15:21:34 +01001288 repeat;
1289 }
1290}
1291
1292template PDU_SN tr_SN_UD(template BIT4 nsapi, template octetstring payload) := {
1293 pDU_SN_UNITDATA := {
1294 nsapi := nsapi,
1295 moreBit := ?,
1296 snPduType := '1'B,
1297 firstSegmentIndicator := ?,
1298 spareBit := ?,
1299 pcomp := ?,
1300 dcomp := ?,
1301 npduNumber := ?,
1302 segmentNumber := ?,
1303 npduNumberContinued := ?,
1304 dataSegmentSnUnitdataPdu := payload
1305 }
1306}
1307
1308/* simple case: single segment, no compression */
1309template (value) PDU_SN ts_SN_UD(BIT4 nsapi, octetstring payload) := {
1310 pDU_SN_UNITDATA := {
1311 nsapi := nsapi,
1312 moreBit := '0'B,
1313 snPduType := '1'B,
1314 firstSegmentIndicator := '1'B,
1315 spareBit := '0'B,
1316 pcomp := '0000'B,
1317 dcomp := '0000'B,
1318 npduNumber := '0000'B,
1319 segmentNumber := '0000'B,
1320 npduNumberContinued := '00'O,
1321 dataSegmentSnUnitdataPdu := payload
1322 }
1323}
1324
1325/* Transceive given 'payload' as MT message from GTP -> OsmoSGSN -> Gb */
Harald Weltef7191672019-05-02 20:37:23 +02001326private function f_gtpu_xceive_mt(inout PdpActPars apars, octetstring payload, integer gb_idx := 0)
1327runs on BSSGP_ConnHdlr {
Harald Welte37692d82018-02-18 15:21:34 +01001328 /* Send PDU via GTP from our simulated GGSN to the SGSN */
1329 f_gtpu_send(apars, payload);
1330 /* Expect PDU via BSSGP/LLC on simulated PCU from SGSN */
1331 alt {
Harald Weltef7191672019-05-02 20:37:23 +02001332 [] as_xid(apars, gb_idx);
Harald Welte955aa942019-05-03 01:29:29 +02001333 //[] BSSGP[gb_idx].receive(tr_BD_SNDCP(apars.sapi, tr_SN_UD(apars.nsapi, payload)));
1334 [] BSSGP[gb_idx].receive(tr_SN_UD(apars.nsapi, payload));
Harald Welte37692d82018-02-18 15:21:34 +01001335 }
1336}
1337
Pau Espin Pedrol8be4d192018-07-18 13:43:44 +02001338/* Transceive given 'payload' as MT message from Gb -> OsmoSGSN -> GTP */
Harald Weltef7191672019-05-02 20:37:23 +02001339private function f_gtpu_xceive_mo(inout PdpActPars apars, octetstring payload, integer gb_idx := 0)
1340runs on BSSGP_ConnHdlr {
Harald Welte37692d82018-02-18 15:21:34 +01001341 /* Send PDU via SNDCP/LLC/BSSGP/NS via simulated MS/PCU to the SGSN */
1342 var GtpPeer peer := valueof(ts_GtpPeerU(apars.sgsn_ip_u));
1343 var PDU_SN sndcp := valueof(ts_SN_UD(apars.nsapi, payload));
Harald Weltef7191672019-05-02 20:37:23 +02001344 BSSGP[gb_idx].send(ts_LLC_UI(enc_PDU_SN(sndcp), apars.sapi, '0'B, 0));
Harald Welte37692d82018-02-18 15:21:34 +01001345 /* Expect PDU via GTP from SGSN on simulated GGSN */
1346 alt {
1347 [] GTP.receive(tr_GTPU_GPDU(peer, apars.ggsn_tei_u, payload));
1348 }
1349}
1350
Harald Welteeded9ad2018-02-17 20:57:34 +01001351private function f_TC_attach_pdp_act(charstring id) runs on BSSGP_ConnHdlr {
Harald Welte37692d82018-02-18 15:21:34 +01001352 var PdpActPars apars := valueof(t_PdpActPars(mp_ggsn_ip));
Harald Welteeded9ad2018-02-17 20:57:34 +01001353
1354 /* first perform regular attach */
1355 f_TC_attach(id);
1356
1357 f_pdp_ctx_act(apars);
1358}
1359testcase TC_attach_pdp_act() runs on test_CT {
1360 var BSSGP_ConnHdlr vc_conn;
1361 f_init();
Alexander Couzens51114d12018-07-31 18:41:56 +02001362 vc_conn := f_start_handler(refers(f_TC_attach_pdp_act), testcasename(), g_gb, 17);
Harald Welteeded9ad2018-02-17 20:57:34 +01001363 vc_conn.done;
1364}
Harald Welteb2124b22018-02-16 22:26:56 +01001365
Harald Welte835b15f2018-02-18 14:39:11 +01001366/* PDP Context activation for not-attached subscriber; expect fail */
1367private function f_TC_pdp_act_unattached(charstring id) runs on BSSGP_ConnHdlr {
Harald Welte37692d82018-02-18 15:21:34 +01001368 var PdpActPars apars := valueof(t_PdpActPars(mp_ggsn_ip));
Alexander Couzenscdfb7512018-07-31 15:37:14 +02001369 f_send_l3_gmm_llc(ts_SM_ACT_PDP_REQ(apars.tid, apars.nsapi, apars.sapi, apars.qos, apars.addr,
Harald Welte835b15f2018-02-18 14:39:11 +01001370 apars.apn, apars.pco));
1371 alt {
1372 /* We might want toalso actually expect a PDPC CTX ACT REJ? */
Harald Welte955aa942019-05-03 01:29:29 +02001373 [] BSSGP[0].receive(tr_GMM_DET_REQ_MT(?, ?)) {
Harald Welte835b15f2018-02-18 14:39:11 +01001374 setverdict(pass);
1375 }
1376 [] GTP.receive(tr_GTPC_MsgType(?, createPDPContextRequest, ?)) {
1377 setverdict(fail, "Unexpected GTP PDP CTX ACT");
Daniel Willmannafce8662018-07-06 23:11:32 +02001378 mtc.stop;
Harald Welte835b15f2018-02-18 14:39:11 +01001379 }
Harald Welte955aa942019-05-03 01:29:29 +02001380 [] BSSGP[0].receive(tr_SM_ACT_PDP_ACCEPT(?, ?)) {
Harald Welte835b15f2018-02-18 14:39:11 +01001381 setverdict(fail, "Unexpected SM PDP CTX ACT ACK");
Daniel Willmannafce8662018-07-06 23:11:32 +02001382 mtc.stop;
Harald Welte835b15f2018-02-18 14:39:11 +01001383 }
Alexander Couzens0e510e62018-07-28 23:06:00 +02001384 [] BSSGP[0].receive { repeat; }
Harald Welte835b15f2018-02-18 14:39:11 +01001385 }
1386}
1387testcase TC_pdp_act_unattached() runs on test_CT {
1388 var BSSGP_ConnHdlr vc_conn;
1389 f_init();
Alexander Couzens51114d12018-07-31 18:41:56 +02001390 vc_conn := f_start_handler(refers(f_TC_pdp_act_unattached), testcasename(), g_gb, 18);
Harald Welte835b15f2018-02-18 14:39:11 +01001391 vc_conn.done;
1392}
1393
Harald Welte37692d82018-02-18 15:21:34 +01001394/* ATTACH + PDP CTX ACT + user plane traffic */
1395private function f_TC_attach_pdp_act_user(charstring id) runs on BSSGP_ConnHdlr {
1396 var PdpActPars apars := valueof(t_PdpActPars(mp_ggsn_ip));
1397
1398 /* first perform regular attach */
1399 f_TC_attach(id);
1400 /* then activate PDP context */
1401 f_pdp_ctx_act(apars);
1402 /* then transceive a downlink PDU */
1403 f_gtpu_xceive_mt(apars, f_rnd_octstring(100));
1404 f_gtpu_xceive_mo(apars, f_rnd_octstring(200));
1405}
1406testcase TC_attach_pdp_act_user() runs on test_CT {
1407 var BSSGP_ConnHdlr vc_conn;
1408 f_init();
Alexander Couzens51114d12018-07-31 18:41:56 +02001409 vc_conn := f_start_handler(refers(f_TC_attach_pdp_act_user), testcasename(), g_gb, 19);
Harald Welte37692d82018-02-18 15:21:34 +01001410 vc_conn.done;
1411}
1412
Harald Welte5b5ca1b2018-02-18 21:25:03 +01001413/* ATTACH + PDP CTX ACT; reject from GGSN */
1414private function f_TC_attach_pdp_act_ggsn_reject(charstring id) runs on BSSGP_ConnHdlr {
1415 var PdpActPars apars := valueof(t_PdpActPars(mp_ggsn_ip));
1416
1417 apars.gtp_resp_cause := int2oct(199, 1); /* no resources available */
1418 apars.exp_rej_cause := '1a'O; /* insufficient resources */
1419
1420 /* first perform regular attach */
1421 f_TC_attach(id);
1422 /* then activate PDP context */
1423 f_pdp_ctx_act(apars);
1424}
1425testcase TC_attach_pdp_act_ggsn_reject() runs on test_CT {
1426 var BSSGP_ConnHdlr vc_conn;
1427 f_init();
Alexander Couzens51114d12018-07-31 18:41:56 +02001428 vc_conn := f_start_handler(refers(f_TC_attach_pdp_act_ggsn_reject), testcasename(), g_gb, 20);
Harald Welte5b5ca1b2018-02-18 21:25:03 +01001429 vc_conn.done;
1430}
Harald Welte835b15f2018-02-18 14:39:11 +01001431
Harald Welte6f203162018-02-18 22:04:55 +01001432/* ATTACH + PDP CTX ACT + user plane traffic + PDP CTX DEACT in MO direction */
1433private function f_TC_attach_pdp_act_user_deact_mo(charstring id) runs on BSSGP_ConnHdlr {
1434 var PdpActPars apars := valueof(t_PdpActPars(mp_ggsn_ip));
1435
1436 /* first perform regular attach */
1437 f_TC_attach(id);
1438 /* then activate PDP context */
1439 f_pdp_ctx_act(apars);
1440 /* then transceive a downlink PDU */
1441 f_gtpu_xceive_mt(apars, f_rnd_octstring(100));
1442 f_gtpu_xceive_mo(apars, f_rnd_octstring(200));
1443
1444 f_pdp_ctx_deact_mo(apars, '00'O);
1445}
1446testcase TC_attach_pdp_act_user_deact_mo() runs on test_CT {
1447 var BSSGP_ConnHdlr vc_conn;
1448 f_init();
Alexander Couzens51114d12018-07-31 18:41:56 +02001449 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 +01001450 vc_conn.done;
1451}
1452
Harald Welte57b9b7f2018-02-18 22:28:13 +01001453/* ATTACH + PDP CTX ACT + user plane traffic + PDP CTX DEACT in MT direction */
1454private function f_TC_attach_pdp_act_user_deact_mt(charstring id) runs on BSSGP_ConnHdlr {
1455 var PdpActPars apars := valueof(t_PdpActPars(mp_ggsn_ip));
1456
1457 /* first perform regular attach */
1458 f_TC_attach(id);
1459 /* then activate PDP context */
1460 f_pdp_ctx_act(apars);
1461 /* then transceive a downlink PDU */
1462 f_gtpu_xceive_mt(apars, f_rnd_octstring(100));
1463 f_gtpu_xceive_mo(apars, f_rnd_octstring(200));
1464
Pau Espin Pedrol482dde62018-07-18 13:47:42 +02001465 f_pdp_ctx_deact_mt(apars, false);
Harald Welte57b9b7f2018-02-18 22:28:13 +01001466}
1467testcase TC_attach_pdp_act_user_deact_mt() runs on test_CT {
1468 var BSSGP_ConnHdlr vc_conn;
1469 f_init();
Alexander Couzens51114d12018-07-31 18:41:56 +02001470 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 +01001471 vc_conn.done;
1472}
1473
Pau Espin Pedrol2a3302a2019-08-15 16:01:20 +02001474/* Test MS sending a duplicate Deact PDP Ctx (OS#3956). */
1475private function f_TC_attach_pdp_act_deact_dup(charstring id) runs on BSSGP_ConnHdlr {
1476 var PdpActPars apars := valueof(t_PdpActPars(mp_ggsn_ip));
1477 var Gtp1cUnitdata g_ud;
1478 var integer i;
1479 var OCT1 cause_regular_deact := '24'O;
1480
1481 /* first perform regular attach + PDP context act */
1482 f_TC_attach(id);
1483 f_pdp_ctx_act(apars);
1484
1485 f_send_l3_gmm_llc(ts_SM_DEACT_PDP_REQ_MO(apars.tid, cause_regular_deact, false, omit), 0);
1486 f_send_l3_gmm_llc(ts_SM_DEACT_PDP_REQ_MO(apars.tid, cause_regular_deact, false, omit), 0);
1487
1488 for (i := 0; i < 2; i := i+1) {
1489 GTP.receive(tr_GTPC_MsgType(?, deletePDPContextRequest, apars.ggsn_tei_c)) -> value g_ud {
1490 var integer seq_nr := oct2int(g_ud.gtpc.opt_part.sequenceNumber);
1491 log("Received deletePDPContextResponse " & int2str(i) & ", seq_nr=" & int2str(seq_nr));
1492 GTP.send(ts_GTPC_DeletePdpResp(g_ud.peer, seq_nr, apars.sgsn_tei_c, '7F'O));
1493 }
1494 }
1495
1496 alt {
1497 [] BSSGP[0].receive(tr_SM_DEACT_PDP_ACCEPT_MT(apars.tid)) {
1498 setverdict(pass);
1499 }
1500 [] as_xid(apars, 0);
1501 }
1502
1503 /* Make sure second DeactPdpAccept is sent: */
1504 timer T := 2.0;
1505 T.start;
1506 alt {
1507 [] BSSGP[0].receive(tr_SM_DEACT_PDP_ACCEPT_MT(apars.tid)) {
1508 setverdict(fail, "Second SM_DEACT_PDP_ACCEPT_MT received");
1509 }
1510 [] T.timeout {
1511 setverdict(pass);
1512 }
1513 }
1514
1515 setverdict(pass);
1516}
1517testcase TC_attach_pdp_act_deact_dup() runs on test_CT {
1518 var BSSGP_ConnHdlr vc_conn;
1519 f_init();
1520 vc_conn := f_start_handler(refers(f_TC_attach_pdp_act_deact_dup), testcasename(), g_gb, 46);
1521 vc_conn.done;
1522}
1523
Alexander Couzens187ad5d2018-05-02 19:31:10 +02001524/* ATTACH + ATTACH (2nd) */
1525private function f_TC_attach_forget_tlli_attach(charstring id) runs on BSSGP_ConnHdlr {
1526 g_pars.t_guard := 5.0;
1527
1528 /* first perform regular attach */
1529 f_TC_attach(id);
1530
1531 /* second to perform regular attach */
1532 f_TC_attach(id);
1533}
1534
1535
1536testcase TC_attach_second_attempt() runs on test_CT {
1537 var BSSGP_ConnHdlr vc_conn;
1538 f_init();
Alexander Couzens51114d12018-07-31 18:41:56 +02001539 vc_conn := f_start_handler(refers(f_TC_attach_forget_tlli_attach), testcasename(), g_gb, 22);
Alexander Couzens187ad5d2018-05-02 19:31:10 +02001540 vc_conn.done;
1541}
Harald Welte57b9b7f2018-02-18 22:28:13 +01001542
Pau Espin Pedrolfcec9142019-08-28 17:33:46 +02001543private function f_TC_attach_echo_timeout(charstring id) runs on BSSGP_ConnHdlr {
1544 var Gtp1cUnitdata g_ud;
1545 var PdpActPars apars := valueof(t_PdpActPars(mp_ggsn_ip));
1546 var integer seq_nr;
1547
1548 /* first perform regular attach */
1549 f_TC_attach(id);
1550 /* then activate PDP context */
1551 f_pdp_ctx_act(apars);
1552
1553 /* Wait to receive first echo request and send initial Restart counter */
1554 GTP.receive(tr_GTPC_MsgType(?, echoRequest, ?)) -> value g_ud {
1555 BSSGP[0].clear;
1556 seq_nr := oct2int(g_ud.gtpc.opt_part.sequenceNumber);
1557 GTP.send(ts_GTPC_PONG(g_ud.peer, seq_nr, apars.ggsn_restart_ctr));
1558 f_sleep(int2float(mp_echo_interval)); /* wait until around next echo is expected */
1559 }
1560
1561 /* At some point next echo request not answered will timeout and SGSN
1562 should drop the pdp ctx. Around T3 (3secs) * 6 (+ extra, a lot due to OS#4178): */
1563 timer T := 3.0 * 6.0 + 16.0;
1564 T.start;
1565 alt {
1566 [] BSSGP[0].receive(tr_SM_DEACT_PDP_REQ_MT(apars.tid, ?, true)) {
1567 f_send_l3_gmm_llc(ts_SM_DEACT_PDP_ACCEPT_MO(apars.tid));
1568 setverdict(pass);
1569 }
1570 [] GTP.receive(tr_GTPC_MsgType(?, deletePDPContextRequest, apars.ggsn_tei_c)) -> value g_ud {
1571 /* SGSN currently doesn't send this message because it expects GGSN to be non-reachable anyway */
1572 seq_nr := oct2int(g_ud.gtpc.opt_part.sequenceNumber);
1573 log("Received deletePDPContextRequest seq_nr=" & int2str(seq_nr));
1574 GTP.send(ts_GTPC_DeletePdpResp(g_ud.peer, seq_nr, apars.sgsn_tei_c, '7F'O));
1575 repeat;
1576 }
1577 [] GTP.receive(tr_GTPC_MsgType(?, echoRequest, ?)) -> value g_ud {
1578 seq_nr := oct2int(g_ud.gtpc.opt_part.sequenceNumber);
1579 log("Received EchoRequest seq_nr=" & int2str(seq_nr));
1580 repeat;
1581 }
1582 [] T.timeout {
1583 setverdict(fail, "BSSGP DeactPdpReq not received");
1584 mtc.stop;
1585 }
1586 [] as_xid(apars);
1587 }
1588 T.stop
1589
1590 setverdict(pass);
1591}
1592/* ATTACH + trigger Recovery procedure through CreatePdpResp */
1593testcase TC_attach_echo_timeout() runs on test_CT {
1594 var BSSGP_ConnHdlr vc_conn;
1595 g_use_echo := true;
1596 f_init();
1597 vc_conn := f_start_handler(refers(f_TC_attach_echo_timeout), testcasename(), g_gb, 67, 50.0);
1598 vc_conn.done;
1599 g_use_echo := false;
1600}
1601
Pau Espin Pedrol94013452018-07-17 15:50:21 +02001602private function f_TC_attach_restart_ctr_echo(charstring id) runs on BSSGP_ConnHdlr {
Pau Espin Pedroldc27e482018-07-10 14:02:49 +02001603 var Gtp1cUnitdata g_ud;
1604 var PdpActPars apars := valueof(t_PdpActPars(mp_ggsn_ip));
1605
1606 /* first perform regular attach */
1607 f_TC_attach(id);
1608 /* Activate a pdp context against the GGSN */
1609 f_pdp_ctx_act(apars);
1610 /* Wait to receive first echo request and send initial Restart counter */
1611 GTP.receive(tr_GTPC_MsgType(?, echoRequest, ?)) -> value g_ud {
1612 var integer seq_nr := oct2int(g_ud.gtpc.opt_part.sequenceNumber);
1613 GTP.send(ts_GTPC_PONG(g_ud.peer, seq_nr, apars.ggsn_restart_ctr));
1614 }
1615 /* Wait to receive second echo request and send incremented Restart
1616 counter. This will fake a restarted GGSN, and pdp ctx allocated
1617 should be released by SGSN */
1618 apars.ggsn_restart_ctr := int2oct(oct2int(apars.ggsn_restart_ctr) + 1, 1);
1619 GTP.receive(tr_GTPC_MsgType(?, echoRequest, ?)) -> value g_ud {
1620 var integer seq_nr := oct2int(g_ud.gtpc.opt_part.sequenceNumber);
1621 GTP.send(ts_GTPC_PONG(g_ud.peer, seq_nr, apars.ggsn_restart_ctr));
1622 }
1623 var OCT1 cause_network_failure := int2oct(38, 1)
1624 alt {
Harald Welte955aa942019-05-03 01:29:29 +02001625 [] BSSGP[0].receive(tr_SM_DEACT_PDP_REQ_MT(apars.tid, cause_network_failure, true)) {
Alexander Couzenscdfb7512018-07-31 15:37:14 +02001626 f_send_l3_gmm_llc(ts_SM_DEACT_PDP_ACCEPT_MO(apars.tid));
Pau Espin Pedroldc27e482018-07-10 14:02:49 +02001627 setverdict(pass);
1628 }
1629 [] as_xid(apars);
1630 }
1631 setverdict(pass);
1632}
Pau Espin Pedrol94013452018-07-17 15:50:21 +02001633/* ATTACH + trigger Recovery procedure through EchoResp */
1634testcase TC_attach_restart_ctr_echo() runs on test_CT {
Pau Espin Pedroldc27e482018-07-10 14:02:49 +02001635 var BSSGP_ConnHdlr vc_conn;
1636 g_use_echo := true
1637 f_init();
Alexander Couzens51114d12018-07-31 18:41:56 +02001638 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 +02001639 vc_conn.done;
1640 g_use_echo := false
1641}
1642
Pau Espin Pedrol94013452018-07-17 15:50:21 +02001643private function f_TC_attach_restart_ctr_create(charstring id) runs on BSSGP_ConnHdlr {
1644 var Gtp1cUnitdata g_ud;
1645 var PdpActPars apars := valueof(t_PdpActPars(mp_ggsn_ip));
1646 var integer seq_nr := 23;
1647 var GtpPeer peer;
1648 /* first perform regular attach */
1649 f_TC_attach(id);
1650
1651 /* Use this CTX ACT to send initial Restart counter to SGSN. */
1652 apars.gtp_resp_cause := int2oct(199, 1); /* no resources available */
1653 apars.exp_rej_cause := '1a'O; /* insufficient resources */
1654 f_pdp_ctx_act(apars, true);
1655
1656 /* Increment restart_ctr. This will fake a restarted GGSN when CreatePdpResp is
1657/* received. */
1658 apars.ggsn_restart_ctr := int2oct(oct2int(apars.ggsn_restart_ctr) + 1, 1);
1659
1660 /* FIXME: Once we can easily handle different pdp ctx simultaneously, it
1661 would be great to have an active pdp context here before triggering
1662 Recovery, and making sure the the DEACT request is sent by the SGSN.
1663 */
1664
1665 /* Activate a pdp context against the GGSN, send incremented Recovery
1666 IE. This should trigger the recovery path, but still this specific
1667 CTX activation should work. */
1668 apars.exp_rej_cause := omit; /* default value for tests */
1669 apars.gtp_resp_cause := int2oct(128, 1); /* default value for tests */
1670 f_pdp_ctx_act(apars, true);
1671
1672 setverdict(pass);
1673}
1674/* ATTACH + trigger Recovery procedure through CreatePdpResp */
1675testcase TC_attach_restart_ctr_create() runs on test_CT {
1676 var BSSGP_ConnHdlr vc_conn;
1677 f_init();
Alexander Couzens51114d12018-07-31 18:41:56 +02001678 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 +02001679 vc_conn.done;
1680}
1681
Pau Espin Pedrol72edc8a2018-07-16 15:10:08 +02001682/* ATTACH + PDP CTX ACT + user plane traffic + PDP CTX DEACT in MT direction + trigger T3395 */
1683private function f_TC_attach_pdp_act_deact_mt_t3395_expire(charstring id) runs on BSSGP_ConnHdlr {
1684 var PdpActPars apars := valueof(t_PdpActPars(mp_ggsn_ip));
1685 var integer seq_nr := 23;
1686 var GtpPeer peer;
1687 var integer i;
1688
1689 /* first perform regular attach */
1690 f_TC_attach(id);
1691 /* then activate PDP context */
1692 f_pdp_ctx_act(apars);
1693
Alexander Couzens0e510e62018-07-28 23:06:00 +02001694 BSSGP[0].clear;
Pau Espin Pedrol72edc8a2018-07-16 15:10:08 +02001695 peer := valueof(ts_GtpPeerC(apars.sgsn_ip_c));
1696 GTP.send(ts_GTPC_DeletePDP(peer, seq_nr, apars.sgsn_tei_c, apars.nsapi, '1'B));
1697
1698 for (i := 0; i < 5; i := i+1) {
1699 alt {
Harald Welte955aa942019-05-03 01:29:29 +02001700 [] BSSGP[0].receive(tr_SM_DEACT_PDP_REQ_MT(apars.tid, ?, true)) {}
Pau Espin Pedrol72edc8a2018-07-16 15:10:08 +02001701 [] as_xid(apars);
1702 }
1703 }
1704
1705 GTP.receive(tr_GTPC_MsgType(?, deletePDPContextResponse, apars.ggsn_tei_c)) {}
1706
Alexander Couzenscdfb7512018-07-31 15:37:14 +02001707 f_send_l3_gmm_llc(ts_SM_DEACT_PDP_ACCEPT_MO(apars.tid));
Pau Espin Pedrol72edc8a2018-07-16 15:10:08 +02001708 setverdict(pass);
1709}
1710testcase TC_attach_pdp_act_deact_mt_t3395_expire() runs on test_CT {
1711 var BSSGP_ConnHdlr vc_conn;
1712 f_init();
1713 f_sleep(1.0);
Alexander Couzens51114d12018-07-31 18:41:56 +02001714 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 +02001715 vc_conn.done;
1716}
1717
Pau Espin Pedrole6f071f2019-05-29 13:02:42 +02001718/* ATTACH + PDP CTX ACT dropped + retrans */
1719private function f_TC_attach_pdp_act_deact_gtp_retrans(charstring id) runs on BSSGP_ConnHdlr {
1720 var PdpActPars apars := valueof(t_PdpActPars(mp_ggsn_ip));
1721 var Gtp1cUnitdata g_ud_first, g_ud_second;
1722 /* first perform regular attach */
1723 f_TC_attach(id);
1724
1725 /* then activate PDP context on the Gb side */
1726 f_send_l3_gmm_llc(ts_SM_ACT_PDP_REQ(apars.tid, apars.nsapi, apars.sapi, apars.qos, apars.addr,
1727 apars.apn, apars.pco), 0);
1728
1729 GTP.receive(tr_GTPC_MsgType(?, createPDPContextRequest, ?)) -> value g_ud_first {}
1730 log("First createPDPContextRequest received, dropping & waiting for retransmission");
1731 GTP.receive(tr_GTPC_MsgType(?, createPDPContextRequest, ?)) -> value g_ud_second {
1732 if (g_ud_first != g_ud_second) {
1733 setverdict(fail, "Retransmitted GTP message createPDPContextRequest is different from original one!");
1734 mtc.stop;
1735 }
1736 f_process_gtp_ctx_act_req(apars, g_ud_second.gtpc);
1737 var integer seq_nr := oct2int(g_ud_second.gtpc.opt_part.sequenceNumber);
1738 GTP.send(ts_GTPC_CreatePdpResp(g_ud_second.peer, seq_nr,
1739 apars.sgsn_tei_c, apars.gtp_resp_cause,
1740 apars.ggsn_tei_c, apars.ggsn_tei_u,
1741 apars.nsapi,
1742 apars.ggsn_ip_c, apars.ggsn_ip_u, apars.chg_id,
1743 omit, omit));
1744 }
Harald Welte955aa942019-05-03 01:29:29 +02001745 BSSGP[0].receive(tr_SM_ACT_PDP_ACCEPT) {}
Pau Espin Pedrole6f071f2019-05-29 13:02:42 +02001746
1747 /* Now the same with Deact */
1748 f_send_l3_gmm_llc(ts_SM_DEACT_PDP_REQ_MO(apars.tid, '00'O, false, omit), 0);
1749 GTP.receive(tr_GTPC_MsgType(?, deletePDPContextRequest, apars.ggsn_tei_c)) -> value g_ud_first {}
1750 log("First deletePDPContextRequest received, dropping & waiting for retransmission");
1751 GTP.receive(tr_GTPC_MsgType(?, deletePDPContextRequest, apars.ggsn_tei_c)) -> value g_ud_second {
1752 if (g_ud_first != g_ud_second) {
1753 setverdict(fail, "Retransmitted GTP message deletePDPContextRequest is different from original one!");
1754 mtc.stop;
1755 }
1756 var integer seq_nr := oct2int(g_ud_second.gtpc.opt_part.sequenceNumber);
1757 BSSGP[0].clear;
1758 GTP.send(ts_GTPC_DeletePdpResp(g_ud_second.peer, seq_nr, apars.sgsn_tei_c, '7F'O));
1759 }
1760 alt {
Harald Welte955aa942019-05-03 01:29:29 +02001761 [] BSSGP[0].receive(tr_SM_DEACT_PDP_ACCEPT_MT(apars.tid)) {
Pau Espin Pedrole6f071f2019-05-29 13:02:42 +02001762 setverdict(pass);
1763 }
1764 [] as_xid(apars, 0);
1765 }
1766
1767 setverdict(pass);
1768}
1769testcase TC_attach_pdp_act_deact_gtp_retrans() runs on test_CT {
1770 var BSSGP_ConnHdlr vc_conn;
1771 f_init();
1772 vc_conn := f_start_handler(refers(f_TC_attach_pdp_act_deact_gtp_retrans), testcasename(), g_gb, 27);
1773 vc_conn.done;
1774}
1775
1776/* Test that SGSN GTP response retransmit queue works fine */
1777private function f_TC_attach_pdp_act_deact_gtp_retrans_resp(charstring id) runs on BSSGP_ConnHdlr {
1778 var PdpActPars apars := valueof(t_PdpActPars(mp_ggsn_ip));
1779 var integer seq_nr := 23;
1780 var Gtp1cUnitdata g_ud_first, g_ud_second;
1781 var template Gtp1cUnitdata g_delete_req;
1782 /* first perform regular attach + PDP context act */
1783 f_TC_attach(id);
1784 f_pdp_ctx_act(apars);
1785
1786 /* Now perform an MT DeleteCtxReq and emulate GGSN didn't receive response and sends a duplicated DeleteCtxReq */
1787 BSSGP[0].clear;
1788 var GtpPeer peer := valueof(ts_GtpPeerC(apars.sgsn_ip_c));
1789 g_delete_req := ts_GTPC_DeletePDP(peer, seq_nr, apars.sgsn_tei_c, apars.nsapi, '1'B);
1790 GTP.send(g_delete_req);
1791 alt {
Harald Welte955aa942019-05-03 01:29:29 +02001792 [] BSSGP[0].receive(tr_SM_DEACT_PDP_REQ_MT(apars.tid, ?, true)) {
Pau Espin Pedrole6f071f2019-05-29 13:02:42 +02001793 f_send_l3_gmm_llc(ts_SM_DEACT_PDP_ACCEPT_MO(apars.tid), 0);
1794 }
1795 [] as_xid(apars, 0);
1796 }
1797 GTP.receive(tr_GTPC_MsgType(?, deletePDPContextResponse, apars.ggsn_tei_c)) -> value g_ud_first {
1798 if (g_ud_first.gtpc.gtpc_pdu.deletePDPContextResponse.cause.causevalue != '80'O) {
1799 setverdict(fail, "Received deletePDPContextResponse cause is not 'Request accepted'");
1800 mtc.stop;
1801 }
1802 };
1803
1804 /* Send duplicate DeleteCtxReq */
1805 log("First deletePDPContextResponse received, dropping & retransmitting retransmission of deletePDPContextRequest");
1806 GTP.send(g_delete_req);
1807 GTP.receive(tr_GTPC_MsgType(?, deletePDPContextResponse, apars.ggsn_tei_c)) -> value g_ud_second {
1808 if (g_ud_first != g_ud_second) {
1809 setverdict(fail, "Retransmitted GTP message deletePDPContextResponse is different from original one!");
1810 mtc.stop;
1811 }
1812 }
1813
1814 /* Let's send now a new DeleteCtxReq (increased seq_nr) to make sure it
1815 * is handled differently by SGSN (expect "non-existent" cause) */
1816 g_delete_req := ts_GTPC_DeletePDP(peer, seq_nr + 1, apars.sgsn_tei_c, apars.nsapi, '1'B);
1817 GTP.send(g_delete_req);
1818 /* Response with cause "non-existent" must be sent with TEID 0 according to specs */
1819 GTP.receive(tr_GTPC_MsgType(?, deletePDPContextResponse, '00000000'O)) -> value g_ud_second {
1820 if (g_ud_second.gtpc.gtpc_pdu.deletePDPContextResponse.cause.causevalue != 'C0'O) {
1821 setverdict(fail, "Received deletePDPContextResponse cause is not 'Non-existent'");
1822 mtc.stop;
1823 }
1824 }
1825
1826 setverdict(pass);
1827}
1828testcase TC_attach_pdp_act_deact_gtp_retrans_resp() runs on test_CT {
1829 var BSSGP_ConnHdlr vc_conn;
1830 f_init();
1831 vc_conn := f_start_handler(refers(f_TC_attach_pdp_act_deact_gtp_retrans_resp), testcasename(), g_gb, 28);
1832 vc_conn.done;
1833}
1834
Alexander Couzens5e307b42018-05-22 18:12:20 +02001835private function f_TC_hlr_location_cancel_request_update(charstring id) runs on BSSGP_ConnHdlr {
1836 /* MS: perform regular attach */
1837 f_TC_attach(id);
1838
1839 /* HLR: cancel the location request */
1840 GSUP.send(ts_GSUP_CL_REQ(g_pars.imsi, OSMO_GSUP_CANCEL_TYPE_UPDATE));
1841 GSUP.receive(tr_GSUP_CL_RES(g_pars.imsi));
Alexander Couzens5e307b42018-05-22 18:12:20 +02001842
1843 /* ensure no Detach Request got received */
1844 timer T := 5.0;
1845 T.start;
1846 alt {
Harald Welte955aa942019-05-03 01:29:29 +02001847 [] BSSGP[0].receive(tr_GMM_DET_REQ_MT(*, *, *)) {
Alexander Couzens5e307b42018-05-22 18:12:20 +02001848 T.stop;
1849 setverdict(fail, "Unexpected GMM Detach Request");
Daniel Willmannafce8662018-07-06 23:11:32 +02001850 mtc.stop;
Alexander Couzens5e307b42018-05-22 18:12:20 +02001851 }
1852 [] T.timeout {
1853 setverdict(pass);
Daniel Willmannafce8662018-07-06 23:11:32 +02001854 mtc.stop;
Alexander Couzens5e307b42018-05-22 18:12:20 +02001855 }
Alexander Couzens0e510e62018-07-28 23:06:00 +02001856 [] BSSGP[0].receive {
Alexander Couzens5e307b42018-05-22 18:12:20 +02001857 repeat;
1858 }
1859 }
1860}
1861
Pau Espin Pedrol482dde62018-07-18 13:47:42 +02001862/* ATTACH + PDP CTX ACT + user plane traffic + ERROR IND in MT direction */
1863private function f_TC_attach_pdp_act_user_error_ind_ggsn(charstring id) runs on BSSGP_ConnHdlr {
1864 var PdpActPars apars := valueof(t_PdpActPars(mp_ggsn_ip));
1865
1866 /* first perform regular attach */
1867 f_TC_attach(id);
1868 /* then activate PDP context */
1869 f_pdp_ctx_act(apars);
1870 /* then transceive a downlink PDU */
1871 f_gtpu_xceive_mo(apars, f_rnd_octstring(200));
1872
1873 /* Send Error indication as response from upload PDU and expect deact towards MS */
1874 f_pdp_ctx_deact_mt(apars, true);
1875}
1876testcase TC_attach_pdp_act_user_error_ind_ggsn() runs on test_CT {
1877 var BSSGP_ConnHdlr vc_conn;
1878 f_init();
Alexander Couzens51114d12018-07-31 18:41:56 +02001879 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 +02001880 vc_conn.done;
1881}
1882
Alexander Couzens5e307b42018-05-22 18:12:20 +02001883testcase TC_hlr_location_cancel_request_update() runs on test_CT {
1884 /* MS <-> SGSN: GMM Attach
1885 * HLR -> SGSN: Cancel Location Request
1886 * HLR <- SGSN: Cancel Location Ack
1887 */
1888 var BSSGP_ConnHdlr vc_conn;
1889 f_init();
1890 f_sleep(1.0);
Alexander Couzens51114d12018-07-31 18:41:56 +02001891 vc_conn := f_start_handler(refers(f_TC_hlr_location_cancel_request_update), testcasename(), g_gb, 31);
Alexander Couzens5e307b42018-05-22 18:12:20 +02001892 vc_conn.done;
1893}
1894
1895
Alexander Couzensc87967a2018-05-22 16:09:54 +02001896private function f_TC_hlr_location_cancel_request_withdraw(charstring id) runs on BSSGP_ConnHdlr {
1897 /* MS: perform regular attach */
1898 f_TC_attach(id);
1899
1900 /* HLR: cancel the location request */
1901 GSUP.send(ts_GSUP_CL_REQ(g_pars.imsi, OSMO_GSUP_CANCEL_TYPE_WITHDRAW));
1902 GSUP.receive(tr_GSUP_CL_RES(g_pars.imsi));
1903 GSUP.send(ts_GSUP_UL_RES(g_pars.imsi));
1904
1905 /* MS: receive a Detach Request */
Harald Welte955aa942019-05-03 01:29:29 +02001906 BSSGP[0].receive(tr_GMM_DET_REQ_MT(c_GMM_DTT_MT_IMSI_DETACH, ?, ?));
Alexander Couzenscdfb7512018-07-31 15:37:14 +02001907 f_send_l3_gmm_llc(ts_GMM_DET_ACCEPT_MO);
Alexander Couzensc87967a2018-05-22 16:09:54 +02001908
1909 setverdict(pass);
1910}
1911
1912testcase TC_hlr_location_cancel_request_withdraw() runs on test_CT {
1913 /* MS <-> SGSN: GMM Attach
1914 * HLR -> SGSN: Cancel Location Request
1915 * HLR <- SGSN: Cancel Location Ack
1916 * MS <- SGSN: Detach Request
1917 * SGSN-> MS: Detach Complete
1918 */
1919 var BSSGP_ConnHdlr vc_conn;
1920 f_init();
1921 f_sleep(1.0);
Alexander Couzens51114d12018-07-31 18:41:56 +02001922 vc_conn := f_start_handler(refers(f_TC_hlr_location_cancel_request_withdraw), testcasename(), g_gb, 29);
Alexander Couzensc87967a2018-05-22 16:09:54 +02001923 vc_conn.done;
1924}
1925
1926
Alexander Couzens6c47f292018-05-22 17:09:49 +02001927private function f_hlr_location_cancel_request_unknown_subscriber(
1928 charstring id,
1929 GSUP_CancelType canceltype) runs on BSSGP_ConnHdlr {
1930
1931 /* HLR: cancel the location request */
1932 GSUP.send(ts_GSUP_CL_REQ(g_pars.imsi, canceltype));
1933
1934 /* cause 2 = IMSI_UNKNOWN */
1935 GSUP.receive(tr_GSUP_CL_ERR(g_pars.imsi, 2));
1936
1937 setverdict(pass);
1938}
1939
1940private function f_TC_hlr_location_cancel_request_unknown_subscriber_withdraw(charstring id) runs on BSSGP_ConnHdlr {
Alexander Couzensace6fc62018-06-05 16:29:02 +02001941 f_hlr_location_cancel_request_unknown_subscriber(id, OSMO_GSUP_CANCEL_TYPE_WITHDRAW);
Alexander Couzens6c47f292018-05-22 17:09:49 +02001942}
1943
1944testcase TC_hlr_location_cancel_request_unknown_subscriber_withdraw() runs on test_CT {
1945 /* HLR -> SGSN: Cancel Location Request
1946 * HLR <- SGSN: Cancel Location Error
1947 */
1948
1949 var BSSGP_ConnHdlr vc_conn;
1950 f_init();
1951 f_sleep(1.0);
Alexander Couzens51114d12018-07-31 18:41:56 +02001952 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 +02001953 vc_conn.done;
1954}
1955
1956private function f_TC_hlr_location_cancel_request_unknown_subscriber_update(charstring id) runs on BSSGP_ConnHdlr {
Alexander Couzensace6fc62018-06-05 16:29:02 +02001957 f_hlr_location_cancel_request_unknown_subscriber(id, OSMO_GSUP_CANCEL_TYPE_WITHDRAW);
Alexander Couzens6c47f292018-05-22 17:09:49 +02001958}
1959
1960testcase TC_hlr_location_cancel_request_unknown_subscriber_update() runs on test_CT {
1961 /* HLR -> SGSN: Cancel Location Request
1962 * HLR <- SGSN: Cancel Location Error
1963 */
1964
1965 var BSSGP_ConnHdlr vc_conn;
1966 f_init();
1967 f_sleep(1.0);
Alexander Couzens51114d12018-07-31 18:41:56 +02001968 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 +02001969 vc_conn.done;
1970}
1971
Alexander Couzens49bb4b42018-06-05 16:28:36 +02001972private function f_TC_attach_detach_check_subscriber_list(charstring id) runs on BSSGP_ConnHdlr {
1973 f_TC_attach(id);
1974 f_detach_mo(c_GMM_DTT_MO_GPRS, true, true);
1975}
Alexander Couzens6c47f292018-05-22 17:09:49 +02001976
Alexander Couzens49bb4b42018-06-05 16:28:36 +02001977testcase TC_attach_detach_check_subscriber_list() runs on test_CT {
1978 /* MS <-> SGSN: Attach
1979 * MS -> SGSN: Detach Req (Power off)
1980 * VTY -> SGSN: Check if MS is NOT in subscriber cache
1981 */
1982 var BSSGP_ConnHdlr vc_conn;
1983 var integer id := 33;
1984 var charstring imsi := hex2str(f_gen_imsi(id));
1985
1986 f_init();
Alexander Couzens51114d12018-07-31 18:41:56 +02001987 vc_conn := f_start_handler(refers(f_TC_attach_detach_check_subscriber_list), testcasename(), g_gb, id);
Alexander Couzens49bb4b42018-06-05 16:28:36 +02001988 vc_conn.done;
1989
1990 f_vty_transceive_not_match(SGSNVTY, "show subscriber cache", pattern "* IMSI: {imsi}*");
1991}
Alexander Couzens6c47f292018-05-22 17:09:49 +02001992
Alexander Couzens667dd7f2018-06-12 16:24:01 +02001993/* Attempt an attach, but loose the Identification Request (IMEI) */
1994private function f_TC_attach_no_imei_response(charstring id) runs on BSSGP_ConnHdlr {
1995 var integer count_req := 0;
1996 var MobileL3_CommonIE_Types.MobileIdentityLV mi;
1997
Alexander Couzenscdfb7512018-07-31 15:37:14 +02001998 f_send_l3_gmm_llc(ts_GMM_ATTACH_REQ(f_mi_get_lv(), f_random_RAI(), true, false, omit, omit));
Alexander Couzens667dd7f2018-06-12 16:24:01 +02001999
2000 alt {
Harald Welte955aa942019-05-03 01:29:29 +02002001 [] BSSGP[0].receive(tr_GMM_ATTACH_REJECT(?)) {
Alexander Couzens667dd7f2018-06-12 16:24:01 +02002002 /* break */
2003 }
Harald Welte955aa942019-05-03 01:29:29 +02002004 [] BSSGP[0].receive(tr_GMM_ID_REQ('001'B)) {
Alexander Couzens667dd7f2018-06-12 16:24:01 +02002005 mi := valueof(ts_MI_IMSI_LV(g_pars.imsi));
Alexander Couzenscdfb7512018-07-31 15:37:14 +02002006 f_send_l3_gmm_llc(ts_GMM_ID_RESP(mi));
Alexander Couzens667dd7f2018-06-12 16:24:01 +02002007 repeat;
2008 }
Harald Welte955aa942019-05-03 01:29:29 +02002009 [] BSSGP[0].receive(tr_GMM_ID_REQ('010'B)) {
Alexander Couzens667dd7f2018-06-12 16:24:01 +02002010 /* ignore ID REQ IMEI */
2011 count_req := count_req + 1;
2012 repeat;
2013 }
2014 }
2015 if (count_req != 5) {
2016 setverdict(fail, "Did not received GMM ID Request Type IMEI 5 times!");
Daniel Willmannafce8662018-07-06 23:11:32 +02002017 mtc.stop;
Alexander Couzens667dd7f2018-06-12 16:24:01 +02002018 }
2019 setverdict(pass);
2020}
2021
2022testcase TC_attach_no_imei_response() runs on test_CT {
2023 /* MS -> SGSN: Attach Request IMSI
2024 * MS <- SGSN: Identity Request IMSI (optional)
2025 * MS -> SGSN: Identity Response IMSI (optional)
2026 * MS <- SGSN: Identity Request IMEI
2027 * MS -x SGSN: no response
2028 * MS <- SGSN: re-send: Identity Request IMEI 4x
2029 * MS <- SGSN: Attach Reject
2030 */
2031 var BSSGP_ConnHdlr vc_conn;
2032 f_init();
2033 f_sleep(1.0);
Alexander Couzens51114d12018-07-31 18:41:56 +02002034 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 +02002035 vc_conn.done;
2036}
2037
Alexander Couzens53f20562018-06-12 16:24:12 +02002038/* Attempt an attach, but loose the Identification Request (IMSI) */
2039private function f_TC_attach_no_imsi_response(charstring id) runs on BSSGP_ConnHdlr {
2040 var integer count_req := 0;
2041 var MobileL3_CommonIE_Types.MobileIdentityLV mi;
2042
2043 /* set p_tmsi to use it in Attach Req via f_mi_get_lv() */
2044 g_pars.p_tmsi := 'c0000035'O;
2045
Alexander Couzenscdfb7512018-07-31 15:37:14 +02002046 f_send_l3_gmm_llc(ts_GMM_ATTACH_REQ(f_mi_get_lv(), f_random_RAI(), true, false, omit, omit));
Alexander Couzens53f20562018-06-12 16:24:12 +02002047
2048 alt {
Harald Welte955aa942019-05-03 01:29:29 +02002049 [] BSSGP[0].receive(tr_GMM_ATTACH_REJECT(?)) {
Alexander Couzens53f20562018-06-12 16:24:12 +02002050 /* break */
2051 }
Harald Welte955aa942019-05-03 01:29:29 +02002052 [] BSSGP[0].receive(tr_GMM_ID_REQ('001'B)) {
Alexander Couzens53f20562018-06-12 16:24:12 +02002053 /* ignore ID REQ IMSI */
2054 count_req := count_req + 1;
2055 repeat;
2056 }
Harald Welte955aa942019-05-03 01:29:29 +02002057 [] BSSGP[0].receive(tr_GMM_ID_REQ('010'B)) {
Alexander Couzens53f20562018-06-12 16:24:12 +02002058 mi := valueof(ts_MI_IMEI_LV(g_pars.imei));
Alexander Couzenscdfb7512018-07-31 15:37:14 +02002059 f_send_l3_gmm_llc(ts_GMM_ID_RESP(mi));
Alexander Couzens53f20562018-06-12 16:24:12 +02002060 repeat;
2061 }
2062 }
2063 if (count_req != 5) {
2064 setverdict(fail, "Did not received GMM ID Request Type IMSI 5 times!");
Daniel Willmannafce8662018-07-06 23:11:32 +02002065 mtc.stop;
Alexander Couzens53f20562018-06-12 16:24:12 +02002066 }
2067 setverdict(pass);
2068}
2069
2070testcase TC_attach_no_imsi_response() runs on test_CT {
2071 /* MS -> SGSN: Attach Request TMSI (unknown)
2072 * MS <- SGSN: Identity Request IMEI (optional)
2073 * MS -> SGSN: Identity Response IMEI (optional)
2074 * MS <- SGSN: Identity Request IMSI
2075 * MS -x SGSN: no response
2076 * MS <- SGSN: re-send: Identity Request IMSI 4x
2077 * MS <- SGSN: Attach Reject
2078 */
2079 var BSSGP_ConnHdlr vc_conn;
2080 f_init();
2081 f_sleep(1.0);
Alexander Couzens51114d12018-07-31 18:41:56 +02002082 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 +02002083 vc_conn.done;
2084}
2085
Alexander Couzenscf818962018-06-05 18:00:00 +02002086private function f_sgsn_vty_destroy_subscriber_imsi(TELNETasp_PT pt, charstring imsi) {
2087 f_vty_transceive(pt, "update-subscriber imsi " & imsi & " destroy");
2088}
2089
2090testcase TC_attach_check_subscriber_list() runs on test_CT {
2091 /* MS <-> SGSN: Attach
2092 * VTY -> SGSN: Check if MS is in subscriber cache
2093 */
2094 var BSSGP_ConnHdlr vc_conn;
2095 var integer id := 34;
2096 var charstring imsi := hex2str(f_gen_imsi(id));
2097
2098 f_init();
2099 f_sleep(1.0);
Alexander Couzens51114d12018-07-31 18:41:56 +02002100 vc_conn := f_start_handler(refers(f_TC_attach), testcasename(), g_gb, id);
Alexander Couzenscf818962018-06-05 18:00:00 +02002101 vc_conn.done;
2102
2103 f_vty_transceive_match(SGSNVTY, "show subscriber cache", pattern "* IMSI: {imsi}*");
2104 f_sgsn_vty_destroy_subscriber_imsi(SGSNVTY, imsi);
2105}
2106
Alexander Couzensf9858652018-06-07 16:14:53 +02002107private function f_TC_attach_closed_imsi_added(charstring id) runs on BSSGP_ConnHdlr {
2108 var RoutingAreaIdentificationV old_ra := f_random_RAI();
Harald Welte955aa942019-05-03 01:29:29 +02002109 var PDU_L3_SGSN_MS l3_mt;
Alexander Couzensf9858652018-06-07 16:14:53 +02002110
2111 /* unregister the old IMSI */
2112 f_bssgp_client_unregister(g_pars.imsi);
2113 /* Simulate a foreign IMSI */
Alexander Couzens03d12242018-08-07 16:13:52 +02002114 g_pars.imsi := '001010123456700'H;
Alexander Couzens51114d12018-07-31 18:41:56 +02002115 f_bssgp_client_register(g_pars.imsi, g_pars.tlli, g_pars.bssgp_cell_id[0]);
Alexander Couzensf9858652018-06-07 16:14:53 +02002116
2117 /* there is no auth */
2118 g_pars.net.expect_auth := false;
2119
Alexander Couzenscdfb7512018-07-31 15:37:14 +02002120 f_send_l3_gmm_llc(ts_GMM_ATTACH_REQ(f_mi_get_lv(), old_ra, false, false, omit, omit));
Alexander Couzensf9858652018-06-07 16:14:53 +02002121 f_gmm_auth();
2122 alt {
Harald Welte955aa942019-05-03 01:29:29 +02002123 [] BSSGP[0].receive(tr_GMM_ATTACH_REJECT(?)) {
Alexander Couzensf9858652018-06-07 16:14:53 +02002124 setverdict(fail, "Received unexpected GMM Attach REJECT");
Daniel Willmannafce8662018-07-06 23:11:32 +02002125 mtc.stop;
Alexander Couzensf9858652018-06-07 16:14:53 +02002126 }
Harald Welte955aa942019-05-03 01:29:29 +02002127 [] BSSGP[0].receive(tr_GMM_ATTACH_ACCEPT(*, *, *)) -> value l3_mt {
2128 f_process_attach_accept(l3_mt.msgs.gprs_mm.attachAccept);
Alexander Couzenscdfb7512018-07-31 15:37:14 +02002129 f_send_l3_gmm_llc(ts_GMM_ATTACH_COMPL);
Alexander Couzensf9858652018-06-07 16:14:53 +02002130 setverdict(pass);
2131 }
2132 }
2133}
Alexander Couzens03d12242018-08-07 16:13:52 +02002134
2135private function f_TC_attach_closed_add_vty(charstring id) runs on BSSGP_ConnHdlr {
2136
2137 f_TC_attach_closed_foreign(id);
2138 f_TC_attach_closed_imsi_added(id);
2139
2140}
2141
2142
Alexander Couzensf9858652018-06-07 16:14:53 +02002143testcase TC_attach_closed_add_vty() runs on test_CT {
2144 /* VTY-> SGSN: policy close
2145 * MS -> SGSN: Attach Request
2146 * MS <- SGSN: Identity Request IMSI
2147 * MS -> SGSN: Identity Response IMSI
2148 * MS <- SGSN: Attach Reject
2149 * VTY-> SGSN: policy imsi-acl add IMSI
2150 * MS -> SGSN: Attach Request
2151 * MS <- SGSN: Identity Request IMSI
2152 * MS -> SGSN: Identity Response IMSI
2153 * MS <- SGSN: Identity Request IMEI
2154 * MS -> SGSN: Identity Response IMEI
2155 * MS <- SGSN: Attach Accept
2156 */
2157 var BSSGP_ConnHdlr vc_conn;
2158 f_init();
2159 f_sleep(1.0);
2160 f_vty_config(SGSNVTY, "sgsn", "auth-policy closed");
2161 f_vty_config(SGSNVTY, "sgsn", "imsi-acl del 001010123456789");
Alexander Couzens03d12242018-08-07 16:13:52 +02002162 f_vty_config(SGSNVTY, "sgsn", "imsi-acl del 001010123456700");
2163 f_vty_config(SGSNVTY, "sgsn", "imsi-acl add 001010123456700");
Alexander Couzensf9858652018-06-07 16:14:53 +02002164 /* test with foreign IMSI: Must Reject */
Alexander Couzens03d12242018-08-07 16:13:52 +02002165 vc_conn := f_start_handler(refers(f_TC_attach_closed_add_vty), testcasename(), g_gb, 9);
Alexander Couzensf9858652018-06-07 16:14:53 +02002166 vc_conn.done;
2167}
2168
Alexander Couzens0085bd72018-06-12 19:08:44 +02002169/* Attempt an attach, but never answer a Attach Complete */
2170private function f_TC_attach_check_complete_resend(charstring id) runs on BSSGP_ConnHdlr {
2171 var integer count_req := 0;
2172
Alexander Couzenscdfb7512018-07-31 15:37:14 +02002173 f_send_l3_gmm_llc(ts_GMM_ATTACH_REQ(f_mi_get_lv(), f_random_RAI(), true, false, omit, omit));
Alexander Couzens0085bd72018-06-12 19:08:44 +02002174 f_gmm_auth();
2175
Alexander Couzensfa0a75f2018-08-07 15:45:04 +02002176 timer T := 10.0;
2177 T.start;
Alexander Couzens0085bd72018-06-12 19:08:44 +02002178 alt {
Alexander Couzensfa0a75f2018-08-07 15:45:04 +02002179 [] T.timeout {
Alexander Couzens0085bd72018-06-12 19:08:44 +02002180 /* break */
2181 }
Harald Welte955aa942019-05-03 01:29:29 +02002182 [] BSSGP[0].receive(tr_GMM_ATTACH_ACCEPT(*, *, *)) {
Alexander Couzens0085bd72018-06-12 19:08:44 +02002183 /* ignore */
2184 count_req := count_req + 1;
Alexander Couzensfa0a75f2018-08-07 15:45:04 +02002185 T.start;
Alexander Couzens0085bd72018-06-12 19:08:44 +02002186 repeat;
2187 }
2188 }
2189 if (count_req != 5) {
2190 setverdict(fail, "Did not received GMM Attach Complete.");
Daniel Willmannafce8662018-07-06 23:11:32 +02002191 mtc.stop;
Alexander Couzens0085bd72018-06-12 19:08:44 +02002192 }
2193 setverdict(pass);
2194}
2195
2196testcase TC_attach_check_complete_resend() runs on test_CT {
2197 /* MS -> SGSN: Attach Request IMSI
2198 * MS <- SGSN: Identity Request *
2199 * MS -> SGSN: Identity Response *
2200 * MS <- SGSN: Attach Complete 5x
2201 */
2202 var BSSGP_ConnHdlr vc_conn;
2203 f_init();
2204 f_sleep(1.0);
Alexander Couzens51114d12018-07-31 18:41:56 +02002205 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 +02002206 vc_conn.done;
2207}
2208
Alexander Couzens5dce90d2018-07-31 03:16:37 +02002209private function f_routing_area_update(RoutingAreaIdentificationV ra, integer bssgp := 0) runs on BSSGP_ConnHdlr {
Harald Welte955aa942019-05-03 01:29:29 +02002210 var PDU_L3_SGSN_MS l3_mt;
Alexander Couzens5dce90d2018-07-31 03:16:37 +02002211
2212 /* then send RAU */
Alexander Couzenscdfb7512018-07-31 15:37:14 +02002213 f_send_l3_gmm_llc(ts_GMM_RAU_REQ(f_mi_get_lv(), GPRS_UPD_T_RA, g_pars.ra, false, omit, omit), bssgp);
Alexander Couzens5dce90d2018-07-31 03:16:37 +02002214 alt {
Harald Welte955aa942019-05-03 01:29:29 +02002215 [] BSSGP[bssgp].receive(tr_GMM_RAU_ACCEPT) -> value l3_mt {
2216 f_process_rau_accept(l3_mt.msgs.gprs_mm.routingAreaUpdateAccept, bssgp);
Alexander Couzenscdfb7512018-07-31 15:37:14 +02002217 f_send_l3_gmm_llc(ts_GMM_RAU_COMPL, bssgp);
Alexander Couzens5dce90d2018-07-31 03:16:37 +02002218 setverdict(pass);
2219 }
Harald Welte955aa942019-05-03 01:29:29 +02002220 [] BSSGP[bssgp].receive(tr_GMM_RAU_REJECT) {
Alexander Couzens5dce90d2018-07-31 03:16:37 +02002221 setverdict(fail, "Unexpected RAU Reject");
2222 mtc.stop;
2223 }
2224 [] BSSGP[bssgp].receive { repeat; }
2225 }
2226}
2227
Alexander Couzensbfda9212018-07-31 03:17:33 +02002228private function f_TC_attach_rau_a_a(charstring id) runs on BSSGP_ConnHdlr {
Alexander Couzensbfda9212018-07-31 03:17:33 +02002229 /* first perform regular attach */
2230 f_TC_attach(id);
2231
2232 /* then send RAU */
2233 f_routing_area_update(g_pars.ra);
2234
2235 /* do another RAU */
2236 f_routing_area_update(g_pars.ra);
2237
2238 f_detach_mo(c_GMM_DTT_MO_GPRS, true, true);
2239}
2240
2241testcase TC_attach_rau_a_a() runs on test_CT {
2242 /* MS <-> SGSN: Successful Attach
2243 * MS -> SGSN: Routing Area Update Request
2244 * MS <- SGSN: Routing Area Update Accept
2245 * MS -> SGSN: Routing Area Update Request
2246 * MS <- SGSN: Routing Area Update Accept
2247 * MS -> SGSN: Detach (PowerOff)
2248 */
2249 var BSSGP_ConnHdlr vc_conn;
2250 f_init();
2251 f_sleep(1.0);
2252 vc_conn := f_start_handler(refers(f_TC_attach_rau_a_a), testcasename(), g_gb, 37);
2253 vc_conn.done;
2254}
2255
Alexander Couzensbe837bd2018-07-31 04:20:11 +02002256private function f_TC_attach_rau_a_b(charstring id) runs on BSSGP_ConnHdlr {
Alexander Couzensbe837bd2018-07-31 04:20:11 +02002257 f_TC_attach(id);
2258
2259 log("attach complete sending rau");
2260 f_routing_area_update(g_pars.ra, 0);
2261
2262 log("rau complete unregistering");
2263 f_bssgp_client_unregister(g_pars.imsi);
2264 f_bssgp_client_register(g_pars.imsi, g_pars.tlli, g_pars.bssgp_cell_id[1], BSSGP_PROC[1]);
2265
2266 log("sending second RAU via different RA");
2267 f_routing_area_update(f_cellid_to_RAI(g_pars.bssgp_cell_id[1]), 1);
2268
2269 f_detach_mo(c_GMM_DTT_MO_GPRS, true, true, 1);
2270}
2271
2272testcase TC_attach_rau_a_b() runs on test_CT {
2273 /* MS <-> SGSN: Successful Attach
2274 * MS -> SGSN: Routing Area _a_ Update Request
2275 * MS <- SGSN: Routing Area _a_ Update Accept
2276 * MS -> SGSN: Routing Area _b_ Update Request
2277 * MS <- SGSN: Routing Area _b_ Update Accept
2278 * MS -> SGSN: Detach (PowerOff)
2279 */
2280 var BSSGP_ConnHdlr vc_conn;
2281 f_init();
2282 f_sleep(1.0);
2283 vc_conn := f_start_handler(refers(f_TC_attach_rau_a_b), testcasename(), g_gb, 38);
2284 vc_conn.done;
2285}
2286
Alexander Couzenscf3c93d2018-08-07 19:48:27 +02002287private function f_TC_attach_gmm_attach_req_while_gmm_attach(charstring id) runs on BSSGP_ConnHdlr {
2288 var integer count_req := 0;
2289 var MobileL3_CommonIE_Types.MobileIdentityLV mi;
2290 var RoutingAreaIdentificationV rand_rai := f_random_RAI();
Harald Welte955aa942019-05-03 01:29:29 +02002291 var PDU_L3_SGSN_MS l3_mt;
Alexander Couzenscf3c93d2018-08-07 19:48:27 +02002292
2293 f_send_l3_gmm_llc(ts_GMM_ATTACH_REQ(f_mi_get_lv(), rand_rai, true, false, omit, omit));
2294
2295 alt {
Harald Welte955aa942019-05-03 01:29:29 +02002296 [] BSSGP[0].receive(tr_GMM_ATTACH_REJECT(?)) {
Alexander Couzenscf3c93d2018-08-07 19:48:27 +02002297 setverdict(fail, "Unexpected GMM ATTACH REJECT");
2298 mtc.stop;
2299 }
Harald Welte955aa942019-05-03 01:29:29 +02002300 [] BSSGP[0].receive(tr_GMM_ID_REQ('001'B)) {
Alexander Couzenscf3c93d2018-08-07 19:48:27 +02002301 mi := valueof(ts_MI_IMSI_LV(g_pars.imsi));
2302 f_send_l3_gmm_llc(ts_GMM_ID_RESP(mi));
2303 repeat;
2304 }
Harald Welte955aa942019-05-03 01:29:29 +02002305 [] BSSGP[0].receive(tr_GMM_ID_REQ('010'B)) {
Alexander Couzenscf3c93d2018-08-07 19:48:27 +02002306 /* send out a second GMM_Attach Request.
2307 * If the SGSN follows the rules, this 2nd ATTACH REQ should be ignored, because
2308 * of the same content */
2309 f_send_l3_gmm_llc(ts_GMM_ATTACH_REQ(f_mi_get_lv(), rand_rai, true, false, omit, omit));
2310 mi := valueof(ts_MI_IMEI_LV(g_pars.imei));
2311 f_send_l3_gmm_llc(ts_GMM_ID_RESP(mi));
2312 }
2313 }
2314 f_sleep(1.0);
2315
2316 /* we've sent already a IMEI answer, we should NOT asked again for IMEI */
2317 alt {
Harald Welte955aa942019-05-03 01:29:29 +02002318 [] BSSGP[0].receive(tr_GMM_ID_REQ('001'B)) {
Alexander Couzenscf3c93d2018-08-07 19:48:27 +02002319 mi := valueof(ts_MI_IMSI_LV(g_pars.imsi));
2320 f_send_l3_gmm_llc(ts_GMM_ID_RESP(mi));
2321 repeat;
2322 }
Harald Welte955aa942019-05-03 01:29:29 +02002323 [] BSSGP[0].receive(tr_GMM_ID_REQ('010'B)) {
Alexander Couzenscf3c93d2018-08-07 19:48:27 +02002324 setverdict(fail, "Unexpected GMM ID REQ (IMEI).");
2325 mtc.stop;
2326 }
Harald Welte955aa942019-05-03 01:29:29 +02002327 [] BSSGP[0].receive(tr_GMM_ATTACH_REJECT(?)) {
Alexander Couzenscf3c93d2018-08-07 19:48:27 +02002328 setverdict(fail, "Unexpected GMM ATTACH REJECT");
2329 mtc.stop;
2330 }
Harald Welte955aa942019-05-03 01:29:29 +02002331 [] BSSGP[0].receive(tr_GMM_ATTACH_ACCEPT('001'B, ?, ?)) -> value l3_mt {
2332 f_process_attach_accept(l3_mt.msgs.gprs_mm.attachAccept);
Alexander Couzenscf3c93d2018-08-07 19:48:27 +02002333 f_send_l3_gmm_llc(ts_GMM_ATTACH_COMPL);
2334 setverdict(pass);
2335 /* FIXME: Extract P-TMSI, if any. Only send Complete if necessary */
2336 }
2337 }
2338}
2339
2340testcase TC_attach_gmm_attach_req_while_gmm_attach() runs on test_CT {
2341 /* Testing if the SGSN ignore Attach Request with the exact same content */
2342 /* MS -> SGSN: Attach Request IMSI
2343 * MS <- SGSN: Identity Request IMSI (optional)
2344 * MS -> SGSN: Identity Response IMSI (optional)
2345 * MS <- SGSN: Identity Request IMEI
2346 * MS -> SGSN: Attach Request (2nd)
2347 * MS <- SGSN: Identity Response IMEI
2348 * MS <- SGSN: Attach Accept
2349 * MS -> SGSN: Attach Complete
2350 */
2351 var BSSGP_ConnHdlr vc_conn;
2352 f_init();
2353 f_sleep(1.0);
2354 f_vty_config(SGSNVTY, "sgsn", "auth-policy accept-all");
2355 vc_conn := f_start_handler(refers(f_TC_attach_gmm_attach_req_while_gmm_attach), testcasename(), g_gb, 39);
2356 vc_conn.done;
2357}
2358
Alexander Couzens0c6324f2018-09-14 16:37:04 +02002359private function f_TC_attach_usim_resync(charstring id) runs on BSSGP_ConnHdlr {
Alexander Couzens0c6324f2018-09-14 16:37:04 +02002360 var RoutingAreaIdentificationV old_ra := f_random_RAI();
2361
2362 var template PDU_L3_MS_SGSN attach_req := ts_GMM_ATTACH_REQ(f_mi_get_lv(), old_ra, false, false, omit, omit);
2363
2364 /* send Attach Request */
2365 /* indicate R99 capability of the MS to enable UMTS AKA in presence of
2366 * 3G auth vectors */
2367 attach_req.msgs.gprs_mm.attachRequest.msNetworkCapability.msNetworkCapabilityV.revisionLevelIndicatior := '1'B;
2368 /* The thing is, if the solSACapability is 'omit', then the
2369 * revisionLevelIndicatior is at the wrong place! */
2370 attach_req.msgs.gprs_mm.attachRequest.msNetworkCapability.msNetworkCapabilityV.solSACapability := '0'B;
2371 f_send_l3_gmm_llc(attach_req);
2372
2373 /* do the auth */
2374 var PDU_L3_MS_SGSN l3_mo;
2375 var PDU_L3_SGSN_MS l3_mt;
2376 var default di := activate(as_mm_identity());
2377
2378 var GSUP_IE auth_tuple;
2379 var template AuthenticationParameterAUTNTLV autn;
2380
2381 g_pars.vec := f_gen_auth_vec_3g();
2382 autn := {
2383 elementIdentifier := '28'O,
2384 lengthIndicator := lengthof(g_pars.vec.autn),
2385 autnValue := g_pars.vec.autn
2386 };
2387 auth_tuple := valueof(ts_GSUP_IE_AuthTuple2G3G(g_pars.vec.rand,
2388 g_pars.vec.sres,
2389 g_pars.vec.kc,
2390 g_pars.vec.ik,
2391 g_pars.vec.ck,
2392 g_pars.vec.autn,
2393 g_pars.vec.res));
2394 log("GSUP sends 2G and 3G auth tuples", auth_tuple);
2395 GSUP.receive(tr_GSUP_SAI_REQ(g_pars.imsi));
2396 GSUP.send(ts_GSUP_SAI_RES(g_pars.imsi, auth_tuple));
2397
2398 var template PDU_L3_SGSN_MS auth_ciph_req := tr_GMM_AUTH_REQ(g_pars.vec.rand);
2399 auth_ciph_req.msgs.gprs_mm.authenticationAndCipheringRequest.authenticationParameterAUTN := autn;
Harald Welte955aa942019-05-03 01:29:29 +02002400 BSSGP[0].receive(auth_ciph_req) -> value l3_mt;
Alexander Couzens0c6324f2018-09-14 16:37:04 +02002401
2402 /* send the gmm auth failure with resync IE */
2403 f_send_l3_gmm_llc(ts_GMM_AUTH_FAIL_UMTS_AKA_RESYNC(g_pars.vec.auts));
2404
2405 /* wait for the GSUP resync request */
2406 GSUP.receive(tr_GSUP_SAI_REQ_UMTS_AKA_RESYNC(
2407 g_pars.imsi,
2408 g_pars.vec.auts,
2409 g_pars.vec.rand));
2410
2411 /* generate new key material */
2412 g_pars.vec := f_gen_auth_vec_3g();
2413 autn := {
2414 elementIdentifier := '28'O,
2415 lengthIndicator := lengthof(g_pars.vec.autn),
2416 autnValue := g_pars.vec.autn
2417 };
2418
2419 auth_tuple := valueof(ts_GSUP_IE_AuthTuple2G3G(g_pars.vec.rand,
2420 g_pars.vec.sres,
2421 g_pars.vec.kc,
2422 g_pars.vec.ik,
2423 g_pars.vec.ck,
2424 g_pars.vec.autn,
2425 g_pars.vec.res));
2426 /* send new key material */
2427 GSUP.send(ts_GSUP_SAI_RES(g_pars.imsi, auth_tuple));
2428
2429 /* wait for the new Auth Request */
2430 auth_ciph_req := tr_GMM_AUTH_REQ(g_pars.vec.rand);
2431 auth_ciph_req.msgs.gprs_mm.authenticationAndCipheringRequest.authenticationParameterAUTN := autn;
Harald Welte955aa942019-05-03 01:29:29 +02002432 BSSGP[0].receive(auth_ciph_req) -> value l3_mt;
Alexander Couzens0c6324f2018-09-14 16:37:04 +02002433 var BIT4 ac_ref := l3_mt.msgs.gprs_mm.authenticationAndCipheringRequest.acReferenceNumber.valueField;
2434 var template PDU_L3_MS_SGSN auth_ciph_resp := ts_GMM_AUTH_RESP_2G(ac_ref, g_pars.vec.sres);
2435 auth_ciph_resp := ts_GMM_AUTH_RESP_2G(ac_ref, g_pars.vec.sres);
2436 auth_ciph_resp.msgs.gprs_mm.authenticationAndCipheringResponse.authenticationParResp := {
2437 valueField := substr(g_pars.vec.res, 0, 4)
2438 };
2439 auth_ciph_resp.msgs.gprs_mm.authenticationAndCipheringResponse.authenticationRespParExt := {
2440 elementIdentifier := '21'O,
2441 lengthIndicator := lengthof(g_pars.vec.res) - 4,
2442 valueField := substr(g_pars.vec.res, 4, lengthof(g_pars.vec.res) - 4)
2443 };
2444 l3_mo := valueof(auth_ciph_resp);
2445 if (ispresent(l3_mt.msgs.gprs_mm.authenticationAndCipheringRequest.imeisvRequest) and
2446 l3_mt.msgs.gprs_mm.authenticationAndCipheringRequest.imeisvRequest.valueField == '001'B) {
2447 l3_mo.msgs.gprs_mm.authenticationAndCipheringResponse.imeisv :=
2448 valueof(ts_MI_IMEISV_TLV(g_pars.imei & '0'H));
2449 }
2450 f_send_l3_gmm_llc(l3_mo);
2451 deactivate(di);
2452
2453 /* Expect SGSN to perform LU with HLR */
2454 f_gmm_gsup_lu_isd();
2455
Harald Welte955aa942019-05-03 01:29:29 +02002456 BSSGP[0].receive(tr_GMM_ATTACH_ACCEPT('001'B, ?, ?)) -> value l3_mt {
2457 f_process_attach_accept(l3_mt.msgs.gprs_mm.attachAccept);
Alexander Couzens0c6324f2018-09-14 16:37:04 +02002458 }
2459 f_send_l3_gmm_llc(ts_GMM_ATTACH_COMPL);
2460 setverdict(pass);
2461}
2462
2463testcase TC_attach_usim_resync() runs on test_CT {
2464 /* MS -> SGSN: Attach Request
2465 * MS <- SGSN: Identity Request IMSI
2466 * MS -> SGSN: Identity Response IMSI
2467 * MS <- SGSN: Identity Request IMEI
2468 * MS -> SGSN: Identity Response IMEI
2469 * HLR<- SGSN: SAI Request
2470 * HLR-> SGSN: SAI Response
2471 * MS <- SGSN: Auth Request
2472 * MS -> SGSN: Auth Failure (with AUTS)
2473 * HLR<- SGSN: SAI Request (with AUTS & RAND)
2474 * HLR-> SGSN: SAI Response (new key material)
2475 * MS <- SGSN: Auth Request (new key material)
2476 * MS -> SGSN: Auth Response
2477 * MS <- SGSN: Attach Accept
2478 * MS -> SGSN: Attach Complete
2479 */
2480 var BSSGP_ConnHdlr vc_conn;
2481 f_init();
2482 f_sleep(1.0);
2483 vc_conn := f_start_handler(refers(f_TC_attach_usim_resync), testcasename(), g_gb, 40);
2484 vc_conn.done;
2485}
2486
Harald Weltea05b8072019-04-23 22:35:05 +02002487
2488/* Send LLC NULL to see if the SGSN survives it (OS#3952) */
2489private function f_TC_llc_null(charstring id) runs on BSSGP_ConnHdlr {
2490 f_gmm_attach(false, false);
2491 f_sleep(1.0);
2492 f_send_llc(ts_LLC_NULL('0'B, c_LLC_SAPI_LLGMM, LLC_CR_UL_CMD));
2493 /* try to detach to check if SGSN is still alive */
2494 f_detach_mo(c_GMM_DTT_MO_GPRS, true, true);
2495}
2496testcase TC_llc_null() runs on test_CT {
2497 var BSSGP_ConnHdlr vc_conn;
2498 f_init();
2499 f_sleep(1.0);
2500 vc_conn := f_start_handler(refers(f_TC_llc_null), testcasename(), g_gb, 41);
2501 vc_conn.done;
2502}
2503
Harald Welte645a1512019-04-23 23:18:23 +02002504/* Send LLC SABM to see if the SGSN rejects it properly with DM */
2505private function f_TC_llc_sabm_dm_llgmm(charstring id) runs on BSSGP_ConnHdlr {
2506 f_gmm_attach(false, false);
2507 f_sleep(1.0);
2508 f_send_llc(ts_LLC_SABM({}, '1'B, c_LLC_SAPI_LLGMM, LLC_CR_UL_CMD));
Harald Welte955aa942019-05-03 01:29:29 +02002509 BSSGP[0].receive(tr_LLC_DM(?, c_LLC_SAPI_LLGMM, LLC_CR_DL_RSP));
Harald Welte645a1512019-04-23 23:18:23 +02002510 setverdict(pass);
2511}
2512testcase TC_llc_sabm_dm_llgmm() runs on test_CT {
2513 var BSSGP_ConnHdlr vc_conn;
2514 f_init();
2515 f_sleep(1.0);
2516 vc_conn := f_start_handler(refers(f_TC_llc_sabm_dm_llgmm), testcasename(), g_gb, 42);
2517 vc_conn.done;
2518}
2519
2520/* Send LLC SABM to see if the SGSN rejects it properly with DM */
2521private function f_TC_llc_sabm_dm_ll5(charstring id) runs on BSSGP_ConnHdlr {
2522 f_gmm_attach(false, false);
2523 f_sleep(1.0);
2524 f_send_llc(ts_LLC_SABM({}, '1'B, c_LLC_SAPI_LL5, LLC_CR_UL_CMD));
Harald Welte955aa942019-05-03 01:29:29 +02002525 BSSGP[0].receive(tr_LLC_DM(?, c_LLC_SAPI_LL5, LLC_CR_DL_RSP));
Harald Welte645a1512019-04-23 23:18:23 +02002526 setverdict(pass);
2527}
2528testcase TC_llc_sabm_dm_ll5() runs on test_CT {
2529 var BSSGP_ConnHdlr vc_conn;
2530 f_init();
2531 f_sleep(1.0);
2532 vc_conn := f_start_handler(refers(f_TC_llc_sabm_dm_ll5), testcasename(), g_gb, 43);
2533 vc_conn.done;
2534}
2535
Harald Welte2aaac1b2019-05-02 10:02:53 +02002536/* test XID handshake with empty L3 info: expect empty return (some phones require that, OS#3426 */
2537private function f_TC_xid_empty_l3(charstring id) runs on BSSGP_ConnHdlr {
2538 var PdpActPars apars := valueof(t_PdpActPars(mp_ggsn_ip));
2539 var template (value) XID_Information xid;
2540 var template XID_Information xid_rx;
2541
2542 /* first perform regular attach */
2543 f_TC_attach(id);
2544 /* then activate PDP context */
2545 f_pdp_ctx_act(apars);
2546
2547 /* start MO XID */
2548 xid := { ts_XID_L3(''O) };
2549 xid_rx := { tr_XID_L3(''O) };
2550 f_send_llc(ts_LLC_XID_MO_CMD(xid, apars.sapi));
2551 alt {
Harald Welte955aa942019-05-03 01:29:29 +02002552 [] BSSGP[0].receive(tr_LLC_XID(xid_rx, apars.sapi));
Harald Welte2aaac1b2019-05-02 10:02:53 +02002553 [] as_xid(apars);
2554 }
2555 setverdict(pass);
2556}
2557testcase TC_xid_empty_l3() runs on test_CT {
2558 var BSSGP_ConnHdlr vc_conn;
2559 f_init();
2560 f_sleep(1.0);
2561 vc_conn := f_start_handler(refers(f_TC_xid_empty_l3), testcasename(), g_gb, 44);
2562 vc_conn.done;
2563}
2564
2565private function f_TC_xid_n201u(charstring id) runs on BSSGP_ConnHdlr {
2566 var PdpActPars apars := valueof(t_PdpActPars(mp_ggsn_ip));
2567 var template (value) XID_Information xid;
2568 var template XID_Information xid_rx;
2569
2570 /* first perform regular attach */
2571 f_TC_attach(id);
2572 /* then activate PDP context */
2573 f_pdp_ctx_act(apars);
2574
2575 /* start MO XID */
2576 xid := { ts_XID_N201U(1234) };
2577 xid_rx := { tr_XID_N201U(1234) };
2578 f_send_llc(ts_LLC_XID_MO_CMD(xid, apars.sapi));
2579 alt {
Harald Welte955aa942019-05-03 01:29:29 +02002580 [] BSSGP[0].receive(tr_LLC_XID_MT_RSP(xid_rx, apars.sapi));
Harald Welte2aaac1b2019-05-02 10:02:53 +02002581 [] as_xid(apars);
2582 }
2583 setverdict(pass);
2584}
2585testcase TC_xid_n201u() runs on test_CT {
2586 var BSSGP_ConnHdlr vc_conn;
2587 f_init();
2588 f_sleep(1.0);
2589 vc_conn := f_start_handler(refers(f_TC_xid_n201u), testcasename(), g_gb, 45);
2590 vc_conn.done;
2591}
2592
Alexander Couzens6bee0872019-05-11 01:48:50 +02002593private function f_TC_attach_pdp_act_gmm_detach(charstring id) runs on BSSGP_ConnHdlr {
2594 var PdpActPars apars := valueof(t_PdpActPars(mp_ggsn_ip));
2595
2596 /* first perform regular attach */
2597 f_TC_attach(id);
2598 /* then activate PDP context */
2599 f_pdp_ctx_act(apars);
2600 /* do a normal detach */
2601 f_detach_mo(c_GMM_DTT_MO_GPRS, false, true);
2602}
2603
2604testcase TC_attach_pdp_act_gmm_detach() runs on test_CT {
2605 /* MS -> SGSN: Attach Request
2606 * MS <-> SGSN: [..]
2607 * MS -> SGSN: Attach Complete
2608 * MS -> SGSN: PDP Activate Request
2609 * MS <- SGSN: PDP Activate Accept
2610 * MS -> SGSN: GMM Detach Request
2611 * MS <- SGSN: GMM Detach Accept
2612 */
2613 var BSSGP_ConnHdlr vc_conn;
2614 f_init();
2615 vc_conn := f_start_handler(refers(f_TC_attach_pdp_act_gmm_detach), testcasename(), g_gb, 26);
2616 vc_conn.done;
2617}
Harald Welte645a1512019-04-23 23:18:23 +02002618
2619
Harald Welte5ac31492018-02-15 20:39:13 +01002620control {
Harald Welte5b7c8122018-02-16 21:48:17 +01002621 execute( TC_attach() );
Neels Hofmeyr8df7d152018-03-14 19:03:28 +01002622 execute( TC_attach_mnc3() );
Neels Hofmeyr0ecb2e32018-04-30 15:13:55 +02002623 execute( TC_attach_umts_aka_umts_res() );
2624 execute( TC_attach_umts_aka_gsm_sres() );
Harald Welte5b7c8122018-02-16 21:48:17 +01002625 execute( TC_attach_auth_id_timeout() );
2626 execute( TC_attach_auth_sai_timeout() );
Harald Weltefe253882018-02-17 09:25:00 +01002627 execute( TC_attach_auth_sai_reject() );
Harald Welte5b7c8122018-02-16 21:48:17 +01002628 execute( TC_attach_gsup_lu_timeout() );
Harald Welteb7c14e92018-02-17 09:29:16 +01002629 execute( TC_attach_gsup_lu_reject() );
Harald Welte3823e2e2018-02-16 21:53:48 +01002630 execute( TC_attach_combined() );
Harald Welte76dee092018-02-16 22:12:59 +01002631 execute( TC_attach_accept_all() );
Harald Welteb2124b22018-02-16 22:26:56 +01002632 execute( TC_attach_closed() );
Alexander Couzens667dd7f2018-06-12 16:24:01 +02002633 execute( TC_attach_no_imei_response() );
Alexander Couzens53f20562018-06-12 16:24:12 +02002634 execute( TC_attach_no_imsi_response() );
Alexander Couzensd81876a2018-08-07 12:43:16 +02002635 execute( TC_attach_closed_add_vty(), 20.0 );
2636 execute( TC_attach_check_subscriber_list(), 20.0 );
2637 execute( TC_attach_detach_check_subscriber_list(), 20.0 );
Alexander Couzens0085bd72018-06-12 19:08:44 +02002638 execute( TC_attach_check_complete_resend() );
Alexander Couzensd81876a2018-08-07 12:43:16 +02002639 execute( TC_hlr_location_cancel_request_update(), 20.0 );
2640 execute( TC_hlr_location_cancel_request_withdraw(), 20.0 );
2641 execute( TC_hlr_location_cancel_request_unknown_subscriber_withdraw(), 20.0 );
2642 execute( TC_hlr_location_cancel_request_unknown_subscriber_update(), 20.0 );
Harald Welte04683d02018-02-16 22:43:45 +01002643 execute( TC_rau_unknown() );
Harald Welte91636de2018-02-17 10:16:14 +01002644 execute( TC_attach_rau() );
Alexander Couzensbfda9212018-07-31 03:17:33 +02002645 execute( TC_attach_rau_a_a() );
Alexander Couzensbe837bd2018-07-31 04:20:11 +02002646 execute( TC_attach_rau_a_b() );
Alexander Couzens0c6324f2018-09-14 16:37:04 +02002647 execute( TC_attach_usim_resync() );
Harald Welte6abb9fe2018-02-17 15:24:48 +01002648 execute( TC_detach_unknown_nopoweroff() );
2649 execute( TC_detach_unknown_poweroff() );
2650 execute( TC_detach_nopoweroff() );
2651 execute( TC_detach_poweroff() );
Harald Welteeded9ad2018-02-17 20:57:34 +01002652 execute( TC_attach_pdp_act() );
Harald Welte835b15f2018-02-18 14:39:11 +01002653 execute( TC_pdp_act_unattached() );
Harald Welte37692d82018-02-18 15:21:34 +01002654 execute( TC_attach_pdp_act_user() );
Harald Welte5b5ca1b2018-02-18 21:25:03 +01002655 execute( TC_attach_pdp_act_ggsn_reject() );
Harald Welte6f203162018-02-18 22:04:55 +01002656 execute( TC_attach_pdp_act_user_deact_mo() );
Harald Welte57b9b7f2018-02-18 22:28:13 +01002657 execute( TC_attach_pdp_act_user_deact_mt() );
Pau Espin Pedrol2a3302a2019-08-15 16:01:20 +02002658 execute( TC_attach_pdp_act_deact_dup() );
Alexander Couzens187ad5d2018-05-02 19:31:10 +02002659 execute( TC_attach_second_attempt() );
Pau Espin Pedrolfcec9142019-08-28 17:33:46 +02002660 execute( TC_attach_echo_timeout() );
Pau Espin Pedrol94013452018-07-17 15:50:21 +02002661 execute( TC_attach_restart_ctr_echo() );
2662 execute( TC_attach_restart_ctr_create() );
Pau Espin Pedrol72edc8a2018-07-16 15:10:08 +02002663 execute( TC_attach_pdp_act_deact_mt_t3395_expire() );
Pau Espin Pedrole6f071f2019-05-29 13:02:42 +02002664 execute( TC_attach_pdp_act_deact_gtp_retrans() );
2665 execute( TC_attach_pdp_act_deact_gtp_retrans_resp() );
Pau Espin Pedrol482dde62018-07-18 13:47:42 +02002666 execute( TC_attach_pdp_act_user_error_ind_ggsn() );
Alexander Couzens6bee0872019-05-11 01:48:50 +02002667 execute( TC_attach_pdp_act_gmm_detach() );
Alexander Couzenscf3c93d2018-08-07 19:48:27 +02002668 execute( TC_attach_gmm_attach_req_while_gmm_attach() );
Harald Weltea05b8072019-04-23 22:35:05 +02002669
Harald Welte2aaac1b2019-05-02 10:02:53 +02002670 execute( TC_xid_empty_l3() );
2671 execute( TC_xid_n201u() );
2672
Harald Weltea05b8072019-04-23 22:35:05 +02002673 execute( TC_llc_null() );
Harald Welte645a1512019-04-23 23:18:23 +02002674 execute( TC_llc_sabm_dm_llgmm() );
2675 execute( TC_llc_sabm_dm_ll5() );
Harald Welte5ac31492018-02-15 20:39:13 +01002676}
Harald Welte96a33b02018-02-04 10:36:22 +01002677
2678
2679
2680}