blob: 577daa95efa6fe57059941ab3e658ce96ba307a8 [file] [log] [blame]
Jacob Erlbeck51a869c2013-10-15 12:00:26 +02001/* test routines for gbproxy
2 * send NS messages to the gbproxy and dumps what happens
3 * (C) 2013 by sysmocom s.f.m.c. GmbH
4 * Author: Jacob Erlbeck <jerlbeck@sysmocom.de>
5 */
6
7#undef _GNU_SOURCE
8#define _GNU_SOURCE
9
10#include <stdio.h>
11#include <stdlib.h>
12#include <stdint.h>
13#include <string.h>
14#include <getopt.h>
15#include <dlfcn.h>
Holger Hans Peter Freytherb9004592014-08-04 11:26:54 +020016#include <time.h>
Jacob Erlbeck51a869c2013-10-15 12:00:26 +020017#include <sys/types.h>
18#include <sys/socket.h>
19
20#include <osmocom/core/msgb.h>
21#include <osmocom/core/application.h>
22#include <osmocom/core/utils.h>
23#include <osmocom/core/logging.h>
24#include <osmocom/core/talloc.h>
25#include <osmocom/core/signal.h>
26#include <osmocom/core/rate_ctr.h>
Jacob Erlbeckb1381062014-07-01 12:41:13 +020027#include <osmocom/gsm/tlv.h>
Jacob Erlbeck59748e62014-08-11 17:26:21 +020028#include <osmocom/gsm/gsm_utils.h>
Harald Welte53373bc2016-04-20 17:11:43 +020029#include <osmocom/gsm/protocol/gsm_04_08_gprs.h>
Jacob Erlbeck51a869c2013-10-15 12:00:26 +020030#include <osmocom/gprs/gprs_msgb.h>
31#include <osmocom/gprs/gprs_ns.h>
32#include <osmocom/gprs/gprs_bssgp.h>
33
34#include <openbsc/gb_proxy.h>
Holger Hans Peter Freyther7127b022014-08-04 11:52:52 +020035#include <openbsc/gprs_utils.h>
Jacob Erlbeckc53f2a62014-08-15 14:56:28 +020036#include <openbsc/gprs_llc.h>
Jacob Erlbeckacfaff32014-09-22 18:54:34 +020037#include <openbsc/gprs_gb_parse.h>
Jacob Erlbeck7fb42db2014-07-07 10:46:01 +020038#include <openbsc/debug.h>
Jacob Erlbeck51a869c2013-10-15 12:00:26 +020039
Daniel Willmann537d4802015-10-12 19:36:35 +020040#include <openssl/rand.h>
41
Jacob Erlbeck51a869c2013-10-15 12:00:26 +020042#define REMOTE_BSS_ADDR 0x01020304
43#define REMOTE_SGSN_ADDR 0x05060708
44
Jacob Erlbeck2082afa2013-10-18 13:04:47 +020045#define SGSN_NSEI 0x0100
Jacob Erlbeck51a869c2013-10-15 12:00:26 +020046
Jacob Erlbeckf181f9e2014-08-27 12:44:25 +020047#define REMOTE_SGSN2_ADDR 0x15161718
48#define SGSN2_NSEI 0x0102
49
Jacob Erlbeckacfaff32014-09-22 18:54:34 +020050#define MATCH_ANY (-1)
51
Jacob Erlbeck7fb42db2014-07-07 10:46:01 +020052struct gbproxy_config gbcfg = {0};
53
Jacob Erlbeckacfaff32014-09-22 18:54:34 +020054struct llist_head *received_messages = NULL;
55
Daniel Willmann537d4802015-10-12 19:36:35 +020056/* override, requires '-Wl,--wrap=RAND_bytes' */
57int __real_RAND_bytes(unsigned char *buf, int num);
58int mock_RAND_bytes(unsigned char *buf, int num);
59int (*RAND_bytes_cb)(unsigned char *, int) =
60 &mock_RAND_bytes;
61
62int __wrap_RAND_bytes(unsigned char *buf, int num)
63{
64 return (*RAND_bytes_cb)(buf, num);
65}
66
67static int rand_seq_num = 0;
68int mock_RAND_bytes(unsigned char *buf, int num)
69{
70 uint32_t val;
71
72 OSMO_ASSERT(num == sizeof(val));
73 OSMO_ASSERT(__real_RAND_bytes(buf, num) == 1);
74
75 val = 0x00dead00 + rand_seq_num;
76
77 rand_seq_num++;
78
79 memcpy(buf, &val, num);
80
81 return 1;
82}
83
Daniel Willmannd1554ec2015-10-12 19:36:34 +020084static void cleanup_test()
85{
Daniel Willmann537d4802015-10-12 19:36:35 +020086 rand_seq_num = 0;
Daniel Willmannd1554ec2015-10-12 19:36:34 +020087}
88
Holger Hans Peter Freytherb9004592014-08-04 11:26:54 +020089static int dump_global(FILE *stream, int indent)
90{
91 unsigned int i;
92 const struct rate_ctr_group_desc *desc;
93 int rc;
94
95 rc = fprintf(stream, "%*sGbproxy global:\n", indent, "");
96 if (rc < 0)
97 return rc;
98
99 desc = gbcfg.ctrg->desc;
100
101 for (i = 0; i < desc->num_ctr; i++) {
102 struct rate_ctr *ctr = &gbcfg.ctrg->ctr[i];
103 if (ctr->current) {
104 rc = fprintf(stream, "%*s %s: %llu\n",
105 indent, "",
106 desc->ctr_desc[i].description,
107 (long long)ctr->current);
108
109 if (rc < 0)
110 return rc;
111 }
112 }
113
114 return 0;
115}
116
Jacob Erlbeck7b821d02014-08-08 08:37:37 +0200117static int dump_peers(FILE *stream, int indent, time_t now,
118 struct gbproxy_config *cfg)
Holger Hans Peter Freytherb9004592014-08-04 11:26:54 +0200119{
Holger Hans Peter Freyther1ddd9e52014-08-04 11:35:32 +0200120 struct gbproxy_peer *peer;
Holger Hans Peter Freytherb9004592014-08-04 11:26:54 +0200121 struct gprs_ra_id raid;
122 unsigned int i;
123 const struct rate_ctr_group_desc *desc;
124 int rc;
Holger Hans Peter Freytherb9004592014-08-04 11:26:54 +0200125
126 rc = fprintf(stream, "%*sPeers:\n", indent, "");
127 if (rc < 0)
128 return rc;
129
Holger Hans Peter Freyther0196c992014-08-04 17:10:08 +0200130 llist_for_each_entry(peer, &cfg->bts_peers, list) {
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +0200131 struct gbproxy_link_info *link_info;
Holger Hans Peter Freyther1ddd9e52014-08-04 11:35:32 +0200132 struct gbproxy_patch_state *state = &peer->patch_state;
Holger Hans Peter Freytherb9004592014-08-04 11:26:54 +0200133 gsm48_parse_ra(&raid, peer->ra);
134
135 rc = fprintf(stream, "%*s NSEI %u, BVCI %u, %sblocked, "
136 "RAI %u-%u-%u-%u\n",
137 indent, "",
138 peer->nsei, peer->bvci,
139 peer->blocked ? "" : "not ",
140 raid.mcc, raid.mnc, raid.lac, raid.rac);
141
142 if (rc < 0)
143 return rc;
144
145 desc = peer->ctrg->desc;
146
147 for (i = 0; i < desc->num_ctr; i++) {
148 struct rate_ctr *ctr = &peer->ctrg->ctr[i];
149 if (ctr->current) {
150 rc = fprintf(stream, "%*s %s: %llu\n",
151 indent, "",
152 desc->ctr_desc[i].description,
153 (long long)ctr->current);
154
155 if (rc < 0)
156 return rc;
157 }
158 }
159
160 fprintf(stream, "%*s TLLI-Cache: %d\n",
Jacob Erlbeckf8562e32014-09-19 16:03:07 +0200161 indent, "", state->logical_link_count);
162 llist_for_each_entry(link_info, &state->logical_links, list) {
Holger Hans Peter Freytherb9004592014-08-04 11:26:54 +0200163 char mi_buf[200];
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +0200164 time_t age = now ? now - link_info->timestamp : 0;
Jacob Erlbeckea1698e2014-09-02 14:40:11 +0200165 int stored_msgs = 0;
166 struct llist_head *iter;
Jacob Erlbeck9a83d7a2014-09-25 11:17:31 +0200167 enum gbproxy_match_id match_id;
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +0200168 llist_for_each(iter, &link_info->stored_msgs)
Jacob Erlbeckea1698e2014-09-02 14:40:11 +0200169 stored_msgs++;
170
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +0200171 if (link_info->imsi_len > 0) {
Jacob Erlbeck89d3d342014-08-06 18:55:15 +0200172 snprintf(mi_buf, sizeof(mi_buf), "(invalid)");
173 gsm48_mi_to_string(mi_buf, sizeof(mi_buf),
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +0200174 link_info->imsi,
175 link_info->imsi_len);
Jacob Erlbeck89d3d342014-08-06 18:55:15 +0200176 } else {
177 snprintf(mi_buf, sizeof(mi_buf), "(none)");
178 }
Jacob Erlbeck59748e62014-08-11 17:26:21 +0200179 fprintf(stream, "%*s TLLI %08x",
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +0200180 indent, "", link_info->tlli.current);
181 if (link_info->tlli.assigned)
182 fprintf(stream, "/%08x", link_info->tlli.assigned);
183 if (link_info->sgsn_tlli.current) {
Jacob Erlbeck9057bc32014-08-12 16:30:30 +0200184 fprintf(stream, " -> %08x",
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +0200185 link_info->sgsn_tlli.current);
186 if (link_info->sgsn_tlli.assigned)
Jacob Erlbeck9057bc32014-08-12 16:30:30 +0200187 fprintf(stream, "/%08x",
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +0200188 link_info->sgsn_tlli.assigned);
Jacob Erlbeck9057bc32014-08-12 16:30:30 +0200189 }
Jacob Erlbeck5f4ef322014-08-22 17:10:01 +0200190 fprintf(stream, ", IMSI %s, AGE %d",
191 mi_buf, (int)age);
192
Jacob Erlbeckea1698e2014-09-02 14:40:11 +0200193 if (stored_msgs)
194 fprintf(stream, ", STORED %d", stored_msgs);
195
Jacob Erlbeck9a83d7a2014-09-25 11:17:31 +0200196 for (match_id = 0; match_id < ARRAY_SIZE(cfg->matches);
197 ++match_id) {
198 if (cfg->matches[match_id].enable &&
199 link_info->is_matching[match_id]) {
200 fprintf(stream, ", IMSI matches");
201 break;
202 }
203 }
Jacob Erlbeckf181f9e2014-08-27 12:44:25 +0200204
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +0200205 if (link_info->imsi_acq_pending)
Jacob Erlbeck5f4ef322014-08-22 17:10:01 +0200206 fprintf(stream, ", IMSI acquisition in progress");
207
Jacob Erlbeck91a0e862014-09-17 10:56:38 +0200208 if (cfg->route_to_sgsn2)
209 fprintf(stream, ", SGSN NSEI %d",
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +0200210 link_info->sgsn_nsei);
Jacob Erlbeck91a0e862014-09-17 10:56:38 +0200211
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +0200212 if (link_info->is_deregistered)
Jacob Erlbeck7430da62014-09-12 15:09:56 +0200213 fprintf(stream, ", DE-REGISTERED");
214
Jacob Erlbeck5f4ef322014-08-22 17:10:01 +0200215 rc = fprintf(stream, "\n");
Holger Hans Peter Freytherb9004592014-08-04 11:26:54 +0200216 if (rc < 0)
217 return rc;
218 }
219 }
220
221 return 0;
222}
223
Jacob Erlbeck7fb26c22014-09-04 11:08:50 +0200224const uint8_t *convert_ra(struct gprs_ra_id *raid)
225{
226 static uint8_t buf[6];
227 gsm48_construct_ra(buf, raid);
228 return buf;
229}
230
Jacob Erlbeckc53f2a62014-08-15 14:56:28 +0200231/* DTAP - Attach Request */
232static const unsigned char dtap_attach_req[] = {
233 0x08, 0x01, 0x02, 0xf5, 0xe0, 0x21, 0x08, 0x02,
234 0x05, 0xf4, 0xfb, 0xc5, 0x46, 0x79, 0x11, 0x22,
235 0x33, 0x40, 0x50, 0x60, 0x19, 0x18, 0xb3, 0x43,
236 0x2b, 0x25, 0x96, 0x62, 0x00, 0x60, 0x80, 0x9a,
237 0xc2, 0xc6, 0x62, 0x00, 0x60, 0x80, 0xba, 0xc8,
238 0xc6, 0x62, 0x00, 0x60, 0x80, 0x00,
Jacob Erlbeck7fb42db2014-07-07 10:46:01 +0200239};
240
Jacob Erlbeck991606b2014-09-12 10:33:38 +0200241/* DTAP - Attach Request (invalid RAI) */
242static const unsigned char dtap_attach_req2[] = {
243 0x08, 0x01, 0x02, 0xf5, 0xe0, 0x21, 0x08, 0x02,
244 0x05, 0xf4, 0xfb, 0x00, 0xbe, 0xef, 0x99, 0x99,
245 0x99, 0x40, 0x50, 0x60, 0x19, 0x18, 0xb3, 0x43,
246 0x2b, 0x25, 0x96, 0x62, 0x00, 0x60, 0x80, 0x9a,
247 0xc2, 0xc6, 0x62, 0x00, 0x60, 0x80, 0xba, 0xc8,
248 0xc6, 0x62, 0x00, 0x60, 0x80, 0x00,
249};
250
Jacob Erlbeck772a22b2014-09-15 14:18:09 +0200251/* DTAP - Attach Request (P-TMSI 0x3f32b700) */
252static const unsigned char dtap_attach_req3[] = {
253 0x08, 0x01, 0x02, 0xf5, 0xe0, 0x21, 0x08, 0x02,
254 0x05, 0xf4, 0xef, 0xe2, 0xb7, 0x00, 0x11, 0x22,
255 0x33, 0x40, 0x50, 0x60, 0x19, 0x18, 0xb3, 0x43,
256 0x2b, 0x25, 0x96, 0x62, 0x00, 0x60, 0x80, 0x9a,
257 0xc2, 0xc6, 0x62, 0x00, 0x60, 0x80, 0xba, 0xc8,
258 0xc6, 0x62, 0x00, 0x60, 0x80, 0x00,
259};
260
Jacob Erlbeck9d0fb1e2014-10-31 10:43:44 +0100261/* DTAP - Attach Request (IMSI 12131415161718) */
262static const unsigned char dtap_attach_req4[] = {
263 0x08, 0x01, 0x02, 0xf5, 0xe0, 0x21, 0x08, 0x02,
264 0x08, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17,
265 0x18, 0x11, 0x22, 0x33, 0x40, 0x50, 0x60, 0x19,
266 0x18, 0xb3, 0x43, 0x2b, 0x25, 0x96, 0x62, 0x00,
267 0x60, 0x80, 0x9a, 0xc2, 0xc6, 0x62, 0x00, 0x60,
268 0x80, 0xba, 0xc8, 0xc6, 0x62, 0x00, 0x60, 0x80,
269 0x00,
270};
271
Jacob Erlbeckc53f2a62014-08-15 14:56:28 +0200272/* DTAP - Identity Request */
273static const unsigned char dtap_identity_req[] = {
274 0x08, 0x15, 0x01
Jacob Erlbeck690768a2014-08-06 15:16:45 +0200275};
276
Jacob Erlbeckc53f2a62014-08-15 14:56:28 +0200277/* DTAP - Identity Response */
278static const unsigned char dtap_identity_resp[] = {
279 0x08, 0x16, 0x08, 0x11, 0x12, 0x13, 0x14, 0x15,
280 0x16, 0x17, 0x18
Jacob Erlbeck690768a2014-08-06 15:16:45 +0200281};
282
Jacob Erlbeckf181f9e2014-08-27 12:44:25 +0200283/* DTAP - Identity Response, IMSI 2 */
284static const unsigned char dtap_identity2_resp[] = {
285 0x08, 0x16, 0x08, 0x11, 0x12, 0x99, 0x99, 0x99,
286 0x16, 0x17, 0x18
287};
288
Jacob Erlbeckaf952ba2014-09-17 12:09:25 +0200289/* DTAP - Identity Response, IMSI 3 */
290static const unsigned char dtap_identity3_resp[] = {
291 0x08, 0x16, 0x08, 0x11, 0x12, 0x99, 0x99, 0x99,
292 0x26, 0x27, 0x28
293};
294
Jacob Erlbeckc53f2a62014-08-15 14:56:28 +0200295/* DTAP - Attach Accept */
296static const unsigned char dtap_attach_acc[] = {
297 0x08, 0x02, 0x01, 0x49, 0x04, 0x21, 0x63, 0x54,
298 0x40, 0x50, 0x60, 0x19, 0xcd, 0xd7, 0x08, 0x17,
299 0x16, 0x18, 0x05, 0xf4, 0xef, 0xe2, 0xb7, 0x00
Jacob Erlbeck7fb42db2014-07-07 10:46:01 +0200300};
301
Jacob Erlbeck52f070a2014-09-04 13:45:56 +0200302/* DTAP - Attach Accept, P-TMSI 2 */
Jacob Erlbeckf181f9e2014-08-27 12:44:25 +0200303static const unsigned char dtap_attach_acc2[] = {
304 0x08, 0x02, 0x01, 0x49, 0x04, 0x21, 0x63, 0x54,
305 0x40, 0x50, 0x60, 0x19, 0xcd, 0xd7, 0x08, 0x17,
306 0x16, 0x18, 0x05, 0xf4, 0xe0, 0x98, 0x76, 0x54
307};
308
Jacob Erlbeckc53f2a62014-08-15 14:56:28 +0200309/* DTAP - Attach Complete */
310static const unsigned char dtap_attach_complete[] = {
311 0x08, 0x03
Jacob Erlbeck59748e62014-08-11 17:26:21 +0200312};
313
Jacob Erlbeck2bf32612014-09-22 11:26:58 +0200314/* DTAP - Attach Reject (GPRS services not allowed) */
315static const unsigned char dtap_attach_rej7[] = {
316 0x08, 0x04, 0x07
317};
318
Jacob Erlbeckc53f2a62014-08-15 14:56:28 +0200319/* DTAP - GMM Information */
320static const unsigned char dtap_gmm_information[] = {
321 0x08, 0x21
Jacob Erlbeck11669742014-06-06 18:47:36 +0200322};
323
Jacob Erlbeckc53f2a62014-08-15 14:56:28 +0200324/* DTAP - Routing Area Update Request */
325static const unsigned char dtap_ra_upd_req[] = {
326 0x08, 0x08, 0x10, 0x11, 0x22, 0x33, 0x40, 0x50,
327 0x60, 0x1d, 0x19, 0x13, 0x42, 0x33, 0x57, 0x2b,
328 0xf7, 0xc8, 0x48, 0x02, 0x13, 0x48, 0x50, 0xc8,
329 0x48, 0x02, 0x14, 0x48, 0x50, 0xc8, 0x48, 0x02,
330 0x17, 0x49, 0x10, 0xc8, 0x48, 0x02, 0x00, 0x19,
331 0x8b, 0xb2, 0x92, 0x17, 0x16, 0x27, 0x07, 0x04,
332 0x31, 0x02, 0xe5, 0xe0, 0x32, 0x02, 0x20, 0x00
Jacob Erlbeck7fb42db2014-07-07 10:46:01 +0200333};
334
Jacob Erlbeckc53f2a62014-08-15 14:56:28 +0200335/* DTAP - Routing Area Update Accept */
336static const unsigned char dtap_ra_upd_acc[] = {
337 0x08, 0x09, 0x00, 0x49, 0x21, 0x63, 0x54,
338 0x40, 0x50, 0x60, 0x19, 0x54, 0xab, 0xb3, 0x18,
339 0x05, 0xf4, 0xef, 0xe2, 0xb7, 0x00, 0x17, 0x16,
Jacob Erlbeck7fb42db2014-07-07 10:46:01 +0200340};
341
Jacob Erlbeck52f070a2014-09-04 13:45:56 +0200342/* DTAP - Routing Area Update Accept, P-TMSI 2 */
343static const unsigned char dtap_ra_upd_acc2[] = {
344 0x08, 0x09, 0x00, 0x49, 0x21, 0x63, 0x54,
345 0x40, 0x50, 0x60, 0x19, 0x54, 0xab, 0xb3, 0x18,
346 0x05, 0xf4, 0xe0, 0x98, 0x76, 0x54, 0x17, 0x16,
347};
348
349/* DTAP - Routing Area Update Accept, P-TMSI 3 */
350static const unsigned char dtap_ra_upd_acc3[] = {
351 0x08, 0x09, 0x00, 0x49, 0x21, 0x63, 0x54,
352 0x40, 0x50, 0x60, 0x19, 0x54, 0xab, 0xb3, 0x18,
353 0x05, 0xf4, 0xe0, 0x54, 0x32, 0x10, 0x17, 0x16,
354};
355
356/* DTAP - Routing Area Update Complete */
357static const unsigned char dtap_ra_upd_complete[] = {
358 0x08, 0x0a
359};
360
Jacob Erlbeck772a22b2014-09-15 14:18:09 +0200361/* DTAP - Routing Area Update Reject */
362/* cause = 10 ("Implicitly detached"), force_standby = 0 */
363static const unsigned char dtap_ra_upd_rej[] = {
364 0x08, 0x0b, 0x0a, 0x00,
365};
Jacob Erlbeck52f070a2014-09-04 13:45:56 +0200366
Jacob Erlbeckc53f2a62014-08-15 14:56:28 +0200367/* DTAP - Activate PDP Context Request */
368static const unsigned char dtap_act_pdp_ctx_req[] = {
369 0x0a, 0x41, 0x05, 0x03, 0x0c, 0x00,
Jacob Erlbeck7fb42db2014-07-07 10:46:01 +0200370 0x00, 0x1f, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00,
371 0x00, 0x00, 0x00, 0x02, 0x01, 0x21, 0x28, 0x03,
372 0x02, 0x61, 0x62, 0x27, 0x14, 0x80, 0x80, 0x21,
373 0x10, 0x01, 0x00, 0x00, 0x10, 0x81, 0x06, 0x00,
374 0x00, 0x00, 0x00, 0x83, 0x06, 0x00, 0x00, 0x00,
Jacob Erlbeckc53f2a62014-08-15 14:56:28 +0200375 0x00
Jacob Erlbeck7fb42db2014-07-07 10:46:01 +0200376};
Jacob Erlbeck51a869c2013-10-15 12:00:26 +0200377
Jacob Erlbeckc53f2a62014-08-15 14:56:28 +0200378/* DTAP - Detach Request (MO) */
Jacob Erlbeck3e23ddf2014-08-11 15:07:37 +0200379/* normal detach, power_off = 1 */
Jacob Erlbeckc53f2a62014-08-15 14:56:28 +0200380static const unsigned char dtap_detach_po_req[] = {
381 0x08, 0x05, 0x09, 0x18, 0x05, 0xf4, 0xef, 0xe2,
382 0xb7, 0x00, 0x19, 0x03, 0xb9, 0x97, 0xcb
Jacob Erlbeck3e23ddf2014-08-11 15:07:37 +0200383};
384
Jacob Erlbeckc53f2a62014-08-15 14:56:28 +0200385/* DTAP - Detach Request (MO) */
Jacob Erlbeck3e23ddf2014-08-11 15:07:37 +0200386/* normal detach, power_off = 0 */
Jacob Erlbeckc53f2a62014-08-15 14:56:28 +0200387static const unsigned char dtap_detach_req[] = {
388 0x08, 0x05, 0x01, 0x18, 0x05, 0xf4, 0xef, 0xe2,
389 0xb7, 0x00, 0x19, 0x03, 0xb9, 0x97, 0xcb
Jacob Erlbeckcf02eb12014-06-19 10:23:50 +0200390};
391
Jacob Erlbeck772a22b2014-09-15 14:18:09 +0200392/* DTAP - Detach Accept (MO) */
Jacob Erlbeckc53f2a62014-08-15 14:56:28 +0200393static const unsigned char dtap_detach_acc[] = {
394 0x08, 0x06, 0x00
Jacob Erlbeckcf02eb12014-06-19 10:23:50 +0200395};
396
Jacob Erlbeck772a22b2014-09-15 14:18:09 +0200397/* DTAP - Detach Request (MT) */
398/* normal detach, reattach required, implicitly detached */
399static const unsigned char dtap_mt_detach_rea_req[] = {
400 0x08, 0x05, 0x01, 0x25, 0x0a
401};
402
403/* DTAP - Detach Request (MT) */
404/* normal detach, reattach not required, implicitly detached */
405static const unsigned char dtap_mt_detach_req[] = {
406 0x08, 0x05, 0x02, 0x25, 0x0a
407};
408
409/* DTAP - Detach Accept (MT) */
410static const unsigned char dtap_mt_detach_acc[] = {
411 0x08, 0x06
412};
413
Jacob Erlbeck6bd7ded2014-08-15 17:20:06 +0200414/* GPRS-LLC - SAPI: LLGMM, U, XID */
415static const unsigned char llc_u_xid_ul[] = {
416 0x41, 0xfb, 0x01, 0x00, 0x0e, 0x00, 0x64, 0x11,
417 0x05, 0x16, 0x01, 0x90, 0x66, 0xb3, 0x28
418};
419
420/* GPRS-LLC - SAPI: LLGMM, U, XID */
421static const unsigned char llc_u_xid_dl[] = {
422 0x41, 0xfb, 0x30, 0x84, 0x10, 0x61, 0xb6, 0x64,
423 0xe4, 0xa9, 0x1a, 0x9e
424};
425
426/* GPRS-LLC - SAPI: LL11, UI, NSAPI 5, DNS query */
427static const unsigned char llc_ui_ll11_dns_query_ul[] = {
428 0x0b, 0xc0, 0x01, 0x65, 0x00, 0x00, 0x00, 0x45,
429 0x00, 0x00, 0x38, 0x95, 0x72, 0x00, 0x00, 0x45,
430 0x11, 0x20, 0x85, 0x0a, 0xc0, 0x07, 0xe4, 0xac,
431 0x10, 0x01, 0x0a, 0xad, 0xab, 0x00, 0x35, 0x00,
432 0x24, 0x0e, 0x1c, 0x3b, 0xe0, 0x01, 0x00, 0x00,
433 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01,
434 0x6d, 0x05, 0x68, 0x65, 0x69, 0x73, 0x65, 0x02,
435 0x64, 0x65, 0x00, 0x00, 0x01, 0x00, 0x01, 0x47,
436 0x8f, 0x07
437};
438
439/* GPRS-LLC - SAPI: LL11, UI, NSAPI 5, DNS query */
440static const unsigned char llc_ui_ll11_dns_resp_dl[] = {
441 0x4b, 0xc0, 0x01, 0x65, 0x00, 0x00, 0x00, 0x45,
442 0x00, 0x00, 0xc6, 0x00, 0x00, 0x40, 0x00, 0x3e,
443 0x11, 0x7c, 0x69, 0xac, 0x10, 0x01, 0x0a, 0x0a,
444 0xc0, 0x07, 0xe4, 0x00, 0x35, 0xad, 0xab, 0x00,
445 0xb2, 0x74, 0x4e, 0x3b, 0xe0, 0x81, 0x80, 0x00,
446 0x01, 0x00, 0x01, 0x00, 0x05, 0x00, 0x00, 0x01,
447 0x6d, 0x05, 0x68, 0x65, 0x69, 0x73, 0x65, 0x02,
448 0x64, 0x65, 0x00, 0x00, 0x01, 0x00, 0x01, 0xc0,
449 0x0c, 0x00, 0x01, 0x00, 0x01, 0x00, 0x00, 0x0e,
450 0x10, 0x00, 0x04, 0xc1, 0x63, 0x90, 0x58, 0xc0,
451 0x0e, 0x00, 0x02, 0x00, 0x01, 0x00, 0x00, 0x0e,
452 0x10, 0x00, 0x16, 0x03, 0x6e, 0x73, 0x32, 0x0c,
453 0x70, 0x6f, 0x70, 0x2d, 0x68, 0x61, 0x6e, 0x6e,
454 0x6f, 0x76, 0x65, 0x72, 0x03, 0x6e, 0x65, 0x74,
455 0x00, 0xc0, 0x0e, 0x00, 0x02, 0x00, 0x01, 0x00,
456 0x00, 0x0e, 0x10, 0x00, 0x10, 0x02, 0x6e, 0x73,
457 0x01, 0x73, 0x08, 0x70, 0x6c, 0x75, 0x73, 0x6c,
458 0x69, 0x6e, 0x65, 0xc0, 0x14, 0xc0, 0x0e, 0x00,
459 0x02, 0x00, 0x01, 0x00, 0x00, 0x0e, 0x10, 0x00,
460 0x05, 0x02, 0x6e, 0x73, 0xc0, 0x0e, 0xc0, 0x0e,
461 0x00, 0x02, 0x00, 0x01, 0x00, 0x00, 0x0e, 0x10,
462 0x00, 0x05, 0x02, 0x6e, 0x73, 0xc0, 0x5f, 0xc0,
463 0x0e, 0x00, 0x02, 0x00, 0x01, 0x00, 0x00, 0x0e,
464 0x10, 0x00, 0x12, 0x02, 0x6e, 0x73, 0x0c, 0x70,
465 0x6f, 0x70, 0x2d, 0x68, 0x61, 0x6e, 0x6e, 0x6f,
466 0x76, 0x65, 0x72, 0xc0, 0x14, 0xaa, 0xdf, 0x31
467};
468
Jacob Erlbeck2082afa2013-10-18 13:04:47 +0200469static int gprs_process_message(struct gprs_ns_inst *nsi, const char *text,
470 struct sockaddr_in *peer, const unsigned char* data,
471 size_t data_len);
Jacob Erlbeck51a869c2013-10-15 12:00:26 +0200472
473static void send_ns_reset(struct gprs_ns_inst *nsi, struct sockaddr_in *src_addr,
474 enum ns_cause cause, uint16_t nsvci, uint16_t nsei)
475{
476 /* GPRS Network Service, PDU type: NS_RESET,
477 */
478 unsigned char msg[12] = {
479 0x02, 0x00, 0x81, 0x01, 0x01, 0x82, 0x11, 0x22,
480 0x04, 0x82, 0x11, 0x22
481 };
482
483 msg[3] = cause;
484 msg[6] = nsvci / 256;
485 msg[7] = nsvci % 256;
486 msg[10] = nsei / 256;
487 msg[11] = nsei % 256;
488
489 gprs_process_message(nsi, "RESET", src_addr, msg, sizeof(msg));
490}
491
Jacob Erlbeck2082afa2013-10-18 13:04:47 +0200492static void send_ns_reset_ack(struct gprs_ns_inst *nsi, struct sockaddr_in *src_addr,
493 uint16_t nsvci, uint16_t nsei)
494{
495 /* GPRS Network Service, PDU type: NS_RESET_ACK,
496 */
497 unsigned char msg[9] = {
498 0x03, 0x01, 0x82, 0x11, 0x22,
499 0x04, 0x82, 0x11, 0x22
500 };
501
502 msg[3] = nsvci / 256;
503 msg[4] = nsvci % 256;
504 msg[7] = nsei / 256;
505 msg[8] = nsei % 256;
506
507 gprs_process_message(nsi, "RESET_ACK", src_addr, msg, sizeof(msg));
508}
509
Jacob Erlbeck51a869c2013-10-15 12:00:26 +0200510static void send_ns_alive(struct gprs_ns_inst *nsi, struct sockaddr_in *src_addr)
511{
512 /* GPRS Network Service, PDU type: NS_ALIVE */
513 unsigned char msg[1] = {
514 0x0a
515 };
516
517 gprs_process_message(nsi, "ALIVE", src_addr, msg, sizeof(msg));
518}
519
520static void send_ns_alive_ack(struct gprs_ns_inst *nsi, struct sockaddr_in *src_addr)
521{
522 /* GPRS Network Service, PDU type: NS_ALIVE_ACK */
523 unsigned char msg[1] = {
524 0x0b
525 };
526
527 gprs_process_message(nsi, "ALIVE_ACK", src_addr, msg, sizeof(msg));
528}
529
530static void send_ns_unblock(struct gprs_ns_inst *nsi, struct sockaddr_in *src_addr)
531{
532 /* GPRS Network Service, PDU type: NS_UNBLOCK */
533 unsigned char msg[1] = {
534 0x06
535 };
536
537 gprs_process_message(nsi, "UNBLOCK", src_addr, msg, sizeof(msg));
538}
539
Jacob Erlbeck2082afa2013-10-18 13:04:47 +0200540static void send_ns_unblock_ack(struct gprs_ns_inst *nsi, struct sockaddr_in *src_addr)
541{
542 /* GPRS Network Service, PDU type: NS_UNBLOCK_ACK */
543 unsigned char msg[1] = {
544 0x07
545 };
546
547 gprs_process_message(nsi, "UNBLOCK_ACK", src_addr, msg, sizeof(msg));
548}
549
550static void send_ns_unitdata(struct gprs_ns_inst *nsi, const char *text,
551 struct sockaddr_in *src_addr, uint16_t nsbvci,
Jacob Erlbeck51a869c2013-10-15 12:00:26 +0200552 const unsigned char *bssgp_msg, size_t bssgp_msg_size)
553{
554 /* GPRS Network Service, PDU type: NS_UNITDATA */
555 unsigned char msg[4096] = {
556 0x00, 0x00, 0x00, 0x00
557 };
558
559 OSMO_ASSERT(bssgp_msg_size <= sizeof(msg) - 4);
560
561 msg[2] = nsbvci / 256;
562 msg[3] = nsbvci % 256;
563 memcpy(msg + 4, bssgp_msg, bssgp_msg_size);
564
Jacob Erlbeck2082afa2013-10-18 13:04:47 +0200565 gprs_process_message(nsi, text ? text : "UNITDATA", src_addr, msg, bssgp_msg_size + 4);
Jacob Erlbeck51a869c2013-10-15 12:00:26 +0200566}
567
Jacob Erlbeckc53f2a62014-08-15 14:56:28 +0200568static void send_bssgp_ul_unitdata(
569 struct gprs_ns_inst *nsi, const char *text,
570 struct sockaddr_in *src_addr, uint16_t nsbvci, uint32_t tlli,
571 struct gprs_ra_id *raid, uint16_t cell_id,
572 const uint8_t *llc_msg, size_t llc_msg_size)
573{
574 /* GPRS Network Service, PDU type: NS_UNITDATA */
575 /* Base Station Subsystem GPRS Protocol: UL_UNITDATA */
576 unsigned char msg[4096] = {
577 0x01, /* TLLI */ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x04,
578 0x08, 0x88, /* RAI */ 0x11, 0x22, 0x33, 0x40, 0x50, 0x60,
579 /* CELL ID */ 0x00, 0x00, 0x00, 0x80, 0x0e, /* LLC LEN */ 0x00, 0x00,
580 };
581
582 size_t bssgp_msg_size = 23 + llc_msg_size;
583
584 OSMO_ASSERT(bssgp_msg_size <= sizeof(msg));
585
586 gsm48_construct_ra(msg + 10, raid);
587 msg[1] = (uint8_t)(tlli >> 24);
588 msg[2] = (uint8_t)(tlli >> 16);
589 msg[3] = (uint8_t)(tlli >> 8);
590 msg[4] = (uint8_t)(tlli >> 0);
591 msg[16] = cell_id / 256;
592 msg[17] = cell_id % 256;
593 msg[21] = llc_msg_size / 256;
594 msg[22] = llc_msg_size % 256;
595 memcpy(msg + 23, llc_msg, llc_msg_size);
596
597 send_ns_unitdata(nsi, text ? text : "BSSGP UL UNITDATA",
598 src_addr, nsbvci, msg, bssgp_msg_size);
599}
600
601static void send_bssgp_dl_unitdata(
602 struct gprs_ns_inst *nsi, const char *text,
603 struct sockaddr_in *src_addr, uint16_t nsbvci, uint32_t tlli,
604 int with_racap_drx, const uint8_t *imsi, size_t imsi_size,
605 const uint8_t *llc_msg, size_t llc_msg_size)
606{
607 /* Base Station Subsystem GPRS Protocol: DL_UNITDATA */
608 unsigned char msg[4096] = {
609 0x00, /* TLLI */ 0x00, 0x00, 0x00, 0x00, 0x00, 0x50, 0x20,
610 0x16, 0x82, 0x02, 0x58,
611 };
612 unsigned char racap_drx[] = {
613 0x13, 0x99, 0x18, 0xb3, 0x43, 0x2b, 0x25, 0x96,
614 0x62, 0x00, 0x60, 0x80, 0x9a, 0xc2, 0xc6, 0x62,
615 0x00, 0x60, 0x80, 0xba, 0xc8, 0xc6, 0x62, 0x00,
616 0x60, 0x80, 0x00, 0x0a, 0x82, 0x08, 0x02
617 };
618
619 size_t bssgp_msg_size = 0;
620
621 OSMO_ASSERT(51 + imsi_size + llc_msg_size <= sizeof(msg));
622
623 msg[1] = (uint8_t)(tlli >> 24);
624 msg[2] = (uint8_t)(tlli >> 16);
625 msg[3] = (uint8_t)(tlli >> 8);
626 msg[4] = (uint8_t)(tlli >> 0);
627
628 bssgp_msg_size = 12;
629
630 if (with_racap_drx) {
631 memcpy(msg + bssgp_msg_size, racap_drx, sizeof(racap_drx));
632 bssgp_msg_size += sizeof(racap_drx);
633 }
634
635 if (imsi) {
636 OSMO_ASSERT(imsi_size <= 127);
637 msg[bssgp_msg_size] = BSSGP_IE_IMSI;
638 msg[bssgp_msg_size + 1] = 0x80 | imsi_size;
639 memcpy(msg + bssgp_msg_size + 2, imsi, imsi_size);
640 bssgp_msg_size += 2 + imsi_size;
641 }
642
643 if ((bssgp_msg_size % 4) != 0) {
644 size_t abytes = (4 - (bssgp_msg_size + 2) % 4) % 4;
645 msg[bssgp_msg_size] = BSSGP_IE_ALIGNMENT;
646 msg[bssgp_msg_size + 1] = 0x80 | abytes;
647 memset(msg + bssgp_msg_size + 2, 0, abytes);
648 bssgp_msg_size += 2 + abytes;
649 }
650
651 msg[bssgp_msg_size] = BSSGP_IE_LLC_PDU;
652 if (llc_msg_size < 128) {
653 msg[bssgp_msg_size + 1] = 0x80 | llc_msg_size;
654 bssgp_msg_size += 2;
655 } else {
656 msg[bssgp_msg_size + 1] = llc_msg_size / 256;
657 msg[bssgp_msg_size + 2] = llc_msg_size % 256;
658 bssgp_msg_size += 3;
659 }
660 memcpy(msg + bssgp_msg_size, llc_msg, llc_msg_size);
661 bssgp_msg_size += llc_msg_size;
662
663
664 send_ns_unitdata(nsi, text ? text : "BSSGP DL UNITDATA",
665 src_addr, nsbvci, msg, bssgp_msg_size);
666}
667
Jacob Erlbeck51a869c2013-10-15 12:00:26 +0200668static void send_bssgp_reset(struct gprs_ns_inst *nsi, struct sockaddr_in *src_addr,
669 uint16_t bvci)
670{
671 /* GPRS Network Service, PDU type: NS_UNITDATA, BVCI 0
672 * BSSGP RESET */
Jacob Erlbeckda4b4922014-08-06 12:38:10 +0200673 unsigned char msg[18] = {
Jacob Erlbeck51a869c2013-10-15 12:00:26 +0200674 0x22, 0x04, 0x82, 0x4a,
Jacob Erlbeckdef03912014-06-02 10:48:59 +0200675 0x2e, 0x07, 0x81, 0x08, 0x08, 0x88, 0x11, 0x22,
676 0x33, 0x40, 0x50, 0x60, 0x10, 0x00
Jacob Erlbeck51a869c2013-10-15 12:00:26 +0200677 };
678
679 msg[3] = bvci / 256;
680 msg[4] = bvci % 256;
681
Jacob Erlbeck2082afa2013-10-18 13:04:47 +0200682 send_ns_unitdata(nsi, "BVC_RESET", src_addr, 0, msg, sizeof(msg));
683}
684
685static void send_bssgp_reset_ack(struct gprs_ns_inst *nsi,
686 struct sockaddr_in *src_addr, uint16_t bvci)
687{
688 /* GPRS Network Service, PDU type: NS_UNITDATA, BVCI 0
689 * BSSGP RESET_ACK */
690 static unsigned char msg[5] = {
691 0x23, 0x04, 0x82, 0x00,
692 0x00
693 };
694
695 msg[3] = bvci / 256;
696 msg[4] = bvci % 256;
697
698 send_ns_unitdata(nsi, "BVC_RESET_ACK", src_addr, 0, msg, sizeof(msg));
Jacob Erlbeck51a869c2013-10-15 12:00:26 +0200699}
700
Jacob Erlbeck7fb42db2014-07-07 10:46:01 +0200701static void send_bssgp_suspend(struct gprs_ns_inst *nsi,
702 struct sockaddr_in *src_addr,
Jacob Erlbeck299389a2014-08-21 16:34:18 +0200703 uint32_t tlli,
Jacob Erlbeck7fb42db2014-07-07 10:46:01 +0200704 struct gprs_ra_id *raid)
705{
706 /* Base Station Subsystem GPRS Protocol, BSSGP SUSPEND */
707 unsigned char msg[15] = {
Jacob Erlbeck299389a2014-08-21 16:34:18 +0200708 0x0b, 0x1f, 0x84, /* TLLI */ 0xff, 0xff, 0xff, 0xff, 0x1b,
709 0x86, /* RAI */ 0xff, 0xff, 0xff, 0xff, 0xff, 0xff
Jacob Erlbeck7fb42db2014-07-07 10:46:01 +0200710 };
711
Jacob Erlbeck299389a2014-08-21 16:34:18 +0200712 msg[3] = (uint8_t)(tlli >> 24);
713 msg[4] = (uint8_t)(tlli >> 16);
714 msg[5] = (uint8_t)(tlli >> 8);
715 msg[6] = (uint8_t)(tlli >> 0);
716
Jacob Erlbeck7fb42db2014-07-07 10:46:01 +0200717 gsm48_construct_ra(msg + 9, raid);
718
719 send_ns_unitdata(nsi, "BVC_SUSPEND", src_addr, 0, msg, sizeof(msg));
720}
721
722static void send_bssgp_suspend_ack(struct gprs_ns_inst *nsi,
723 struct sockaddr_in *src_addr,
Jacob Erlbeck299389a2014-08-21 16:34:18 +0200724 uint32_t tlli,
Jacob Erlbeck7fb42db2014-07-07 10:46:01 +0200725 struct gprs_ra_id *raid)
726{
727 /* Base Station Subsystem GPRS Protocol, BSSGP SUSPEND ACK */
728 unsigned char msg[18] = {
Jacob Erlbeck299389a2014-08-21 16:34:18 +0200729 0x0c, 0x1f, 0x84, /* TLLI */ 0xff, 0xff, 0xff, 0xff, 0x1b,
730 0x86, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0x1d,
Jacob Erlbeck7fb42db2014-07-07 10:46:01 +0200731 0x81, 0x01
732 };
733
Jacob Erlbeck299389a2014-08-21 16:34:18 +0200734 msg[3] = (uint8_t)(tlli >> 24);
735 msg[4] = (uint8_t)(tlli >> 16);
736 msg[5] = (uint8_t)(tlli >> 8);
737 msg[6] = (uint8_t)(tlli >> 0);
738
Jacob Erlbeck7fb42db2014-07-07 10:46:01 +0200739 gsm48_construct_ra(msg + 9, raid);
740
741 send_ns_unitdata(nsi, "BVC_SUSPEND_ACK", src_addr, 0, msg, sizeof(msg));
742}
743
Jacob Erlbeck299389a2014-08-21 16:34:18 +0200744static void send_bssgp_llc_discarded(struct gprs_ns_inst *nsi,
745 struct sockaddr_in *src_addr,
746 uint16_t bvci, uint32_t tlli,
747 unsigned n_frames, unsigned n_octets)
748{
749 /* Base Station Subsystem GPRS Protocol: LLC-DISCARDED (0x2c) */
750 unsigned char msg[] = {
751 0x2c, 0x1f, 0x84, /* TLLI */ 0xff, 0xff, 0xff, 0xff, 0x0f,
752 0x81, /* n frames */ 0xff, 0x04, 0x82, /* BVCI */ 0xff, 0xff, 0x25, 0x83,
753 /* n octets */ 0xff, 0xff, 0xff
754 };
755
756 msg[3] = (uint8_t)(tlli >> 24);
757 msg[4] = (uint8_t)(tlli >> 16);
758 msg[5] = (uint8_t)(tlli >> 8);
759 msg[6] = (uint8_t)(tlli >> 0);
760 msg[9] = (uint8_t)(n_frames);
761 msg[12] = (uint8_t)(bvci >> 8);
762 msg[13] = (uint8_t)(bvci >> 0);
763 msg[16] = (uint8_t)(n_octets >> 16);
764 msg[17] = (uint8_t)(n_octets >> 8);
765 msg[18] = (uint8_t)(n_octets >> 0);
766
767 send_ns_unitdata(nsi, "LLC_DISCARDED", src_addr, 0, msg, sizeof(msg));
768}
769
Jacob Erlbeckc37ef6c2014-09-30 13:49:43 +0200770static void send_bssgp_paging(struct gprs_ns_inst *nsi,
771 struct sockaddr_in *src_addr,
772 const uint8_t *imsi, size_t imsi_size,
773 struct gprs_ra_id *raid, uint32_t ptmsi)
774{
775 /* Base Station Subsystem GPRS Protocol, BSSGP SUSPEND */
776 unsigned char msg[100] = {
777 0x06,
778 };
779
780 const unsigned char drx_ie[] = {0x0a, 0x82, 0x07, 0x04};
781 const unsigned char qos_ie[] = {0x18, 0x83, 0x00, 0x00, 0x00};
782
783 size_t bssgp_msg_size = 1;
784
785 if (imsi) {
786 OSMO_ASSERT(imsi_size <= 127);
787 msg[bssgp_msg_size] = BSSGP_IE_IMSI;
788 msg[bssgp_msg_size + 1] = 0x80 | imsi_size;
789 memcpy(msg + bssgp_msg_size + 2, imsi, imsi_size);
790 bssgp_msg_size += 2 + imsi_size;
791 }
792
793 memcpy(msg + bssgp_msg_size, drx_ie, sizeof(drx_ie));
794 bssgp_msg_size += sizeof(drx_ie);
795
796 if (raid) {
797 msg[bssgp_msg_size] = BSSGP_IE_ROUTEING_AREA;
798 msg[bssgp_msg_size+1] = 0x86;
799 gsm48_construct_ra(msg + bssgp_msg_size + 2, raid);
800 bssgp_msg_size += 8;
801 }
802
803 memcpy(msg + bssgp_msg_size, qos_ie, sizeof(qos_ie));
804 bssgp_msg_size += sizeof(qos_ie);
805
806 if (ptmsi != GSM_RESERVED_TMSI) {
807 const uint32_t ptmsi_be = htonl(ptmsi);
808 msg[bssgp_msg_size] = BSSGP_IE_TMSI;
809 msg[bssgp_msg_size+1] = 0x84;
810 memcpy(msg + bssgp_msg_size + 2, &ptmsi_be, 4);
811 bssgp_msg_size += 6;
812 }
813
814 send_ns_unitdata(nsi, "PAGING_PS", src_addr, 0, msg, bssgp_msg_size);
815}
816
Jacob Erlbeckf181f9e2014-08-27 12:44:25 +0200817static void send_bssgp_flow_control_bvc(struct gprs_ns_inst *nsi,
818 struct sockaddr_in *src_addr,
819 uint16_t bvci, uint8_t tag)
820{
821 /* GPRS Network Service, PDU type: NS_UNITDATA,
822 * BSSGP FLOW_CONTROL_BVC */
823 unsigned char msg[] = {
824 0x26, 0x1e, 0x81, /* Tag */ 0xff, 0x05, 0x82, 0x01, 0xdc,
825 0x03, 0x82, 0x02, 0x76, 0x01, 0x82, 0x00, 0x50,
826 0x1c, 0x82, 0x02, 0x58, 0x06, 0x82, 0x00, 0x03
827 };
828
829 msg[3] = tag;
830
831 send_ns_unitdata(nsi, "FLOW_CONTROL_BVC", src_addr, bvci,
832 msg, sizeof(msg));
833}
834
835static void send_bssgp_flow_control_bvc_ack(struct gprs_ns_inst *nsi,
836 struct sockaddr_in *src_addr,
837 uint16_t bvci, uint8_t tag)
838{
839 /* GPRS Network Service, PDU type: NS_UNITDATA,
840 * BSSGP FLOW_CONTROL_BVC_ACK */
841 unsigned char msg[] = {
842 0x27, 0x1e, 0x81, /* Tag */ 0xce
843 };
844
845 msg[3] = tag;
846
847 send_ns_unitdata(nsi, "FLOW_CONTROL_BVC_ACK", src_addr, bvci,
848 msg, sizeof(msg));
849}
850
Jacob Erlbeckc53f2a62014-08-15 14:56:28 +0200851static void send_llc_ul_ui(
852 struct gprs_ns_inst *nsi, const char *text,
853 struct sockaddr_in *src_addr, uint16_t nsbvci, uint32_t tlli,
854 struct gprs_ra_id *raid, uint16_t cell_id,
855 unsigned sapi, unsigned nu,
856 const uint8_t *msg, size_t msg_size)
857{
858 unsigned char llc_msg[4096] = {
859 0x00, 0xc0, 0x01
860 };
861
862 size_t llc_msg_size = 3 + msg_size + 3;
863 uint8_t e_bit = 0;
864 uint8_t pm_bit = 1;
865 unsigned fcs;
866
867 nu &= 0x01ff;
868
869 OSMO_ASSERT(llc_msg_size <= sizeof(llc_msg));
870
871 llc_msg[0] = (sapi & 0x0f);
872 llc_msg[1] = 0xc0 | (nu >> 6); /* UI frame */
873 llc_msg[2] = (nu << 2) | ((e_bit & 1) << 1) | (pm_bit & 1);
874
875 memcpy(llc_msg + 3, msg, msg_size);
876
877 fcs = gprs_llc_fcs(llc_msg, msg_size + 3);
878 llc_msg[3 + msg_size + 0] = (uint8_t)(fcs >> 0);
879 llc_msg[3 + msg_size + 1] = (uint8_t)(fcs >> 8);
880 llc_msg[3 + msg_size + 2] = (uint8_t)(fcs >> 16);
881
882 send_bssgp_ul_unitdata(nsi, text ? text : "LLC UI",
883 src_addr, nsbvci, tlli, raid, cell_id,
884 llc_msg, llc_msg_size);
885}
886
887static void send_llc_dl_ui(
888 struct gprs_ns_inst *nsi, const char *text,
889 struct sockaddr_in *src_addr, uint16_t nsbvci, uint32_t tlli,
890 int with_racap_drx, const uint8_t *imsi, size_t imsi_size,
891 unsigned sapi, unsigned nu,
892 const uint8_t *msg, size_t msg_size)
893{
894 /* GPRS Network Service, PDU type: NS_UNITDATA */
895 /* Base Station Subsystem GPRS Protocol: UL_UNITDATA */
896 unsigned char llc_msg[4096] = {
897 0x00, 0x00, 0x01
898 };
899
900 size_t llc_msg_size = 3 + msg_size + 3;
901 uint8_t e_bit = 0;
902 uint8_t pm_bit = 1;
903 unsigned fcs;
904
905 nu &= 0x01ff;
906
907 OSMO_ASSERT(llc_msg_size <= sizeof(llc_msg));
908
909 llc_msg[0] = 0x40 | (sapi & 0x0f);
910 llc_msg[1] = 0xc0 | (nu >> 6); /* UI frame */
911 llc_msg[2] = (nu << 2) | ((e_bit & 1) << 1) | (pm_bit & 1);
912
913 memcpy(llc_msg + 3, msg, msg_size);
914
915 fcs = gprs_llc_fcs(llc_msg, msg_size + 3);
916 llc_msg[3 + msg_size + 0] = (uint8_t)(fcs >> 0);
917 llc_msg[3 + msg_size + 1] = (uint8_t)(fcs >> 8);
918 llc_msg[3 + msg_size + 2] = (uint8_t)(fcs >> 16);
919
920 send_bssgp_dl_unitdata(nsi, text ? text : "LLC UI",
921 src_addr, nsbvci, tlli,
922 with_racap_drx, imsi, imsi_size,
923 llc_msg, llc_msg_size);
924}
925
926
Jacob Erlbeck51a869c2013-10-15 12:00:26 +0200927static void setup_ns(struct gprs_ns_inst *nsi, struct sockaddr_in *src_addr,
928 uint16_t nsvci, uint16_t nsei)
929{
930 printf("Setup NS-VC: remote 0x%08x:%d, "
931 "NSVCI 0x%04x(%d), NSEI 0x%04x(%d)\n\n",
932 ntohl(src_addr->sin_addr.s_addr), ntohs(src_addr->sin_port),
933 nsvci, nsvci, nsei, nsei);
934
935 send_ns_reset(nsi, src_addr, NS_CAUSE_OM_INTERVENTION, nsvci, nsei);
936 send_ns_alive(nsi, src_addr);
937 send_ns_unblock(nsi, src_addr);
938 send_ns_alive_ack(nsi, src_addr);
939}
940
941static void setup_bssgp(struct gprs_ns_inst *nsi, struct sockaddr_in *src_addr,
942 uint16_t bvci)
943{
944 printf("Setup BSSGP: remote 0x%08x:%d, "
945 "BVCI 0x%04x(%d)\n\n",
946 ntohl(src_addr->sin_addr.s_addr), ntohs(src_addr->sin_port),
947 bvci, bvci);
948
949 send_bssgp_reset(nsi, src_addr, bvci);
950}
951
Jacob Erlbeckf181f9e2014-08-27 12:44:25 +0200952static void connect_sgsn(struct gprs_ns_inst *nsi, struct sockaddr_in *sgsn_peer,
953 uint32_t sgsn_nsei)
Jacob Erlbeck2e038f72014-07-07 10:46:00 +0200954{
Jacob Erlbeckf181f9e2014-08-27 12:44:25 +0200955 gprs_ns_nsip_connect(nsi, sgsn_peer, sgsn_nsei, sgsn_nsei+1);
956 send_ns_reset_ack(nsi, sgsn_peer, sgsn_nsei+1, sgsn_nsei);
Jacob Erlbeck2e038f72014-07-07 10:46:00 +0200957 send_ns_alive_ack(nsi, sgsn_peer);
958 send_ns_unblock_ack(nsi, sgsn_peer);
959 send_ns_alive(nsi, sgsn_peer);
960}
961
Holger Hans Peter Freyther99a20d62014-07-07 14:19:10 +0200962static void configure_sgsn_peer(struct sockaddr_in *sgsn_peer)
963{
964 sgsn_peer->sin_family = AF_INET;
965 sgsn_peer->sin_port = htons(32000);
966 sgsn_peer->sin_addr.s_addr = htonl(REMOTE_SGSN_ADDR);
967}
968
Jacob Erlbeckf181f9e2014-08-27 12:44:25 +0200969static void configure_sgsn2_peer(struct sockaddr_in *sgsn_peer)
970{
971 sgsn_peer->sin_family = AF_INET;
972 sgsn_peer->sin_port = htons(32001);
973 sgsn_peer->sin_addr.s_addr = htonl(REMOTE_SGSN2_ADDR);
974}
975
Holger Hans Peter Freyther99a20d62014-07-07 14:19:10 +0200976static void configure_bss_peers(struct sockaddr_in *bss_peers, size_t size)
977{
978 size_t i;
979
980 for (i = 0; i < size; ++i) {
981 bss_peers[i].sin_family = AF_INET;
982 bss_peers[i].sin_port = htons((i + 1) * 1111);
983 bss_peers[i].sin_addr.s_addr = htonl(REMOTE_BSS_ADDR);
984 }
985}
986
Jacob Erlbeck51a869c2013-10-15 12:00:26 +0200987int gprs_ns_rcvmsg(struct gprs_ns_inst *nsi, struct msgb *msg,
988 struct sockaddr_in *saddr, enum gprs_ns_ll ll);
989
990/* override */
991int gprs_ns_callback(enum gprs_ns_evt event, struct gprs_nsvc *nsvc,
992 struct msgb *msg, uint16_t bvci)
993{
Holger Hans Peter Freytherdaaea0c2015-08-03 09:28:41 +0200994 printf("CALLBACK, event %d, msg length %zu, bvci 0x%04x\n%s\n\n",
Jacob Erlbeck51a869c2013-10-15 12:00:26 +0200995 event, msgb_bssgp_len(msg), bvci,
Jacob Erlbeckff0d65a2014-07-09 23:19:11 +0200996 osmo_hexdump(msgb_l2(msg), msgb_l2len(msg)));
Jacob Erlbeck51a869c2013-10-15 12:00:26 +0200997
998 switch (event) {
999 case GPRS_NS_EVT_UNIT_DATA:
Holger Hans Peter Freythereece6272014-08-04 15:42:36 +02001000 return gbprox_rcvmsg(&gbcfg, msg, nsvc->nsei, bvci, nsvc->nsvci);
Jacob Erlbeck51a869c2013-10-15 12:00:26 +02001001 default:
1002 break;
1003 }
1004 return 0;
1005}
1006
1007/* override */
1008ssize_t sendto(int sockfd, const void *buf, size_t len, int flags,
1009 const struct sockaddr *dest_addr, socklen_t addrlen)
1010{
1011 typedef ssize_t (*sendto_t)(int, const void *, size_t, int,
1012 const struct sockaddr *, socklen_t);
1013 static sendto_t real_sendto = NULL;
1014 uint32_t dest_host = htonl(((struct sockaddr_in *)dest_addr)->sin_addr.s_addr);
Jacob Erlbeck2082afa2013-10-18 13:04:47 +02001015 int dest_port = htons(((struct sockaddr_in *)dest_addr)->sin_port);
Jacob Erlbeck51a869c2013-10-15 12:00:26 +02001016
1017 if (!real_sendto)
1018 real_sendto = dlsym(RTLD_NEXT, "sendto");
1019
1020 if (dest_host == REMOTE_BSS_ADDR)
Holger Hans Peter Freyther8e6ecc92015-04-23 11:55:23 -04001021 printf("MESSAGE to BSS at 0x%08x:%d, msg length %zu\n%s\n\n",
Jacob Erlbeck2082afa2013-10-18 13:04:47 +02001022 dest_host, dest_port,
1023 len, osmo_hexdump(buf, len));
Jacob Erlbeck51a869c2013-10-15 12:00:26 +02001024 else if (dest_host == REMOTE_SGSN_ADDR)
Holger Hans Peter Freyther8e6ecc92015-04-23 11:55:23 -04001025 printf("MESSAGE to SGSN at 0x%08x:%d, msg length %zu\n%s\n\n",
Jacob Erlbeck2082afa2013-10-18 13:04:47 +02001026 dest_host, dest_port,
1027 len, osmo_hexdump(buf, len));
Jacob Erlbeckf181f9e2014-08-27 12:44:25 +02001028 else if (dest_host == REMOTE_SGSN2_ADDR)
Holger Hans Peter Freyther8e6ecc92015-04-23 11:55:23 -04001029 printf("MESSAGE to SGSN 2 at 0x%08x:%d, msg length %zu\n%s\n\n",
Jacob Erlbeckf181f9e2014-08-27 12:44:25 +02001030 dest_host, dest_port,
1031 len, osmo_hexdump(buf, len));
Jacob Erlbeck51a869c2013-10-15 12:00:26 +02001032 else
1033 return real_sendto(sockfd, buf, len, flags, dest_addr, addrlen);
1034
1035 return len;
1036}
1037
1038/* override */
1039int gprs_ns_sendmsg(struct gprs_ns_inst *nsi, struct msgb *msg)
1040{
Jacob Erlbeck2082afa2013-10-18 13:04:47 +02001041 typedef int (*gprs_ns_sendmsg_t)(struct gprs_ns_inst *nsi, struct msgb *msg);
1042 static gprs_ns_sendmsg_t real_gprs_ns_sendmsg = NULL;
Jacob Erlbeck51a869c2013-10-15 12:00:26 +02001043 uint16_t bvci = msgb_bvci(msg);
1044 uint16_t nsei = msgb_nsei(msg);
1045
Jacob Erlbeckff0d65a2014-07-09 23:19:11 +02001046 size_t len = msgb_length(msg);
Jacob Erlbeck51a869c2013-10-15 12:00:26 +02001047
Jacob Erlbeck2082afa2013-10-18 13:04:47 +02001048 if (!real_gprs_ns_sendmsg)
1049 real_gprs_ns_sendmsg = dlsym(RTLD_NEXT, "gprs_ns_sendmsg");
1050
Jacob Erlbeck51a869c2013-10-15 12:00:26 +02001051 if (nsei == SGSN_NSEI)
Jacob Erlbeckff0d65a2014-07-09 23:19:11 +02001052 printf("NS UNITDATA MESSAGE to SGSN, BVCI 0x%04x, "
Holger Hans Peter Freyther8e6ecc92015-04-23 11:55:23 -04001053 "msg length %zu (%s)\n",
Jacob Erlbeckff0d65a2014-07-09 23:19:11 +02001054 bvci, len, __func__);
Jacob Erlbeckf181f9e2014-08-27 12:44:25 +02001055 else if (nsei == SGSN2_NSEI)
1056 printf("NS UNITDATA MESSAGE to SGSN 2, BVCI 0x%04x, "
Holger Hans Peter Freyther8e6ecc92015-04-23 11:55:23 -04001057 "msg length %zu (%s)\n",
Jacob Erlbeckf181f9e2014-08-27 12:44:25 +02001058 bvci, len, __func__);
Jacob Erlbeck51a869c2013-10-15 12:00:26 +02001059 else
Jacob Erlbeckff0d65a2014-07-09 23:19:11 +02001060 printf("NS UNITDATA MESSAGE to BSS, BVCI 0x%04x, "
Holger Hans Peter Freyther8e6ecc92015-04-23 11:55:23 -04001061 "msg length %zu (%s)\n",
Jacob Erlbeckff0d65a2014-07-09 23:19:11 +02001062 bvci, len, __func__);
Jacob Erlbeck51a869c2013-10-15 12:00:26 +02001063
Jacob Erlbeckacfaff32014-09-22 18:54:34 +02001064 if (received_messages) {
1065 struct msgb *msg_copy;
1066 msg_copy = gprs_msgb_copy(msg, "received_messages");
1067 llist_add_tail(&msg_copy->list, received_messages);
1068 }
1069
Jacob Erlbeck2082afa2013-10-18 13:04:47 +02001070 return real_gprs_ns_sendmsg(nsi, msg);
Jacob Erlbeck51a869c2013-10-15 12:00:26 +02001071}
1072
Jacob Erlbeckacfaff32014-09-22 18:54:34 +02001073/* Get the next message from the receive FIFO
1074 *
1075 * \returns a pointer to the message which will be invalidated at the next call
1076 * to expect_msg. Returns NULL, if there is no message left.
1077 */
1078static struct msgb *expect_msg(void)
1079{
1080 static struct msgb *msg = NULL;
1081
1082 msgb_free(msg);
1083 msg = NULL;
1084
1085 if (!received_messages)
1086 return NULL;
1087
1088 if (llist_empty(received_messages))
1089 return NULL;
1090
1091 msg = llist_entry(received_messages->next, struct msgb, list);
1092 llist_del(&msg->list);
1093
1094 return msg;
1095}
1096
1097struct expect_result {
1098 struct msgb *msg;
1099 struct gprs_gb_parse_context parse_ctx;
1100};
1101
1102static struct expect_result *expect_bssgp_msg(
1103 int match_nsei, int match_bvci, int match_pdu_type)
1104{
1105 static struct expect_result result;
1106 static const struct expect_result empty_result = {0,};
1107 static struct msgb *msg;
1108 uint16_t nsei;
1109 int rc;
1110
1111 memcpy(&result, &empty_result, sizeof(result));
1112
1113 msg = expect_msg();
1114 if (!msg)
1115 return NULL;
1116
1117 nsei = msgb_nsei(msg);
1118
1119 if (match_nsei != MATCH_ANY && match_nsei != nsei) {
1120 fprintf(stderr, "%s: NSEI mismatch (expected %u, got %u)\n",
1121 __func__, match_nsei, nsei);
1122 return NULL;
1123 }
1124
1125 if (match_bvci != MATCH_ANY && match_bvci != msgb_bvci(msg)) {
1126 fprintf(stderr, "%s: BVCI mismatch (expected %u, got %u)\n",
1127 __func__, match_bvci, msgb_bvci(msg));
1128 return NULL;
1129 }
1130
1131 result.msg = msg;
1132
1133 result.parse_ctx.to_bss = nsei != SGSN_NSEI && nsei != SGSN2_NSEI;
1134 result.parse_ctx.peer_nsei = nsei;
1135
1136 if (!msgb_bssgph(msg)) {
1137 fprintf(stderr, "%s: Expected BSSGP\n", __func__);
1138 return NULL;
1139 }
1140
1141 rc = gprs_gb_parse_bssgp(msgb_bssgph(msg), msgb_bssgp_len(msg),
1142 &result.parse_ctx);
1143
1144 if (!rc) {
1145 fprintf(stderr, "%s: Failed to parse message\n", __func__);
1146 return NULL;
1147 }
1148
1149 if (match_pdu_type != MATCH_ANY &&
1150 match_pdu_type != result.parse_ctx.pdu_type) {
1151 fprintf(stderr, "%s: PDU type mismatch (expected %u, got %u)\n",
1152 __func__, match_pdu_type, result.parse_ctx.pdu_type);
1153 return NULL;
1154 }
1155
1156 return &result;
1157}
1158
1159static struct expect_result *expect_llc_msg(
1160 int match_nsei, int match_bvci, int match_sapi, int match_type)
1161{
1162 static struct expect_result *result;
1163
1164 result = expect_bssgp_msg(match_nsei, match_bvci, MATCH_ANY);
1165 if (!result)
1166 return NULL;
1167
1168 if (!result->parse_ctx.llc) {
1169 fprintf(stderr, "%s: Expected LLC message\n", __func__);
1170 return NULL;
1171 }
1172
1173 if (match_sapi != MATCH_ANY &&
1174 match_sapi != result->parse_ctx.llc_hdr_parsed.sapi) {
1175 fprintf(stderr, "%s: LLC SAPI mismatch (expected %u, got %u)\n",
1176 __func__, match_sapi, result->parse_ctx.llc_hdr_parsed.sapi);
1177 return NULL;
1178 }
1179
1180 if (match_type != MATCH_ANY &&
1181 match_type != result->parse_ctx.llc_hdr_parsed.cmd) {
1182 fprintf(stderr,
1183 "%s: LLC command/type mismatch (expected %u, got %u)\n",
1184 __func__, match_type, result->parse_ctx.llc_hdr_parsed.cmd);
1185 return NULL;
1186 }
1187
1188 return result;
1189}
1190
1191static struct expect_result *expect_gmm_msg(int match_nsei, int match_bvci,
1192 int match_type)
1193{
1194 static struct expect_result *result;
1195
1196 result = expect_llc_msg(match_nsei, match_bvci, GPRS_SAPI_GMM, GPRS_LLC_UI);
1197 if (!result)
1198 return NULL;
1199
1200 if (!result->parse_ctx.g48_hdr) {
1201 fprintf(stderr, "%s: Expected GSM 04.08 message\n", __func__);
1202 return NULL;
1203 }
1204
1205 if (match_type != MATCH_ANY &&
1206 match_type != result->parse_ctx.g48_hdr->msg_type) {
1207 fprintf(stderr,
1208 "%s: GSM 04.08 message type mismatch (expected %u, got %u)\n",
1209 __func__, match_type, result->parse_ctx.g48_hdr->msg_type);
1210 return NULL;
1211 }
1212
1213 return result;
1214}
1215
Jacob Erlbeck51a869c2013-10-15 12:00:26 +02001216static void dump_rate_ctr_group(FILE *stream, const char *prefix,
1217 struct rate_ctr_group *ctrg)
1218{
1219 unsigned int i;
1220
1221 for (i = 0; i < ctrg->desc->num_ctr; i++) {
1222 struct rate_ctr *ctr = &ctrg->ctr[i];
1223 if (ctr->current && !strchr(ctrg->desc->ctr_desc[i].name, '.'))
1224 fprintf(stream, " %s%s: %llu%s",
1225 prefix, ctrg->desc->ctr_desc[i].description,
1226 (long long)ctr->current,
1227 "\n");
1228 };
1229}
1230
1231/* Signal handler for signals from NS layer */
1232static int test_signal(unsigned int subsys, unsigned int signal,
1233 void *handler_data, void *signal_data)
1234{
1235 struct ns_signal_data *nssd = signal_data;
1236 int rc;
1237
1238 if (subsys != SS_L_NS)
1239 return 0;
1240
1241 switch (signal) {
1242 case S_NS_RESET:
1243 printf("==> got signal NS_RESET, NS-VC 0x%04x/%s\n",
1244 nssd->nsvc->nsvci,
1245 gprs_ns_ll_str(nssd->nsvc));
1246 break;
1247
1248 case S_NS_ALIVE_EXP:
1249 printf("==> got signal NS_ALIVE_EXP, NS-VC 0x%04x/%s\n",
1250 nssd->nsvc->nsvci,
1251 gprs_ns_ll_str(nssd->nsvc));
1252 break;
1253
1254 case S_NS_BLOCK:
1255 printf("==> got signal NS_BLOCK, NS-VC 0x%04x/%s\n",
1256 nssd->nsvc->nsvci,
1257 gprs_ns_ll_str(nssd->nsvc));
1258 break;
1259
1260 case S_NS_UNBLOCK:
1261 printf("==> got signal NS_UNBLOCK, NS-VC 0x%04x/%s\n",
1262 nssd->nsvc->nsvci,
1263 gprs_ns_ll_str(nssd->nsvc));
1264 break;
1265
1266 case S_NS_REPLACED:
1267 printf("==> got signal NS_REPLACED: 0x%04x/%s",
1268 nssd->nsvc->nsvci,
1269 gprs_ns_ll_str(nssd->nsvc));
1270 printf(" -> 0x%04x/%s\n",
1271 nssd->old_nsvc->nsvci,
1272 gprs_ns_ll_str(nssd->old_nsvc));
1273 break;
1274
1275 default:
1276 printf("==> got signal %d, NS-VC 0x%04x/%s\n", signal,
1277 nssd->nsvc->nsvci,
1278 gprs_ns_ll_str(nssd->nsvc));
1279 break;
1280 }
1281 printf("\n");
1282 rc = gbprox_signal(subsys, signal, handler_data, signal_data);
1283 return rc;
1284}
1285
1286static int gprs_process_message(struct gprs_ns_inst *nsi, const char *text, struct sockaddr_in *peer, const unsigned char* data, size_t data_len)
1287{
1288 struct msgb *msg;
1289 int ret;
1290 if (data_len > NS_ALLOC_SIZE - NS_ALLOC_HEADROOM) {
Holger Hans Peter Freyther8e6ecc92015-04-23 11:55:23 -04001291 fprintf(stderr, "message too long: %zu\n", data_len);
Jacob Erlbeck51a869c2013-10-15 12:00:26 +02001292 return -1;
1293 }
1294
1295 msg = gprs_ns_msgb_alloc();
Neels Hofmeyrc9ac20e2016-04-14 15:21:33 +02001296 OSMO_ASSERT(msg);
Jacob Erlbeck51a869c2013-10-15 12:00:26 +02001297 memmove(msg->data, data, data_len);
1298 msg->l2h = msg->data;
1299 msgb_put(msg, data_len);
1300
1301 printf("PROCESSING %s from 0x%08x:%d\n%s\n\n",
1302 text, ntohl(peer->sin_addr.s_addr), ntohs(peer->sin_port),
1303 osmo_hexdump(data, data_len));
1304
1305 ret = gprs_ns_rcvmsg(nsi, msg, peer, GPRS_NS_LL_UDP);
1306
1307 printf("result (%s) = %d\n\n", text, ret);
1308
1309 msgb_free(msg);
1310
1311 return ret;
1312}
1313
1314static void gprs_dump_nsi(struct gprs_ns_inst *nsi)
1315{
1316 struct gprs_nsvc *nsvc;
1317
1318 printf("Current NS-VCIs:\n");
1319 llist_for_each_entry(nsvc, &nsi->gprs_nsvcs, list) {
1320 struct sockaddr_in *peer = &(nsvc->ip.bts_addr);
Jacob Erlbeck2082afa2013-10-18 13:04:47 +02001321 printf(" VCI 0x%04x, NSEI 0x%04x, peer 0x%08x:%d%s%s\n",
Jacob Erlbeck51a869c2013-10-15 12:00:26 +02001322 nsvc->nsvci, nsvc->nsei,
Jacob Erlbeck2082afa2013-10-18 13:04:47 +02001323 ntohl(peer->sin_addr.s_addr), ntohs(peer->sin_port),
1324 nsvc->state & NSE_S_BLOCKED ? ", blocked" : "",
1325 nsvc->state & NSE_S_ALIVE ? "" : ", dead"
Jacob Erlbeck51a869c2013-10-15 12:00:26 +02001326 );
1327 dump_rate_ctr_group(stdout, " ", nsvc->ctrg);
1328 }
1329 printf("\n");
1330}
1331
1332static void test_gbproxy()
1333{
1334 struct gprs_ns_inst *nsi = gprs_ns_instantiate(gprs_ns_callback, NULL);
1335 struct sockaddr_in bss_peer[4] = {{0},};
Jacob Erlbeck2082afa2013-10-18 13:04:47 +02001336 struct sockaddr_in sgsn_peer= {0};
Jacob Erlbeck51a869c2013-10-15 12:00:26 +02001337
1338 bssgp_nsi = nsi;
1339 gbcfg.nsi = bssgp_nsi;
1340 gbcfg.nsip_sgsn_nsei = SGSN_NSEI;
1341
Holger Hans Peter Freyther99a20d62014-07-07 14:19:10 +02001342 configure_sgsn_peer(&sgsn_peer);
1343 configure_bss_peers(bss_peer, ARRAY_SIZE(bss_peer));
Jacob Erlbeck51a869c2013-10-15 12:00:26 +02001344
Jacob Erlbeckff0d65a2014-07-09 23:19:11 +02001345 printf("=== %s ===\n", __func__);
Jacob Erlbeck2082afa2013-10-18 13:04:47 +02001346 printf("--- Initialise SGSN ---\n\n");
1347
Jacob Erlbeckf181f9e2014-08-27 12:44:25 +02001348 connect_sgsn(nsi, &sgsn_peer, SGSN_NSEI);
Jacob Erlbeck2082afa2013-10-18 13:04:47 +02001349 gprs_dump_nsi(nsi);
1350
Jacob Erlbeck51a869c2013-10-15 12:00:26 +02001351 printf("--- Initialise BSS 1 ---\n\n");
1352
1353 setup_ns(nsi, &bss_peer[0], 0x1001, 0x1000);
1354 setup_bssgp(nsi, &bss_peer[0], 0x1002);
1355 gprs_dump_nsi(nsi);
Jacob Erlbeck7b821d02014-08-08 08:37:37 +02001356 dump_peers(stdout, 0, 0, &gbcfg);
Jacob Erlbeck51a869c2013-10-15 12:00:26 +02001357
Jacob Erlbeck2082afa2013-10-18 13:04:47 +02001358 send_bssgp_reset_ack(nsi, &sgsn_peer, 0x1002);
1359
Jacob Erlbeck51a869c2013-10-15 12:00:26 +02001360 printf("--- Initialise BSS 2 ---\n\n");
1361
1362 setup_ns(nsi, &bss_peer[1], 0x2001, 0x2000);
1363 setup_bssgp(nsi, &bss_peer[1], 0x2002);
1364 gprs_dump_nsi(nsi);
Jacob Erlbeck7b821d02014-08-08 08:37:37 +02001365 dump_peers(stdout, 0, 0, &gbcfg);
Jacob Erlbeck51a869c2013-10-15 12:00:26 +02001366
Jacob Erlbeck2082afa2013-10-18 13:04:47 +02001367 send_bssgp_reset_ack(nsi, &sgsn_peer, 0x2002);
1368
Jacob Erlbeck51a869c2013-10-15 12:00:26 +02001369 printf("--- Move BSS 1 to new port ---\n\n");
1370
1371 setup_ns(nsi, &bss_peer[2], 0x1001, 0x1000);
1372 gprs_dump_nsi(nsi);
Jacob Erlbeck7b821d02014-08-08 08:37:37 +02001373 dump_peers(stdout, 0, 0, &gbcfg);
Jacob Erlbeck51a869c2013-10-15 12:00:26 +02001374
1375 printf("--- Move BSS 2 to former BSS 1 port ---\n\n");
1376
1377 setup_ns(nsi, &bss_peer[0], 0x2001, 0x2000);
1378 gprs_dump_nsi(nsi);
Jacob Erlbeck7b821d02014-08-08 08:37:37 +02001379 dump_peers(stdout, 0, 0, &gbcfg);
Jacob Erlbeck51a869c2013-10-15 12:00:26 +02001380
1381 printf("--- Move BSS 1 to current BSS 2 port ---\n\n");
1382
1383 setup_ns(nsi, &bss_peer[0], 0x2001, 0x2000);
1384 gprs_dump_nsi(nsi);
Jacob Erlbeck7b821d02014-08-08 08:37:37 +02001385 dump_peers(stdout, 0, 0, &gbcfg);
Jacob Erlbeck51a869c2013-10-15 12:00:26 +02001386
1387 printf("--- Move BSS 2 to new port ---\n\n");
1388
1389 setup_ns(nsi, &bss_peer[3], 0x2001, 0x2000);
1390 gprs_dump_nsi(nsi);
Jacob Erlbeck7b821d02014-08-08 08:37:37 +02001391 dump_peers(stdout, 0, 0, &gbcfg);
Jacob Erlbeck51a869c2013-10-15 12:00:26 +02001392
1393 printf("--- Move BSS 2 to former BSS 1 port ---\n\n");
1394
1395 setup_ns(nsi, &bss_peer[2], 0x2001, 0x2000);
1396 gprs_dump_nsi(nsi);
Jacob Erlbeck7b821d02014-08-08 08:37:37 +02001397 dump_peers(stdout, 0, 0, &gbcfg);
Jacob Erlbeck51a869c2013-10-15 12:00:26 +02001398
Jacob Erlbeck2082afa2013-10-18 13:04:47 +02001399 printf("--- Move BSS 1 to original BSS 1 port ---\n\n");
1400
1401 setup_ns(nsi, &bss_peer[0], 0x1001, 0x1000);
1402 gprs_dump_nsi(nsi);
Jacob Erlbeck7b821d02014-08-08 08:37:37 +02001403 dump_peers(stdout, 0, 0, &gbcfg);
Jacob Erlbeck2082afa2013-10-18 13:04:47 +02001404
1405 printf("--- Reset BSS 1 with a new BVCI ---\n\n");
1406
1407 setup_bssgp(nsi, &bss_peer[0], 0x1012);
1408 gprs_dump_nsi(nsi);
Jacob Erlbeck7b821d02014-08-08 08:37:37 +02001409 dump_peers(stdout, 0, 0, &gbcfg);
Jacob Erlbeck2082afa2013-10-18 13:04:47 +02001410
1411 send_bssgp_reset_ack(nsi, &sgsn_peer, 0x1012);
1412
1413 printf("--- Reset BSS 1 with the old BVCI ---\n\n");
1414
1415 setup_bssgp(nsi, &bss_peer[0], 0x1002);
1416 gprs_dump_nsi(nsi);
Jacob Erlbeck7b821d02014-08-08 08:37:37 +02001417 dump_peers(stdout, 0, 0, &gbcfg);
Jacob Erlbeck2082afa2013-10-18 13:04:47 +02001418
1419 send_bssgp_reset_ack(nsi, &sgsn_peer, 0x1002);
1420
1421 printf("--- Reset BSS 1 with the old BVCI again ---\n\n");
1422
1423 setup_bssgp(nsi, &bss_peer[0], 0x1002);
1424 gprs_dump_nsi(nsi);
Jacob Erlbeck7b821d02014-08-08 08:37:37 +02001425 dump_peers(stdout, 0, 0, &gbcfg);
Jacob Erlbeck2082afa2013-10-18 13:04:47 +02001426
1427 send_bssgp_reset_ack(nsi, &sgsn_peer, 0x1002);
1428
1429 printf("--- Send message from BSS 1 to SGSN, BVCI 0x1012 ---\n\n");
1430
1431 send_ns_unitdata(nsi, NULL, &bss_peer[0], 0x1012, (uint8_t *)"", 0);
1432
1433 printf("--- Send message from SGSN to BSS 1, BVCI 0x1012 ---\n\n");
1434
1435 send_ns_unitdata(nsi, NULL, &sgsn_peer, 0x1012, (uint8_t *)"", 0);
1436
1437 printf("--- Send message from BSS 1 to SGSN, BVCI 0x1002 ---\n\n");
1438
1439 send_ns_unitdata(nsi, NULL, &bss_peer[0], 0x1012, (uint8_t *)"", 0);
1440
1441 printf("--- Send message from SGSN to BSS 1, BVCI 0x1002 ---\n\n");
1442
1443 send_ns_unitdata(nsi, NULL, &sgsn_peer, 0x1012, (uint8_t *)"", 0);
1444
1445 printf("--- Send message from BSS 2 to SGSN, BVCI 0x2002 ---\n\n");
1446
1447 send_ns_unitdata(nsi, NULL, &bss_peer[0], 0x2002, (uint8_t *)"", 0);
1448
1449 printf("--- Send message from SGSN to BSS 2, BVCI 0x2002 ---\n\n");
1450
1451 send_ns_unitdata(nsi, NULL, &sgsn_peer, 0x2002, (uint8_t *)"", 0);
1452
1453 printf("--- Reset BSS 1 with the old BVCI on BSS2's link ---\n\n");
1454
1455 setup_bssgp(nsi, &bss_peer[2], 0x1002);
1456 gprs_dump_nsi(nsi);
Jacob Erlbeck7b821d02014-08-08 08:37:37 +02001457 dump_peers(stdout, 0, 0, &gbcfg);
Jacob Erlbeck2082afa2013-10-18 13:04:47 +02001458
Holger Hans Peter Freytherb9004592014-08-04 11:26:54 +02001459 dump_global(stdout, 0);
Jacob Erlbeckda890c72013-10-18 22:12:16 +02001460
Jacob Erlbeck2082afa2013-10-18 13:04:47 +02001461 send_bssgp_reset_ack(nsi, &sgsn_peer, 0x1002);
1462
1463 printf("--- Send message from BSS 1 to SGSN, BVCI 0x1002 ---\n\n");
1464
1465 send_ns_unitdata(nsi, NULL, &bss_peer[0], 0x1012, (uint8_t *)"", 0);
1466
1467 printf("--- Send message from SGSN to BSS 1, BVCI 0x1002 ---\n\n");
1468
1469 send_ns_unitdata(nsi, NULL, &sgsn_peer, 0x1012, (uint8_t *)"", 0);
1470
Jacob Erlbeckda890c72013-10-18 22:12:16 +02001471 printf("--- Send message from SGSN to BSS 1, BVCI 0x10ff (invalid) ---\n\n");
1472
1473 send_ns_unitdata(nsi, NULL, &sgsn_peer, 0x10ff, (uint8_t *)"", 0);
1474
Jacob Erlbeck7fb26c22014-09-04 11:08:50 +02001475 /* Find peer */
1476 OSMO_ASSERT(gbproxy_peer_by_bvci(&gbcfg, 0xeeee) == NULL);
1477 OSMO_ASSERT(gbproxy_peer_by_bvci(&gbcfg, 0x1000) == NULL);
1478 OSMO_ASSERT(gbproxy_peer_by_bvci(&gbcfg, 0x1012) != NULL);
1479 OSMO_ASSERT(gbproxy_peer_by_nsei(&gbcfg, 0xeeee) == NULL);
1480 OSMO_ASSERT(gbproxy_peer_by_nsei(&gbcfg, 0x1012) == NULL);
1481 OSMO_ASSERT(gbproxy_peer_by_nsei(&gbcfg, 0x1000) != NULL);
1482
1483
1484 /* Cleanup */
1485 OSMO_ASSERT(gbproxy_cleanup_peers(&gbcfg, 0, 0) == 0);
1486 OSMO_ASSERT(gbproxy_cleanup_peers(&gbcfg, 0x1000, 0xeeee) == 0);
1487 OSMO_ASSERT(gbproxy_cleanup_peers(&gbcfg, 0, 0x1002) == 0);
1488 OSMO_ASSERT(gbproxy_cleanup_peers(&gbcfg, 0x1000, 0x1012) == 1);
1489 OSMO_ASSERT(gbproxy_cleanup_peers(&gbcfg, 0x1000, 0x1012) == 0);
1490
1491 dump_peers(stdout, 0, 0, &gbcfg);
1492
Holger Hans Peter Freytherb9004592014-08-04 11:26:54 +02001493 dump_global(stdout, 0);
Jacob Erlbeckda890c72013-10-18 22:12:16 +02001494
Holger Hans Peter Freythereece6272014-08-04 15:42:36 +02001495 gbprox_reset(&gbcfg);
Jacob Erlbeck51a869c2013-10-15 12:00:26 +02001496 gprs_ns_destroy(nsi);
1497 nsi = NULL;
Jacob Erlbeck72b401f2013-10-24 12:48:55 +02001498}
1499
1500static void test_gbproxy_ident_changes()
1501{
1502 struct gprs_ns_inst *nsi = gprs_ns_instantiate(gprs_ns_callback, NULL);
1503 struct sockaddr_in bss_peer[1] = {{0},};
1504 struct sockaddr_in sgsn_peer= {0};
1505 uint16_t nsei[2] = {0x1000, 0x2000};
1506 uint16_t nsvci[2] = {0x1001, 0x2001};
1507 uint16_t bvci[4] = {0x1002, 0x2002, 0x3002, 0x4002};
1508
1509 bssgp_nsi = nsi;
1510 gbcfg.nsi = bssgp_nsi;
1511 gbcfg.nsip_sgsn_nsei = SGSN_NSEI;
1512
Holger Hans Peter Freyther99a20d62014-07-07 14:19:10 +02001513 configure_sgsn_peer(&sgsn_peer);
1514 configure_bss_peers(bss_peer, ARRAY_SIZE(bss_peer));
Jacob Erlbeck72b401f2013-10-24 12:48:55 +02001515
Jacob Erlbeckff0d65a2014-07-09 23:19:11 +02001516 printf("=== %s ===\n", __func__);
Jacob Erlbeck72b401f2013-10-24 12:48:55 +02001517 printf("--- Initialise SGSN ---\n\n");
1518
Jacob Erlbeckf181f9e2014-08-27 12:44:25 +02001519 connect_sgsn(nsi, &sgsn_peer, SGSN_NSEI);
Jacob Erlbeck72b401f2013-10-24 12:48:55 +02001520 gprs_dump_nsi(nsi);
1521
1522 printf("--- Initialise BSS 1 ---\n\n");
1523
1524 setup_ns(nsi, &bss_peer[0], nsvci[0], nsei[0]);
1525 gprs_dump_nsi(nsi);
1526
1527 printf("--- Setup BVCI 1 ---\n\n");
1528
1529 setup_bssgp(nsi, &bss_peer[0], bvci[0]);
1530 send_bssgp_reset_ack(nsi, &sgsn_peer, bvci[0]);
Jacob Erlbeck7b821d02014-08-08 08:37:37 +02001531 dump_peers(stdout, 0, 0, &gbcfg);
Jacob Erlbeck72b401f2013-10-24 12:48:55 +02001532
1533 printf("--- Setup BVCI 2 ---\n\n");
1534
1535 setup_bssgp(nsi, &bss_peer[0], bvci[1]);
1536 send_bssgp_reset_ack(nsi, &sgsn_peer, bvci[1]);
Jacob Erlbeck7b821d02014-08-08 08:37:37 +02001537 dump_peers(stdout, 0, 0, &gbcfg);
Jacob Erlbeck72b401f2013-10-24 12:48:55 +02001538
1539 printf("--- Send message from BSS 1 to SGSN and back, BVCI 1 ---\n\n");
1540
1541 send_ns_unitdata(nsi, NULL, &bss_peer[0], bvci[0], (uint8_t *)"", 0);
1542 send_ns_unitdata(nsi, NULL, &sgsn_peer, bvci[0], (uint8_t *)"", 0);
1543
1544 printf("--- Send message from BSS 1 to SGSN and back, BVCI 2 ---\n\n");
1545
1546 send_ns_unitdata(nsi, NULL, &bss_peer[0], bvci[1], (uint8_t *)"", 0);
1547 send_ns_unitdata(nsi, NULL, &sgsn_peer, bvci[1], (uint8_t *)"", 0);
1548
1549 printf("--- Change NSEI ---\n\n");
1550
1551 setup_ns(nsi, &bss_peer[0], nsvci[0], nsei[1]);
1552 gprs_dump_nsi(nsi);
1553
1554 printf("--- Setup BVCI 1 ---\n\n");
1555
1556 setup_bssgp(nsi, &bss_peer[0], bvci[0]);
1557 send_bssgp_reset_ack(nsi, &sgsn_peer, bvci[0]);
Jacob Erlbeck7b821d02014-08-08 08:37:37 +02001558 dump_peers(stdout, 0, 0, &gbcfg);
Jacob Erlbeck72b401f2013-10-24 12:48:55 +02001559
1560 printf("--- Setup BVCI 3 ---\n\n");
1561
1562 setup_bssgp(nsi, &bss_peer[0], bvci[2]);
1563 send_bssgp_reset_ack(nsi, &sgsn_peer, bvci[2]);
Jacob Erlbeck7b821d02014-08-08 08:37:37 +02001564 dump_peers(stdout, 0, 0, &gbcfg);
Jacob Erlbeck72b401f2013-10-24 12:48:55 +02001565
1566 printf("--- Send message from BSS 1 to SGSN and back, BVCI 1 ---\n\n");
1567
1568 send_ns_unitdata(nsi, NULL, &bss_peer[0], bvci[0], (uint8_t *)"", 0);
1569 send_ns_unitdata(nsi, NULL, &sgsn_peer, bvci[0], (uint8_t *)"", 0);
1570
1571 printf("--- Send message from BSS 1 to SGSN and back, BVCI 2 "
1572 " (should fail) ---\n\n");
1573
1574 send_ns_unitdata(nsi, NULL, &bss_peer[0], bvci[1], (uint8_t *)"", 0);
Jacob Erlbeck7b821d02014-08-08 08:37:37 +02001575 dump_peers(stdout, 0, 0, &gbcfg);
Jacob Erlbeck72b401f2013-10-24 12:48:55 +02001576 send_ns_unitdata(nsi, NULL, &sgsn_peer, bvci[1], (uint8_t *)"", 0);
Jacob Erlbeck7b821d02014-08-08 08:37:37 +02001577 dump_peers(stdout, 0, 0, &gbcfg);
Jacob Erlbeck72b401f2013-10-24 12:48:55 +02001578
1579 printf("--- Send message from BSS 1 to SGSN and back, BVCI 3 ---\n\n");
1580
1581 send_ns_unitdata(nsi, NULL, &bss_peer[0], bvci[2], (uint8_t *)"", 0);
1582 send_ns_unitdata(nsi, NULL, &sgsn_peer, bvci[2], (uint8_t *)"", 0);
1583
1584 printf("--- Change NSVCI ---\n\n");
1585
1586 setup_ns(nsi, &bss_peer[0], nsvci[1], nsei[1]);
1587 gprs_dump_nsi(nsi);
1588
1589 printf("--- Setup BVCI 1 ---\n\n");
1590
1591 setup_bssgp(nsi, &bss_peer[0], bvci[0]);
1592 send_bssgp_reset_ack(nsi, &sgsn_peer, bvci[0]);
Jacob Erlbeck7b821d02014-08-08 08:37:37 +02001593 dump_peers(stdout, 0, 0, &gbcfg);
Jacob Erlbeck72b401f2013-10-24 12:48:55 +02001594
1595 printf("--- Setup BVCI 4 ---\n\n");
1596
1597 setup_bssgp(nsi, &bss_peer[0], bvci[3]);
1598 send_bssgp_reset_ack(nsi, &sgsn_peer, bvci[3]);
Jacob Erlbeck7b821d02014-08-08 08:37:37 +02001599 dump_peers(stdout, 0, 0, &gbcfg);
Jacob Erlbeck72b401f2013-10-24 12:48:55 +02001600
1601 printf("--- Send message from BSS 1 to SGSN and back, BVCI 1 ---\n\n");
1602
1603 send_ns_unitdata(nsi, NULL, &bss_peer[0], bvci[0], (uint8_t *)"", 0);
1604 send_ns_unitdata(nsi, NULL, &sgsn_peer, bvci[0], (uint8_t *)"", 0);
1605
1606 printf("--- Send message from BSS 1 to SGSN and back, BVCI 2 "
1607 " (should fail) ---\n\n");
1608
1609 send_ns_unitdata(nsi, NULL, &bss_peer[0], bvci[1], (uint8_t *)"", 0);
Jacob Erlbeck7b821d02014-08-08 08:37:37 +02001610 dump_peers(stdout, 0, 0, &gbcfg);
Jacob Erlbeck72b401f2013-10-24 12:48:55 +02001611 send_ns_unitdata(nsi, NULL, &sgsn_peer, bvci[1], (uint8_t *)"", 0);
Jacob Erlbeck7b821d02014-08-08 08:37:37 +02001612 dump_peers(stdout, 0, 0, &gbcfg);
Jacob Erlbeck72b401f2013-10-24 12:48:55 +02001613
1614 printf("--- Send message from BSS 1 to SGSN and back, BVCI 3 ---\n\n");
1615
1616 send_ns_unitdata(nsi, NULL, &bss_peer[0], bvci[2], (uint8_t *)"", 0);
1617 send_ns_unitdata(nsi, NULL, &sgsn_peer, bvci[2], (uint8_t *)"", 0);
1618
1619 printf("--- Send message from BSS 1 to SGSN and back, BVCI 4 ---\n\n");
1620
1621 send_ns_unitdata(nsi, NULL, &bss_peer[0], bvci[3], (uint8_t *)"", 0);
1622 send_ns_unitdata(nsi, NULL, &sgsn_peer, bvci[3], (uint8_t *)"", 0);
1623
Holger Hans Peter Freytherb9004592014-08-04 11:26:54 +02001624 dump_global(stdout, 0);
Jacob Erlbeck7b821d02014-08-08 08:37:37 +02001625 dump_peers(stdout, 0, 0, &gbcfg);
Jacob Erlbeck72b401f2013-10-24 12:48:55 +02001626
Holger Hans Peter Freythereece6272014-08-04 15:42:36 +02001627 gbprox_reset(&gbcfg);
Jacob Erlbeck72b401f2013-10-24 12:48:55 +02001628 gprs_ns_destroy(nsi);
1629 nsi = NULL;
Jacob Erlbeck51a869c2013-10-15 12:00:26 +02001630}
1631
Jacob Erlbeck7fb42db2014-07-07 10:46:01 +02001632static void test_gbproxy_ra_patching()
1633{
1634 struct gprs_ns_inst *nsi = gprs_ns_instantiate(gprs_ns_callback, NULL);
1635 struct sockaddr_in bss_peer[1] = {{0},};
1636 struct sockaddr_in sgsn_peer= {0};
1637 struct gprs_ra_id rai_bss =
1638 {.mcc = 112, .mnc = 332, .lac = 16464, .rac = 96};
1639 struct gprs_ra_id rai_sgsn =
1640 {.mcc = 123, .mnc = 456, .lac = 16464, .rac = 96};
1641 struct gprs_ra_id rai_unknown =
1642 {.mcc = 1, .mnc = 99, .lac = 99, .rac = 96};
Jacob Erlbeckc53f2a62014-08-15 14:56:28 +02001643 uint16_t cell_id = 0x7530;
Jacob Erlbeck7c101d92014-06-06 18:49:23 +02001644 const char *err_msg = NULL;
Jacob Erlbeck59748e62014-08-11 17:26:21 +02001645 const uint32_t ptmsi = 0xefe2b700;
1646 const uint32_t local_tlli = 0xefe2b700;
Jacob Erlbeckc53f2a62014-08-15 14:56:28 +02001647 const uint32_t foreign_tlli = 0xbbc54679;
Jacob Erlbeck991606b2014-09-12 10:33:38 +02001648 const uint32_t foreign_tlli2 = 0xbb00beef;
Jacob Erlbeckc53f2a62014-08-15 14:56:28 +02001649 const uint8_t imsi[] = {0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17, 0x18};
Jacob Erlbeck9a83d7a2014-09-25 11:17:31 +02001650 const char *patch_re = "^9898|^121314";
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +02001651 struct gbproxy_link_info *link_info;
Jacob Erlbeck59748e62014-08-11 17:26:21 +02001652 struct gbproxy_peer *peer;
Jacob Erlbeck55ec2bf2014-09-23 14:56:38 +02001653 LLIST_HEAD(rcv_list);
Jacob Erlbeckc79beec2014-10-10 09:48:12 +02001654 struct expect_result *expect_res;
Jacob Erlbeck59748e62014-08-11 17:26:21 +02001655
1656 OSMO_ASSERT(local_tlli == gprs_tmsi2tlli(ptmsi, TLLI_LOCAL));
Jacob Erlbeck7fb42db2014-07-07 10:46:01 +02001657
1658 bssgp_nsi = nsi;
1659 gbcfg.nsi = bssgp_nsi;
1660 gbcfg.nsip_sgsn_nsei = SGSN_NSEI;
Jacob Erlbeck67a44452014-05-19 10:14:58 +02001661 gbcfg.core_mcc = 123;
1662 gbcfg.core_mnc = 456;
Jacob Erlbeck73685282014-05-23 20:48:07 +02001663 gbcfg.core_apn = talloc_zero_size(NULL, 100);
Holger Hans Peter Freytherce1b22e2014-08-04 14:22:13 +02001664 gbcfg.core_apn_size = gprs_str_to_apn(gbcfg.core_apn, 100, "foo.bar");
Jacob Erlbeck9057bc32014-08-12 16:30:30 +02001665 gbcfg.patch_ptmsi = 0;
Jacob Erlbeck7fb42db2014-07-07 10:46:01 +02001666
Holger Hans Peter Freyther99a20d62014-07-07 14:19:10 +02001667 configure_sgsn_peer(&sgsn_peer);
1668 configure_bss_peers(bss_peer, ARRAY_SIZE(bss_peer));
Jacob Erlbeck7fb42db2014-07-07 10:46:01 +02001669
Jacob Erlbeck9a83d7a2014-09-25 11:17:31 +02001670 if (gbproxy_set_patch_filter(&gbcfg.matches[GBPROX_MATCH_PATCHING],
1671 patch_re, &err_msg) != 0) {
Jacob Erlbeck7c101d92014-06-06 18:49:23 +02001672 fprintf(stderr, "Failed to compile RE '%s': %s\n",
Jacob Erlbeck9a83d7a2014-09-25 11:17:31 +02001673 patch_re, err_msg);
Jacob Erlbeck7c101d92014-06-06 18:49:23 +02001674 exit(1);
1675 }
1676
1677
Jacob Erlbeckff0d65a2014-07-09 23:19:11 +02001678 printf("=== %s ===\n", __func__);
Jacob Erlbeck7fb42db2014-07-07 10:46:01 +02001679 printf("--- Initialise SGSN ---\n\n");
1680
Jacob Erlbeckf181f9e2014-08-27 12:44:25 +02001681 connect_sgsn(nsi, &sgsn_peer, SGSN_NSEI);
Jacob Erlbeck7fb42db2014-07-07 10:46:01 +02001682 gprs_dump_nsi(nsi);
1683
1684 printf("--- Initialise BSS 1 ---\n\n");
1685
1686 setup_ns(nsi, &bss_peer[0], 0x1001, 0x1000);
Jacob Erlbeck55ec2bf2014-09-23 14:56:38 +02001687
1688 received_messages = &rcv_list;
1689
Jacob Erlbeck7fb42db2014-07-07 10:46:01 +02001690 setup_bssgp(nsi, &bss_peer[0], 0x1002);
1691 gprs_dump_nsi(nsi);
Jacob Erlbeck7b821d02014-08-08 08:37:37 +02001692 dump_peers(stdout, 0, 0, &gbcfg);
Jacob Erlbeck7fb42db2014-07-07 10:46:01 +02001693
Jacob Erlbeck5f1faa32014-08-21 10:01:30 +02001694 peer = gbproxy_peer_by_nsei(&gbcfg, 0x1000);
Jacob Erlbeck59748e62014-08-11 17:26:21 +02001695 OSMO_ASSERT(peer != NULL);
1696
Jacob Erlbeck55ec2bf2014-09-23 14:56:38 +02001697 OSMO_ASSERT(expect_bssgp_msg(SGSN_NSEI, 0, BSSGP_PDUT_BVC_RESET));
1698
Jacob Erlbeck7fb42db2014-07-07 10:46:01 +02001699 send_bssgp_reset_ack(nsi, &sgsn_peer, 0x1002);
1700
Jacob Erlbeck55ec2bf2014-09-23 14:56:38 +02001701 OSMO_ASSERT(expect_bssgp_msg(0x1000, 0, BSSGP_PDUT_BVC_RESET_ACK));
1702
Jacob Erlbeck299389a2014-08-21 16:34:18 +02001703 send_bssgp_suspend(nsi, &bss_peer[0], 0xccd1758b, &rai_bss);
Jacob Erlbeck55ec2bf2014-09-23 14:56:38 +02001704
1705 OSMO_ASSERT(expect_bssgp_msg(SGSN_NSEI, 0, BSSGP_PDUT_SUSPEND));
1706
Jacob Erlbeck299389a2014-08-21 16:34:18 +02001707 send_bssgp_suspend_ack(nsi, &sgsn_peer, 0xccd1758b, &rai_sgsn);
Jacob Erlbeck7fb42db2014-07-07 10:46:01 +02001708
Jacob Erlbeck55ec2bf2014-09-23 14:56:38 +02001709 OSMO_ASSERT(expect_bssgp_msg(0x1000, 0, BSSGP_PDUT_SUSPEND_ACK));
1710
Holger Hans Peter Freytherb9004592014-08-04 11:26:54 +02001711 dump_global(stdout, 0);
Jacob Erlbeck7b821d02014-08-08 08:37:37 +02001712 dump_peers(stdout, 0, 0, &gbcfg);
Jacob Erlbeck7fb42db2014-07-07 10:46:01 +02001713
Jacob Erlbeck948c07f2014-09-11 15:22:18 +02001714 OSMO_ASSERT(2 == peer->ctrg->ctr[GBPROX_PEER_CTR_RAID_PATCHED_BSS].current);
1715 OSMO_ASSERT(1 == peer->ctrg->ctr[GBPROX_PEER_CTR_RAID_PATCHED_SGSN].current);
1716
Jacob Erlbeck7fb42db2014-07-07 10:46:01 +02001717 printf("--- Send message from BSS 1 to SGSN, BVCI 0x1002 ---\n\n");
1718
Jacob Erlbeckc53f2a62014-08-15 14:56:28 +02001719 send_llc_ul_ui(nsi, "ATTACH REQUEST", &bss_peer[0], 0x1002,
1720 foreign_tlli, &rai_bss, cell_id,
1721 GPRS_SAPI_GMM, 0,
1722 dtap_attach_req, sizeof(dtap_attach_req));
Jacob Erlbeck7fb42db2014-07-07 10:46:01 +02001723
Jacob Erlbeck948c07f2014-09-11 15:22:18 +02001724 OSMO_ASSERT(4 == peer->ctrg->ctr[GBPROX_PEER_CTR_RAID_PATCHED_BSS].current);
Jacob Erlbeck55ec2bf2014-09-23 14:56:38 +02001725 OSMO_ASSERT(expect_gmm_msg(SGSN_NSEI, 0x1002, GSM48_MT_GMM_ATTACH_REQ));
Jacob Erlbeck948c07f2014-09-11 15:22:18 +02001726
Jacob Erlbeckc53f2a62014-08-15 14:56:28 +02001727 send_llc_dl_ui(nsi, "IDENT REQUEST", &sgsn_peer, 0x1002,
1728 foreign_tlli, 0, NULL, 0,
1729 GPRS_SAPI_GMM, 0,
1730 dtap_identity_req, sizeof(dtap_identity_req));
Jacob Erlbeck690768a2014-08-06 15:16:45 +02001731
Jacob Erlbeck55ec2bf2014-09-23 14:56:38 +02001732 OSMO_ASSERT(expect_gmm_msg(0x1000, 0x1002, GSM48_MT_GMM_ID_REQ));
1733
Jacob Erlbeckc53f2a62014-08-15 14:56:28 +02001734 send_llc_ul_ui(nsi, "IDENT RESPONSE", &bss_peer[0], 0x1002,
1735 foreign_tlli, &rai_bss, cell_id,
1736 GPRS_SAPI_GMM, 3,
1737 dtap_identity_resp, sizeof(dtap_identity_resp));
Jacob Erlbeck690768a2014-08-06 15:16:45 +02001738
Jacob Erlbeck55ec2bf2014-09-23 14:56:38 +02001739 OSMO_ASSERT(expect_gmm_msg(SGSN_NSEI, 0x1002, GSM48_MT_GMM_ID_RESP));
1740
Jacob Erlbeck948c07f2014-09-11 15:22:18 +02001741 OSMO_ASSERT(5 == peer->ctrg->ctr[GBPROX_PEER_CTR_RAID_PATCHED_BSS].current);
1742 OSMO_ASSERT(1 == peer->ctrg->ctr[GBPROX_PEER_CTR_RAID_PATCHED_SGSN].current);
1743
Jacob Erlbeckc53f2a62014-08-15 14:56:28 +02001744 send_llc_dl_ui(nsi, "ATTACH ACCEPT", &sgsn_peer, 0x1002,
1745 foreign_tlli, 1, imsi, sizeof(imsi),
1746 GPRS_SAPI_GMM, 1,
1747 dtap_attach_acc, sizeof(dtap_attach_acc));
Jacob Erlbeck7fb42db2014-07-07 10:46:01 +02001748
Jacob Erlbeck55ec2bf2014-09-23 14:56:38 +02001749 OSMO_ASSERT(expect_gmm_msg(0x1000, 0x1002, GSM48_MT_GMM_ATTACH_ACK));
1750
Jacob Erlbeck948c07f2014-09-11 15:22:18 +02001751 OSMO_ASSERT(2 == peer->ctrg->ctr[GBPROX_PEER_CTR_RAID_PATCHED_SGSN].current);
1752
Jacob Erlbeck7fb26c22014-09-04 11:08:50 +02001753 OSMO_ASSERT(gbproxy_peer_by_rai(&gbcfg, convert_ra(&rai_bss)) != NULL);
1754 OSMO_ASSERT(gbproxy_peer_by_rai(&gbcfg, convert_ra(&rai_sgsn)) == NULL);
1755 OSMO_ASSERT(gbproxy_peer_by_rai(&gbcfg, convert_ra(&rai_unknown)) == NULL);
1756
1757 OSMO_ASSERT(gbproxy_peer_by_lai(&gbcfg, convert_ra(&rai_bss)) != NULL);
1758 OSMO_ASSERT(gbproxy_peer_by_lai(&gbcfg, convert_ra(&rai_sgsn)) == NULL);
1759 OSMO_ASSERT(gbproxy_peer_by_lai(&gbcfg, convert_ra(&rai_unknown)) == NULL);
1760
1761 OSMO_ASSERT(gbproxy_peer_by_lac(&gbcfg, convert_ra(&rai_bss)) != NULL);
1762 OSMO_ASSERT(gbproxy_peer_by_lac(&gbcfg, convert_ra(&rai_sgsn)) != NULL);
1763 OSMO_ASSERT(gbproxy_peer_by_lac(&gbcfg, convert_ra(&rai_unknown)) == NULL);
1764
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +02001765 link_info = gbproxy_link_info_by_sgsn_tlli(peer, local_tlli, SGSN_NSEI);
1766 OSMO_ASSERT(link_info);
1767 OSMO_ASSERT(link_info->tlli.assigned == local_tlli);
1768 OSMO_ASSERT(link_info->tlli.current != local_tlli);
1769 OSMO_ASSERT(!link_info->tlli.bss_validated);
1770 OSMO_ASSERT(!link_info->tlli.net_validated);
1771 OSMO_ASSERT(link_info->sgsn_tlli.assigned == local_tlli);
1772 OSMO_ASSERT(link_info->sgsn_tlli.current != local_tlli);
1773 OSMO_ASSERT(!link_info->sgsn_tlli.bss_validated);
1774 OSMO_ASSERT(!link_info->sgsn_tlli.net_validated);
Jacob Erlbeck59748e62014-08-11 17:26:21 +02001775
Jacob Erlbeckc53f2a62014-08-15 14:56:28 +02001776 send_llc_ul_ui(nsi, "ATTACH COMPLETE", &bss_peer[0], 0x1002,
1777 local_tlli, &rai_bss, cell_id,
1778 GPRS_SAPI_GMM, 4,
1779 dtap_attach_complete, sizeof(dtap_attach_complete));
Jacob Erlbeck59748e62014-08-11 17:26:21 +02001780
Jacob Erlbeck55ec2bf2014-09-23 14:56:38 +02001781 OSMO_ASSERT(expect_gmm_msg(SGSN_NSEI, 0x1002, GSM48_MT_GMM_ATTACH_COMPL));
1782
Jacob Erlbeck948c07f2014-09-11 15:22:18 +02001783 OSMO_ASSERT(6 == peer->ctrg->ctr[GBPROX_PEER_CTR_RAID_PATCHED_BSS].current);
1784
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +02001785 link_info = gbproxy_link_info_by_sgsn_tlli(peer, local_tlli, SGSN_NSEI);
1786 OSMO_ASSERT(link_info);
1787 OSMO_ASSERT(link_info->tlli.assigned == local_tlli);
1788 OSMO_ASSERT(link_info->tlli.current != local_tlli);
1789 OSMO_ASSERT(link_info->tlli.bss_validated);
1790 OSMO_ASSERT(!link_info->tlli.net_validated);
1791 OSMO_ASSERT(link_info->sgsn_tlli.assigned == local_tlli);
1792 OSMO_ASSERT(link_info->sgsn_tlli.current != local_tlli);
1793 OSMO_ASSERT(link_info->sgsn_tlli.bss_validated);
1794 OSMO_ASSERT(!link_info->sgsn_tlli.net_validated);
Jacob Erlbeck59748e62014-08-11 17:26:21 +02001795
Jacob Erlbeckaa3e3342014-06-27 11:55:04 +02001796 /* Replace APN (1) */
Jacob Erlbeckc53f2a62014-08-15 14:56:28 +02001797 send_llc_ul_ui(nsi, "ACT PDP CTX REQ (REPLACE APN)", &bss_peer[0], 0x1002,
1798 local_tlli, &rai_bss, cell_id,
1799 GPRS_SAPI_GMM, 3,
1800 dtap_act_pdp_ctx_req, sizeof(dtap_act_pdp_ctx_req));
Jacob Erlbeck7fb42db2014-07-07 10:46:01 +02001801
Jacob Erlbeck55ec2bf2014-09-23 14:56:38 +02001802 OSMO_ASSERT(expect_gmm_msg(SGSN_NSEI, 0x1002, GSM48_MT_GSM_ACT_PDP_REQ));
1803
Jacob Erlbeck948c07f2014-09-11 15:22:18 +02001804 OSMO_ASSERT(7 == peer->ctrg->ctr[GBPROX_PEER_CTR_RAID_PATCHED_BSS].current);
1805
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +02001806 link_info = gbproxy_link_info_by_sgsn_tlli(peer, local_tlli, SGSN_NSEI);
1807 OSMO_ASSERT(link_info);
1808 OSMO_ASSERT(link_info->tlli.assigned == local_tlli);
1809 OSMO_ASSERT(link_info->tlli.current != local_tlli);
1810 OSMO_ASSERT(link_info->tlli.bss_validated);
1811 OSMO_ASSERT(!link_info->tlli.net_validated);
1812 OSMO_ASSERT(link_info->sgsn_tlli.assigned == local_tlli);
1813 OSMO_ASSERT(link_info->sgsn_tlli.current != local_tlli);
1814 OSMO_ASSERT(link_info->sgsn_tlli.bss_validated);
1815 OSMO_ASSERT(!link_info->sgsn_tlli.net_validated);
Jacob Erlbeck59748e62014-08-11 17:26:21 +02001816
Jacob Erlbeckc53f2a62014-08-15 14:56:28 +02001817 send_llc_dl_ui(nsi, "GMM INFO", &sgsn_peer, 0x1002,
1818 local_tlli, 1, imsi, sizeof(imsi),
1819 GPRS_SAPI_GMM, 2,
1820 dtap_gmm_information, sizeof(dtap_gmm_information));
Jacob Erlbeck11669742014-06-06 18:47:36 +02001821
Jacob Erlbeck55ec2bf2014-09-23 14:56:38 +02001822 OSMO_ASSERT(expect_gmm_msg(0x1000, 0x1002, GSM48_MT_GMM_INFO));
1823
Jacob Erlbeck948c07f2014-09-11 15:22:18 +02001824 OSMO_ASSERT(2 == peer->ctrg->ctr[GBPROX_PEER_CTR_RAID_PATCHED_SGSN].current);
1825
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +02001826 link_info = gbproxy_link_info_by_sgsn_tlli(peer, local_tlli, SGSN_NSEI);
1827 OSMO_ASSERT(link_info);
1828 OSMO_ASSERT(link_info->tlli.assigned == 0);
1829 OSMO_ASSERT(link_info->tlli.current == local_tlli);
1830 OSMO_ASSERT(link_info->sgsn_tlli.assigned == 0);
1831 OSMO_ASSERT(link_info->sgsn_tlli.current == local_tlli);
Jacob Erlbeck59748e62014-08-11 17:26:21 +02001832
Jacob Erlbeckaa3e3342014-06-27 11:55:04 +02001833 /* Replace APN (2) */
Jacob Erlbeckc53f2a62014-08-15 14:56:28 +02001834 send_llc_ul_ui(nsi, "ACT PDP CTX REQ (REPLACE APN)", &bss_peer[0], 0x1002,
1835 local_tlli, &rai_bss, cell_id,
1836 GPRS_SAPI_GMM, 3,
1837 dtap_act_pdp_ctx_req, sizeof(dtap_act_pdp_ctx_req));
Jacob Erlbeck7fb42db2014-07-07 10:46:01 +02001838
Jacob Erlbeckc79beec2014-10-10 09:48:12 +02001839 expect_res = expect_gmm_msg(SGSN_NSEI, 0x1002, GSM48_MT_GSM_ACT_PDP_REQ);
1840 OSMO_ASSERT(expect_res != NULL);
1841 OSMO_ASSERT(expect_res->parse_ctx.apn_ie_len == gbcfg.core_apn_size + 2);
Jacob Erlbeck55ec2bf2014-09-23 14:56:38 +02001842
Jacob Erlbeck948c07f2014-09-11 15:22:18 +02001843 OSMO_ASSERT(8 == peer->ctrg->ctr[GBPROX_PEER_CTR_RAID_PATCHED_BSS].current);
1844
Jacob Erlbeck73685282014-05-23 20:48:07 +02001845 gbcfg.core_apn[0] = 0;
1846 gbcfg.core_apn_size = 0;
Jacob Erlbeck7fb42db2014-07-07 10:46:01 +02001847
1848 /* Remove APN */
Jacob Erlbeckc53f2a62014-08-15 14:56:28 +02001849 send_llc_ul_ui(nsi, "ACT PDP CTX REQ (REMOVE APN)", &bss_peer[0], 0x1002,
1850 local_tlli, &rai_bss, cell_id,
1851 GPRS_SAPI_GMM, 3,
1852 dtap_act_pdp_ctx_req, sizeof(dtap_act_pdp_ctx_req));
Jacob Erlbeck7fb42db2014-07-07 10:46:01 +02001853
Jacob Erlbeckc79beec2014-10-10 09:48:12 +02001854 expect_res = expect_gmm_msg(SGSN_NSEI, 0x1002, GSM48_MT_GSM_ACT_PDP_REQ);
1855 OSMO_ASSERT(expect_res != NULL);
1856 OSMO_ASSERT(expect_res->parse_ctx.apn_ie_len == 0);
Jacob Erlbeck55ec2bf2014-09-23 14:56:38 +02001857
Jacob Erlbeck948c07f2014-09-11 15:22:18 +02001858 OSMO_ASSERT(9 == peer->ctrg->ctr[GBPROX_PEER_CTR_RAID_PATCHED_BSS].current);
1859
Jacob Erlbeck7b821d02014-08-08 08:37:37 +02001860 dump_peers(stdout, 0, 0, &gbcfg);
Jacob Erlbeckaa3e3342014-06-27 11:55:04 +02001861
Jacob Erlbeckcf02eb12014-06-19 10:23:50 +02001862 /* Detach */
Jacob Erlbeckc53f2a62014-08-15 14:56:28 +02001863 send_llc_ul_ui(nsi, "DETACH REQ", &bss_peer[0], 0x1002,
1864 local_tlli, &rai_bss, cell_id,
1865 GPRS_SAPI_GMM, 6,
1866 dtap_detach_req, sizeof(dtap_detach_req));
Jacob Erlbeckcf02eb12014-06-19 10:23:50 +02001867
Jacob Erlbeck55ec2bf2014-09-23 14:56:38 +02001868 OSMO_ASSERT(expect_gmm_msg(SGSN_NSEI, 0x1002, GSM48_MT_GMM_DETACH_REQ));
1869
Jacob Erlbeck948c07f2014-09-11 15:22:18 +02001870 OSMO_ASSERT(10 == peer->ctrg->ctr[GBPROX_PEER_CTR_RAID_PATCHED_BSS].current);
1871 OSMO_ASSERT(2 == peer->ctrg->ctr[GBPROX_PEER_CTR_RAID_PATCHED_SGSN].current);
1872
Jacob Erlbeckc53f2a62014-08-15 14:56:28 +02001873 send_llc_dl_ui(nsi, "DETACH ACC", &sgsn_peer, 0x1002,
1874 local_tlli, 1, imsi, sizeof(imsi),
1875 GPRS_SAPI_GMM, 5,
1876 dtap_detach_acc, sizeof(dtap_detach_acc));
Jacob Erlbeckcf02eb12014-06-19 10:23:50 +02001877
Jacob Erlbeck55ec2bf2014-09-23 14:56:38 +02001878 OSMO_ASSERT(expect_gmm_msg(0x1000, 0x1002, GSM48_MT_GMM_DETACH_ACK));
1879
Jacob Erlbeck7b821d02014-08-08 08:37:37 +02001880 dump_peers(stdout, 0, 0, &gbcfg);
Jacob Erlbeckaa3e3342014-06-27 11:55:04 +02001881
1882 printf("--- RA update ---\n\n");
1883
Jacob Erlbeckc53f2a62014-08-15 14:56:28 +02001884 send_llc_ul_ui(nsi, "RA UPD REQ", &bss_peer[0], 0x1002,
1885 foreign_tlli, &rai_bss, 0x7080,
1886 GPRS_SAPI_GMM, 5,
1887 dtap_ra_upd_req, sizeof(dtap_ra_upd_req));
Jacob Erlbeckaa3e3342014-06-27 11:55:04 +02001888
Jacob Erlbeck55ec2bf2014-09-23 14:56:38 +02001889 OSMO_ASSERT(expect_gmm_msg(SGSN_NSEI, 0x1002, GSM48_MT_GMM_RA_UPD_REQ));
1890
Jacob Erlbeck948c07f2014-09-11 15:22:18 +02001891 OSMO_ASSERT(12 == peer->ctrg->ctr[GBPROX_PEER_CTR_RAID_PATCHED_BSS].current);
1892
Jacob Erlbeckc53f2a62014-08-15 14:56:28 +02001893 send_llc_dl_ui(nsi, "RA UPD ACC", &sgsn_peer, 0x1002,
1894 foreign_tlli, 1, imsi, sizeof(imsi),
1895 GPRS_SAPI_GMM, 6,
1896 dtap_ra_upd_acc, sizeof(dtap_ra_upd_acc));
Jacob Erlbeckaa3e3342014-06-27 11:55:04 +02001897
Jacob Erlbeck55ec2bf2014-09-23 14:56:38 +02001898 OSMO_ASSERT(expect_gmm_msg(0x1000, 0x1002, GSM48_MT_GMM_RA_UPD_ACK));
1899
Jacob Erlbeck948c07f2014-09-11 15:22:18 +02001900 OSMO_ASSERT(3 == peer->ctrg->ctr[GBPROX_PEER_CTR_RAID_PATCHED_SGSN].current);
1901
Jacob Erlbeckaa3e3342014-06-27 11:55:04 +02001902 /* Remove APN */
Jacob Erlbeckc53f2a62014-08-15 14:56:28 +02001903 send_llc_ul_ui(nsi, "ACT PDP CTX REQ (REMOVE APN)", &bss_peer[0], 0x1002,
1904 local_tlli, &rai_bss, cell_id,
1905 GPRS_SAPI_GMM, 3,
1906 dtap_act_pdp_ctx_req, sizeof(dtap_act_pdp_ctx_req));
Jacob Erlbeckaa3e3342014-06-27 11:55:04 +02001907
Jacob Erlbeckc79beec2014-10-10 09:48:12 +02001908 expect_res = expect_gmm_msg(SGSN_NSEI, 0x1002, GSM48_MT_GSM_ACT_PDP_REQ);
1909 OSMO_ASSERT(expect_res != NULL);
1910 OSMO_ASSERT(expect_res->parse_ctx.apn_ie_len == 0);
Jacob Erlbeck55ec2bf2014-09-23 14:56:38 +02001911
Jacob Erlbeck948c07f2014-09-11 15:22:18 +02001912 OSMO_ASSERT(13 == peer->ctrg->ctr[GBPROX_PEER_CTR_RAID_PATCHED_BSS].current);
1913
Jacob Erlbeck7b821d02014-08-08 08:37:37 +02001914 dump_peers(stdout, 0, 0, &gbcfg);
Jacob Erlbeckaa3e3342014-06-27 11:55:04 +02001915
Jacob Erlbeck3e23ddf2014-08-11 15:07:37 +02001916 /* Detach (power off -> no Detach Accept) */
Jacob Erlbeckc53f2a62014-08-15 14:56:28 +02001917 send_llc_ul_ui(nsi, "DETACH REQ (PWR OFF)", &bss_peer[0], 0x1002,
1918 local_tlli, &rai_bss, cell_id,
1919 GPRS_SAPI_GMM, 6,
1920 dtap_detach_po_req, sizeof(dtap_detach_po_req));
Jacob Erlbeckaa3e3342014-06-27 11:55:04 +02001921
Jacob Erlbeck55ec2bf2014-09-23 14:56:38 +02001922 OSMO_ASSERT(expect_gmm_msg(SGSN_NSEI, 0x1002, GSM48_MT_GMM_DETACH_REQ));
1923
Jacob Erlbeck948c07f2014-09-11 15:22:18 +02001924 OSMO_ASSERT(14 == peer->ctrg->ctr[GBPROX_PEER_CTR_RAID_PATCHED_BSS].current);
1925
Holger Hans Peter Freytherb9004592014-08-04 11:26:54 +02001926 dump_global(stdout, 0);
Jacob Erlbeck7b821d02014-08-08 08:37:37 +02001927 dump_peers(stdout, 0, 0, &gbcfg);
Jacob Erlbeck7fb42db2014-07-07 10:46:01 +02001928
1929 printf("--- Bad cases ---\n\n");
1930
Jacob Erlbeck991606b2014-09-12 10:33:38 +02001931 /* The RAI in the Attach Request message differs from the RAI in the
1932 * BSSGP message, only patch the latter */
1933
1934 send_llc_ul_ui(nsi, "ATTACH REQUEST (foreign RAI)", &bss_peer[0], 0x1002,
1935 foreign_tlli2, &rai_bss, cell_id,
1936 GPRS_SAPI_GMM, 0,
1937 dtap_attach_req2, sizeof(dtap_attach_req2));
1938
Jacob Erlbeck55ec2bf2014-09-23 14:56:38 +02001939 OSMO_ASSERT(expect_gmm_msg(SGSN_NSEI, 0x1002, GSM48_MT_GMM_ATTACH_REQ));
1940
Jacob Erlbeck948c07f2014-09-11 15:22:18 +02001941 OSMO_ASSERT(15 == peer->ctrg->ctr[GBPROX_PEER_CTR_RAID_PATCHED_BSS].current);
1942
Jacob Erlbeck7c101d92014-06-06 18:49:23 +02001943 printf("TLLI is already detached, shouldn't patch\n");
Jacob Erlbeckc53f2a62014-08-15 14:56:28 +02001944 send_llc_ul_ui(nsi, "ACT PDP CTX REQ", &bss_peer[0], 0x1002,
1945 local_tlli, &rai_bss, cell_id,
1946 GPRS_SAPI_GMM, 3,
1947 dtap_act_pdp_ctx_req, sizeof(dtap_act_pdp_ctx_req));
Jacob Erlbeckcf02eb12014-06-19 10:23:50 +02001948
Jacob Erlbeck55ec2bf2014-09-23 14:56:38 +02001949 OSMO_ASSERT(expect_gmm_msg(SGSN_NSEI, 0x1002, GSM48_MT_GSM_ACT_PDP_REQ));
1950
Jacob Erlbeck006c0382014-05-27 13:49:04 +02001951 printf("Invalid RAI, shouldn't patch\n");
Jacob Erlbeck299389a2014-08-21 16:34:18 +02001952 send_bssgp_suspend_ack(nsi, &sgsn_peer, 0xccd1758b, &rai_unknown);
Jacob Erlbeck7fb42db2014-07-07 10:46:01 +02001953
Jacob Erlbeck55ec2bf2014-09-23 14:56:38 +02001954 /* TODO: The following breaks with the current libosmocore, enable it
1955 * again (and remove the plain expect_msg), when the msgb_bssgph patch
1956 * is integrated */
1957 /* OSMO_ASSERT(expect_bssgp_msg(SGSN_NSEI, 0, BSSGP_PDUT_STATUS)); */
1958 OSMO_ASSERT(expect_msg());
1959
Holger Hans Peter Freytherb9004592014-08-04 11:26:54 +02001960 dump_global(stdout, 0);
Jacob Erlbeck7b821d02014-08-08 08:37:37 +02001961 dump_peers(stdout, 0, 0, &gbcfg);
Jacob Erlbeck7fb42db2014-07-07 10:46:01 +02001962
Jacob Erlbeck55ec2bf2014-09-23 14:56:38 +02001963 OSMO_ASSERT(!expect_msg());
1964 received_messages = NULL;
1965
Jacob Erlbeck9ccc41e2014-09-25 11:21:34 +02001966 gbproxy_clear_patch_filter(&gbcfg.matches[GBPROX_MATCH_PATCHING]);
Holger Hans Peter Freythereece6272014-08-04 15:42:36 +02001967 gbprox_reset(&gbcfg);
Jacob Erlbeck7fb42db2014-07-07 10:46:01 +02001968 gprs_ns_destroy(nsi);
1969 nsi = NULL;
Jacob Erlbeck7fb42db2014-07-07 10:46:01 +02001970}
1971
Jacob Erlbeck04f679b2014-09-18 09:21:20 +02001972static void test_gbproxy_ptmsi_assignment()
1973{
1974 struct gprs_ns_inst *nsi = gprs_ns_instantiate(gprs_ns_callback, NULL);
1975 struct sockaddr_in bss_peer[1] = {{0},};
1976 struct sockaddr_in sgsn_peer= {0};
1977 struct gprs_ra_id rai_bss =
1978 {.mcc = 112, .mnc = 332, .lac = 16464, .rac = 96};
1979 struct gprs_ra_id rai_unknown =
1980 {.mcc = 1, .mnc = 99, .lac = 99, .rac = 96};
1981 uint16_t cell_id = 0x1234;
1982
1983 const uint32_t ptmsi = 0xefe2b700;
1984 const uint32_t local_tlli = 0xefe2b700;
1985
1986 const uint32_t foreign_tlli1 = 0x8000dead;
1987 const uint32_t foreign_tlli2 = 0x8000beef;
1988
1989 const uint8_t imsi1[] = {0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17, 0x18};
1990 const uint8_t imsi2[] = {0x11, 0x12, 0x99, 0x99, 0x99, 0x16, 0x17, 0x18};
1991
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +02001992 struct gbproxy_link_info *link_info, *link_info2;
Jacob Erlbeck04f679b2014-09-18 09:21:20 +02001993 struct gbproxy_peer *peer;
1994 unsigned bss_nu = 0;
1995 unsigned sgsn_nu = 0;
1996
1997 OSMO_ASSERT(local_tlli == gprs_tmsi2tlli(ptmsi, TLLI_LOCAL));
1998
1999 bssgp_nsi = nsi;
2000 gbcfg.nsi = bssgp_nsi;
2001 gbcfg.nsip_sgsn_nsei = SGSN_NSEI;
2002 gbcfg.core_mcc = 0;
2003 gbcfg.core_mnc = 0;
2004 gbcfg.core_apn = talloc_zero_size(NULL, 100);
2005 gbcfg.core_apn_size = gprs_str_to_apn(gbcfg.core_apn, 100, "foo.bar");
2006 gbcfg.patch_ptmsi = 0;
Jacob Erlbeck04f679b2014-09-18 09:21:20 +02002007
2008 configure_sgsn_peer(&sgsn_peer);
2009 configure_bss_peers(bss_peer, ARRAY_SIZE(bss_peer));
2010
2011 printf("=== %s ===\n", __func__);
2012 printf("--- Initialise SGSN ---\n\n");
2013
2014 connect_sgsn(nsi, &sgsn_peer, SGSN_NSEI);
2015
2016 printf("--- Initialise BSS 1 ---\n\n");
2017
2018 setup_ns(nsi, &bss_peer[0], 0x1001, 0x1000);
2019 setup_bssgp(nsi, &bss_peer[0], 0x1002);
2020
2021 peer = gbproxy_peer_by_nsei(&gbcfg, 0x1000);
2022 OSMO_ASSERT(peer != NULL);
2023
2024 send_bssgp_reset_ack(nsi, &sgsn_peer, 0x1002);
2025
2026 gprs_dump_nsi(nsi);
2027 dump_global(stdout, 0);
2028 dump_peers(stdout, 0, 0, &gbcfg);
2029
2030 printf("--- Establish first LLC connection ---\n\n");
2031
2032 send_llc_ul_ui(nsi, "ATTACH REQUEST", &bss_peer[0], 0x1002,
2033 foreign_tlli1, &rai_unknown, cell_id,
2034 GPRS_SAPI_GMM, bss_nu++,
2035 dtap_attach_req, sizeof(dtap_attach_req));
2036
2037 dump_peers(stdout, 0, 0, &gbcfg);
2038
2039 send_llc_dl_ui(nsi, "IDENT REQUEST", &sgsn_peer, 0x1002,
2040 foreign_tlli1, 0, NULL, 0,
2041 GPRS_SAPI_GMM, sgsn_nu++,
2042 dtap_identity_req, sizeof(dtap_identity_req));
2043
2044 dump_peers(stdout, 0, 0, &gbcfg);
2045
2046 send_llc_ul_ui(nsi, "IDENT RESPONSE", &bss_peer[0], 0x1002,
2047 foreign_tlli1, &rai_bss, cell_id,
2048 GPRS_SAPI_GMM, bss_nu++,
2049 dtap_identity_resp, sizeof(dtap_identity_resp));
2050
2051 dump_peers(stdout, 0, 0, &gbcfg);
2052
2053 send_llc_dl_ui(nsi, "ATTACH ACCEPT", &sgsn_peer, 0x1002,
2054 foreign_tlli1, 1, imsi1, sizeof(imsi1),
2055 GPRS_SAPI_GMM, sgsn_nu++,
2056 dtap_attach_acc, sizeof(dtap_attach_acc));
2057
2058 dump_peers(stdout, 0, 0, &gbcfg);
2059
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +02002060 link_info = gbproxy_link_info_by_tlli(peer, foreign_tlli1);
2061 link_info2 = gbproxy_link_info_by_tlli(peer, local_tlli);
2062 OSMO_ASSERT(link_info);
2063 OSMO_ASSERT(link_info == link_info2);
2064 OSMO_ASSERT(link_info->tlli.assigned == local_tlli);
2065 OSMO_ASSERT(link_info->tlli.current == foreign_tlli1);
2066 OSMO_ASSERT(!link_info->tlli.bss_validated);
2067 OSMO_ASSERT(!link_info->tlli.net_validated);
2068 OSMO_ASSERT(link_info->tlli.ptmsi == ptmsi);
Jacob Erlbeck04f679b2014-09-18 09:21:20 +02002069
2070 send_llc_ul_ui(nsi, "ATTACH COMPLETE", &bss_peer[0], 0x1002,
2071 local_tlli, &rai_bss, cell_id,
2072 GPRS_SAPI_GMM, bss_nu++,
2073 dtap_attach_complete, sizeof(dtap_attach_complete));
2074
2075 dump_peers(stdout, 0, 0, &gbcfg);
2076
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +02002077 link_info = gbproxy_link_info_by_tlli(peer, local_tlli);
2078 OSMO_ASSERT(link_info);
2079 OSMO_ASSERT(link_info->tlli.assigned == local_tlli);
2080 OSMO_ASSERT(link_info->tlli.current == foreign_tlli1);
2081 OSMO_ASSERT(link_info->tlli.bss_validated);
2082 OSMO_ASSERT(!link_info->tlli.net_validated);
2083 OSMO_ASSERT(link_info->tlli.ptmsi == ptmsi);
Jacob Erlbeck04f679b2014-09-18 09:21:20 +02002084
2085
2086 send_llc_dl_ui(nsi, "GMM INFO", &sgsn_peer, 0x1002,
2087 local_tlli, 1, imsi1, sizeof(imsi1),
2088 GPRS_SAPI_GMM, sgsn_nu++,
2089 dtap_gmm_information, sizeof(dtap_gmm_information));
2090
2091 dump_peers(stdout, 0, 0, &gbcfg);
2092
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +02002093 link_info = gbproxy_link_info_by_imsi(peer, imsi1, ARRAY_SIZE(imsi1));
2094 OSMO_ASSERT(link_info);
2095 OSMO_ASSERT(link_info->tlli.ptmsi == ptmsi);
2096 OSMO_ASSERT(!gbproxy_link_info_by_imsi(peer, imsi2, ARRAY_SIZE(imsi2)));
Jacob Erlbeck04f679b2014-09-18 09:21:20 +02002097
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +02002098 link_info2 = gbproxy_link_info_by_tlli(peer, local_tlli);
2099 OSMO_ASSERT(link_info == link_info2);
2100 OSMO_ASSERT(link_info->tlli.assigned == 0);
2101 OSMO_ASSERT(link_info->tlli.current == local_tlli);
2102 OSMO_ASSERT(link_info->tlli.ptmsi == ptmsi);
Jacob Erlbeck04f679b2014-09-18 09:21:20 +02002103
2104 printf("--- Establish second LLC connection with the same P-TMSI ---\n\n");
2105
2106 send_llc_ul_ui(nsi, "ATTACH REQUEST", &bss_peer[0], 0x1002,
2107 foreign_tlli2, &rai_unknown, cell_id,
2108 GPRS_SAPI_GMM, bss_nu++,
2109 dtap_attach_req, sizeof(dtap_attach_req));
2110
2111 dump_peers(stdout, 0, 0, &gbcfg);
2112
2113 send_llc_dl_ui(nsi, "IDENT REQUEST", &sgsn_peer, 0x1002,
2114 foreign_tlli2, 0, NULL, 0,
2115 GPRS_SAPI_GMM, sgsn_nu++,
2116 dtap_identity_req, sizeof(dtap_identity_req));
2117
2118 dump_peers(stdout, 0, 0, &gbcfg);
2119
2120 send_llc_ul_ui(nsi, "IDENT RESPONSE", &bss_peer[0], 0x1002,
2121 foreign_tlli2, &rai_bss, cell_id,
2122 GPRS_SAPI_GMM, bss_nu++,
2123 dtap_identity2_resp, sizeof(dtap_identity2_resp));
2124
2125 dump_peers(stdout, 0, 0, &gbcfg);
2126
2127 send_llc_dl_ui(nsi, "ATTACH ACCEPT", &sgsn_peer, 0x1002,
2128 foreign_tlli2, 1, imsi2, sizeof(imsi2),
2129 GPRS_SAPI_GMM, sgsn_nu++,
2130 dtap_attach_acc, sizeof(dtap_attach_acc));
2131
2132 dump_peers(stdout, 0, 0, &gbcfg);
2133
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +02002134 link_info = gbproxy_link_info_by_tlli(peer, foreign_tlli2);
2135 link_info2 = gbproxy_link_info_by_tlli(peer, local_tlli);
2136 OSMO_ASSERT(link_info);
2137 OSMO_ASSERT(link_info == link_info2);
2138 OSMO_ASSERT(link_info->tlli.assigned == local_tlli);
2139 OSMO_ASSERT(link_info->tlli.current == foreign_tlli2);
2140 OSMO_ASSERT(!link_info->tlli.bss_validated);
2141 OSMO_ASSERT(!link_info->tlli.net_validated);
2142 OSMO_ASSERT(link_info->tlli.ptmsi == ptmsi);
Jacob Erlbeck04f679b2014-09-18 09:21:20 +02002143
2144 send_llc_ul_ui(nsi, "ATTACH COMPLETE", &bss_peer[0], 0x1002,
2145 local_tlli, &rai_bss, cell_id,
2146 GPRS_SAPI_GMM, bss_nu++,
2147 dtap_attach_complete, sizeof(dtap_attach_complete));
2148
2149 dump_peers(stdout, 0, 0, &gbcfg);
2150
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +02002151 link_info = gbproxy_link_info_by_tlli(peer, local_tlli);
2152 OSMO_ASSERT(link_info);
2153 OSMO_ASSERT(link_info->tlli.assigned == local_tlli);
2154 OSMO_ASSERT(link_info->tlli.current == foreign_tlli2);
2155 OSMO_ASSERT(link_info->tlli.bss_validated);
2156 OSMO_ASSERT(!link_info->tlli.net_validated);
2157 OSMO_ASSERT(link_info->tlli.ptmsi == ptmsi);
Jacob Erlbeck04f679b2014-09-18 09:21:20 +02002158
2159 send_llc_dl_ui(nsi, "GMM INFO", &sgsn_peer, 0x1002,
2160 local_tlli, 1, imsi2, sizeof(imsi2),
2161 GPRS_SAPI_GMM, sgsn_nu++,
2162 dtap_gmm_information, sizeof(dtap_gmm_information));
2163
2164 dump_peers(stdout, 0, 0, &gbcfg);
2165
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +02002166 link_info = gbproxy_link_info_by_imsi(peer, imsi2, ARRAY_SIZE(imsi2));
2167 OSMO_ASSERT(link_info);
2168 OSMO_ASSERT(link_info->tlli.ptmsi == ptmsi);
2169 OSMO_ASSERT(!gbproxy_link_info_by_imsi(peer, imsi1, ARRAY_SIZE(imsi1)));
Jacob Erlbeck04f679b2014-09-18 09:21:20 +02002170
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +02002171 link_info2 = gbproxy_link_info_by_tlli(peer, local_tlli);
2172 OSMO_ASSERT(link_info == link_info2);
2173 OSMO_ASSERT(link_info->tlli.assigned == 0);
2174 OSMO_ASSERT(link_info->tlli.current == local_tlli);
2175 OSMO_ASSERT(link_info->tlli.ptmsi == ptmsi);
Jacob Erlbeck04f679b2014-09-18 09:21:20 +02002176
2177 dump_global(stdout, 0);
2178
2179 gbprox_reset(&gbcfg);
2180 gprs_ns_destroy(nsi);
2181 nsi = NULL;
Daniel Willmannd1554ec2015-10-12 19:36:34 +02002182
2183 cleanup_test();
Jacob Erlbeck04f679b2014-09-18 09:21:20 +02002184}
2185
Jacob Erlbeck6bd7ded2014-08-15 17:20:06 +02002186static void test_gbproxy_ptmsi_patching()
2187{
2188 struct gprs_ns_inst *nsi = gprs_ns_instantiate(gprs_ns_callback, NULL);
2189 struct sockaddr_in bss_peer[1] = {{0},};
2190 struct sockaddr_in sgsn_peer= {0};
2191 struct gprs_ra_id rai_bss =
2192 {.mcc = 112, .mnc = 332, .lac = 16464, .rac = 96};
2193 struct gprs_ra_id rai_sgsn =
2194 {.mcc = 123, .mnc = 456, .lac = 16464, .rac = 96};
Jacob Erlbeck299389a2014-08-21 16:34:18 +02002195 struct gprs_ra_id rai_wrong_mcc_sgsn =
2196 {.mcc = 999, .mnc = 456, .lac = 16464, .rac = 96};
Jacob Erlbeck6bd7ded2014-08-15 17:20:06 +02002197 struct gprs_ra_id rai_unknown =
2198 {.mcc = 1, .mnc = 99, .lac = 99, .rac = 96};
2199 uint16_t cell_id = 0x1234;
2200
2201 const uint32_t sgsn_ptmsi = 0xefe2b700;
Jacob Erlbeck52f070a2014-09-04 13:45:56 +02002202 const uint32_t sgsn_ptmsi2 = 0xe0987654;
2203 const uint32_t sgsn_ptmsi3 = 0xe0543210;
Jacob Erlbeck6bd7ded2014-08-15 17:20:06 +02002204 const uint32_t local_sgsn_tlli = 0xefe2b700;
Jacob Erlbeck52f070a2014-09-04 13:45:56 +02002205 const uint32_t local_sgsn_tlli2 = 0xe0987654;
2206 const uint32_t local_sgsn_tlli3 = 0xe0543210;
Daniel Willmann537d4802015-10-12 19:36:35 +02002207 const uint32_t random_sgsn_tlli = 0x78dead00;
Jacob Erlbeck7fb26c22014-09-04 11:08:50 +02002208 const uint32_t unknown_sgsn_tlli = 0xeebadbad;
Jacob Erlbeck6bd7ded2014-08-15 17:20:06 +02002209
Daniel Willmann537d4802015-10-12 19:36:35 +02002210 const uint32_t bss_ptmsi = 0xc0dead01;
2211 const uint32_t bss_ptmsi2 = 0xc0dead02;
2212 const uint32_t bss_ptmsi3 = 0xc0dead03;
2213 const uint32_t local_bss_tlli = 0xc0dead01;
2214 const uint32_t local_bss_tlli2 = 0xc0dead02;
2215 const uint32_t local_bss_tlli3 = 0xc0dead03;
Jacob Erlbeck6bd7ded2014-08-15 17:20:06 +02002216 const uint32_t foreign_bss_tlli = 0x8000dead;
2217
Jacob Erlbeck7fb26c22014-09-04 11:08:50 +02002218
Jacob Erlbeck6bd7ded2014-08-15 17:20:06 +02002219 const uint8_t imsi[] = {0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17, 0x18};
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +02002220 struct gbproxy_link_info *link_info;
Jacob Erlbeck6bd7ded2014-08-15 17:20:06 +02002221 struct gbproxy_peer *peer;
2222 unsigned bss_nu = 0;
2223 unsigned sgsn_nu = 0;
Jacob Erlbeckc37ef6c2014-09-30 13:49:43 +02002224 int old_ctr;
Jacob Erlbeck6bd7ded2014-08-15 17:20:06 +02002225
2226 OSMO_ASSERT(local_sgsn_tlli == gprs_tmsi2tlli(sgsn_ptmsi, TLLI_LOCAL));
Jacob Erlbeck52f070a2014-09-04 13:45:56 +02002227 OSMO_ASSERT(local_sgsn_tlli2 == gprs_tmsi2tlli(sgsn_ptmsi2, TLLI_LOCAL));
2228 OSMO_ASSERT(local_sgsn_tlli3 == gprs_tmsi2tlli(sgsn_ptmsi3, TLLI_LOCAL));
2229 OSMO_ASSERT(local_bss_tlli == gprs_tmsi2tlli(bss_ptmsi, TLLI_LOCAL));
2230 OSMO_ASSERT(local_bss_tlli2 == gprs_tmsi2tlli(bss_ptmsi2, TLLI_LOCAL));
2231 OSMO_ASSERT(local_bss_tlli3 == gprs_tmsi2tlli(bss_ptmsi3, TLLI_LOCAL));
Jacob Erlbeck6bd7ded2014-08-15 17:20:06 +02002232
2233 bssgp_nsi = nsi;
2234 gbcfg.nsi = bssgp_nsi;
2235 gbcfg.nsip_sgsn_nsei = SGSN_NSEI;
2236 gbcfg.core_mcc = 123;
2237 gbcfg.core_mnc = 456;
2238 gbcfg.core_apn = talloc_zero_size(NULL, 100);
2239 gbcfg.core_apn_size = gprs_str_to_apn(gbcfg.core_apn, 100, "foo.bar");
2240 gbcfg.patch_ptmsi = 1;
Jacob Erlbeck6bd7ded2014-08-15 17:20:06 +02002241
2242 configure_sgsn_peer(&sgsn_peer);
2243 configure_bss_peers(bss_peer, ARRAY_SIZE(bss_peer));
2244
2245 printf("=== %s ===\n", __func__);
2246 printf("--- Initialise SGSN ---\n\n");
2247
Jacob Erlbeckf181f9e2014-08-27 12:44:25 +02002248 connect_sgsn(nsi, &sgsn_peer, SGSN_NSEI);
Jacob Erlbeck6bd7ded2014-08-15 17:20:06 +02002249
2250 printf("--- Initialise BSS 1 ---\n\n");
2251
2252 setup_ns(nsi, &bss_peer[0], 0x1001, 0x1000);
2253 setup_bssgp(nsi, &bss_peer[0], 0x1002);
2254
Jacob Erlbeck5f1faa32014-08-21 10:01:30 +02002255 peer = gbproxy_peer_by_nsei(&gbcfg, 0x1000);
Jacob Erlbeck6bd7ded2014-08-15 17:20:06 +02002256 OSMO_ASSERT(peer != NULL);
2257
2258 send_bssgp_reset_ack(nsi, &sgsn_peer, 0x1002);
2259
Jacob Erlbeck6bd7ded2014-08-15 17:20:06 +02002260 gprs_dump_nsi(nsi);
2261 dump_global(stdout, 0);
2262 dump_peers(stdout, 0, 0, &gbcfg);
2263
2264 printf("--- Send message from BSS 1 to SGSN, BVCI 0x1002 ---\n\n");
2265
2266 send_llc_ul_ui(nsi, "ATTACH REQUEST", &bss_peer[0], 0x1002,
2267 foreign_bss_tlli, &rai_unknown, cell_id,
2268 GPRS_SAPI_GMM, bss_nu++,
2269 dtap_attach_req, sizeof(dtap_attach_req));
2270
2271 dump_peers(stdout, 0, 0, &gbcfg);
2272
2273 send_llc_dl_ui(nsi, "IDENT REQUEST", &sgsn_peer, 0x1002,
2274 random_sgsn_tlli, 0, NULL, 0,
2275 GPRS_SAPI_GMM, sgsn_nu++,
2276 dtap_identity_req, sizeof(dtap_identity_req));
2277
2278 dump_peers(stdout, 0, 0, &gbcfg);
2279
2280 send_llc_ul_ui(nsi, "IDENT RESPONSE", &bss_peer[0], 0x1002,
2281 foreign_bss_tlli, &rai_bss, cell_id,
2282 GPRS_SAPI_GMM, bss_nu++,
2283 dtap_identity_resp, sizeof(dtap_identity_resp));
2284
2285 dump_peers(stdout, 0, 0, &gbcfg);
2286
2287 send_llc_dl_ui(nsi, "ATTACH ACCEPT", &sgsn_peer, 0x1002,
2288 random_sgsn_tlli, 1, imsi, sizeof(imsi),
2289 GPRS_SAPI_GMM, sgsn_nu++,
2290 dtap_attach_acc, sizeof(dtap_attach_acc));
2291
2292 dump_peers(stdout, 0, 0, &gbcfg);
2293
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +02002294 link_info = gbproxy_link_info_by_sgsn_tlli(peer, random_sgsn_tlli, SGSN_NSEI);
2295 OSMO_ASSERT(link_info);
2296 OSMO_ASSERT(link_info->tlli.assigned == local_bss_tlli);
2297 OSMO_ASSERT(link_info->tlli.current == foreign_bss_tlli);
2298 OSMO_ASSERT(!link_info->tlli.bss_validated);
2299 OSMO_ASSERT(!link_info->tlli.net_validated);
2300 OSMO_ASSERT(link_info->tlli.ptmsi == bss_ptmsi);
2301 OSMO_ASSERT(link_info->sgsn_tlli.assigned == local_sgsn_tlli);
2302 OSMO_ASSERT(link_info->sgsn_tlli.current == random_sgsn_tlli);
2303 OSMO_ASSERT(!link_info->sgsn_tlli.bss_validated);
2304 OSMO_ASSERT(!link_info->sgsn_tlli.net_validated);
2305 OSMO_ASSERT(link_info->sgsn_tlli.ptmsi == sgsn_ptmsi);
Jacob Erlbeck6bd7ded2014-08-15 17:20:06 +02002306
2307 send_llc_ul_ui(nsi, "ATTACH COMPLETE", &bss_peer[0], 0x1002,
2308 local_bss_tlli, &rai_bss, cell_id,
2309 GPRS_SAPI_GMM, bss_nu++,
2310 dtap_attach_complete, sizeof(dtap_attach_complete));
2311
2312 dump_peers(stdout, 0, 0, &gbcfg);
2313
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +02002314 link_info = gbproxy_link_info_by_sgsn_tlli(peer, local_sgsn_tlli, SGSN_NSEI);
2315 OSMO_ASSERT(link_info);
2316 OSMO_ASSERT(link_info->tlli.assigned == local_bss_tlli);
2317 OSMO_ASSERT(link_info->tlli.current == foreign_bss_tlli);
2318 OSMO_ASSERT(link_info->tlli.bss_validated);
2319 OSMO_ASSERT(!link_info->tlli.net_validated);
2320 OSMO_ASSERT(link_info->sgsn_tlli.assigned == local_sgsn_tlli);
2321 OSMO_ASSERT(link_info->sgsn_tlli.current == random_sgsn_tlli);
2322 OSMO_ASSERT(link_info->sgsn_tlli.bss_validated);
2323 OSMO_ASSERT(!link_info->sgsn_tlli.net_validated);
Jacob Erlbeck6bd7ded2014-08-15 17:20:06 +02002324
2325 send_llc_dl_ui(nsi, "GMM INFO", &sgsn_peer, 0x1002,
2326 local_sgsn_tlli, 1, imsi, sizeof(imsi),
2327 GPRS_SAPI_GMM, sgsn_nu++,
2328 dtap_gmm_information, sizeof(dtap_gmm_information));
2329
2330 dump_peers(stdout, 0, 0, &gbcfg);
2331
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +02002332 link_info = gbproxy_link_info_by_sgsn_tlli(peer, local_sgsn_tlli, SGSN_NSEI);
2333 OSMO_ASSERT(link_info);
2334 OSMO_ASSERT(link_info->tlli.current == local_bss_tlli);
2335 OSMO_ASSERT(link_info->tlli.assigned == 0);
2336 OSMO_ASSERT(link_info->sgsn_tlli.current == local_sgsn_tlli);
2337 OSMO_ASSERT(link_info->sgsn_tlli.assigned == 0);
Jacob Erlbeck6bd7ded2014-08-15 17:20:06 +02002338
Jacob Erlbeck82add782014-09-05 18:08:12 +02002339 send_llc_ul_ui(nsi, "ACT PDP CTX REQ (REPLACE APN)", &bss_peer[0], 0x1002,
2340 local_bss_tlli, &rai_bss, cell_id,
2341 GPRS_SAPI_GMM, bss_nu++,
2342 dtap_act_pdp_ctx_req, sizeof(dtap_act_pdp_ctx_req));
2343
2344 dump_peers(stdout, 0, 0, &gbcfg);
2345
Jacob Erlbeck6bd7ded2014-08-15 17:20:06 +02002346 /* Non-DTAP */
2347 send_bssgp_ul_unitdata(nsi, "XID (UL)", &bss_peer[0], 0x1002,
2348 local_bss_tlli, &rai_bss, cell_id,
2349 llc_u_xid_ul, sizeof(llc_u_xid_ul));
2350
2351 send_bssgp_dl_unitdata(nsi, "XID (DL)", &sgsn_peer, 0x1002,
2352 local_sgsn_tlli, 1, imsi, sizeof(imsi),
2353 llc_u_xid_dl, sizeof(llc_u_xid_dl));
2354
2355 send_bssgp_ul_unitdata(nsi, "LL11 DNS QUERY (UL)", &bss_peer[0], 0x1002,
2356 local_bss_tlli, &rai_bss, cell_id,
2357 llc_ui_ll11_dns_query_ul,
2358 sizeof(llc_ui_ll11_dns_query_ul));
2359
2360 send_bssgp_dl_unitdata(nsi, "LL11 DNS RESP (DL)", &sgsn_peer, 0x1002,
2361 local_sgsn_tlli, 1, imsi, sizeof(imsi),
2362 llc_ui_ll11_dns_resp_dl,
2363 sizeof(llc_ui_ll11_dns_resp_dl));
2364
2365 dump_peers(stdout, 0, 0, &gbcfg);
2366
Jacob Erlbeck52f070a2014-09-04 13:45:56 +02002367 /* Repeated RA Update Requests */
2368 send_llc_ul_ui(nsi, "RA UPD REQ (P-TMSI 2)", &bss_peer[0], 0x1002,
2369 local_bss_tlli, &rai_bss, 0x7080,
2370 GPRS_SAPI_GMM, bss_nu++,
2371 dtap_ra_upd_req, sizeof(dtap_ra_upd_req));
2372
2373 send_llc_dl_ui(nsi, "RA UDP ACC (P-TMSI 2)", &sgsn_peer, 0x1002,
2374 local_sgsn_tlli, 1, imsi, sizeof(imsi),
2375 GPRS_SAPI_GMM, sgsn_nu++,
2376 dtap_ra_upd_acc2, sizeof(dtap_ra_upd_acc2));
2377
2378 dump_peers(stdout, 0, 0, &gbcfg);
2379
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +02002380 OSMO_ASSERT(gbproxy_link_info_by_sgsn_tlli(peer, local_sgsn_tlli2, SGSN_NSEI) != NULL);
2381 link_info = gbproxy_link_info_by_sgsn_tlli(peer, local_sgsn_tlli, SGSN_NSEI);
2382 OSMO_ASSERT(link_info);
2383 OSMO_ASSERT(link_info->tlli.assigned == local_bss_tlli2);
2384 OSMO_ASSERT(link_info->tlli.current == local_bss_tlli);
2385 OSMO_ASSERT(!link_info->tlli.bss_validated);
2386 OSMO_ASSERT(!link_info->tlli.net_validated);
2387 OSMO_ASSERT(link_info->tlli.ptmsi == bss_ptmsi2);
2388 OSMO_ASSERT(link_info->sgsn_tlli.assigned == local_sgsn_tlli2);
2389 OSMO_ASSERT(link_info->sgsn_tlli.current == local_sgsn_tlli);
2390 OSMO_ASSERT(!link_info->sgsn_tlli.bss_validated);
2391 OSMO_ASSERT(!link_info->sgsn_tlli.net_validated);
2392 OSMO_ASSERT(link_info->sgsn_tlli.ptmsi == sgsn_ptmsi2);
Jacob Erlbeck52f070a2014-09-04 13:45:56 +02002393
2394 send_llc_ul_ui(nsi, "RA UPD REQ (P-TMSI 3)", &bss_peer[0], 0x1002,
2395 local_bss_tlli2, &rai_bss, 0x7080,
2396 GPRS_SAPI_GMM, bss_nu++,
2397 dtap_ra_upd_req, sizeof(dtap_ra_upd_req));
2398
2399 send_llc_dl_ui(nsi, "RA UDP ACC (P-TMSI 3)", &sgsn_peer, 0x1002,
2400 local_sgsn_tlli2, 1, imsi, sizeof(imsi),
2401 GPRS_SAPI_GMM, sgsn_nu++,
2402 dtap_ra_upd_acc3, sizeof(dtap_ra_upd_acc3));
2403
2404 dump_peers(stdout, 0, 0, &gbcfg);
2405
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +02002406 OSMO_ASSERT(gbproxy_link_info_by_sgsn_tlli(peer, local_sgsn_tlli2, SGSN_NSEI) == NULL);
2407 OSMO_ASSERT(gbproxy_link_info_by_sgsn_tlli(peer, local_sgsn_tlli3, SGSN_NSEI) != NULL);
2408 link_info = gbproxy_link_info_by_sgsn_tlli(peer, local_sgsn_tlli, SGSN_NSEI);
2409 OSMO_ASSERT(link_info);
2410 OSMO_ASSERT(link_info->tlli.assigned == local_bss_tlli3);
2411 OSMO_ASSERT(link_info->tlli.current == local_bss_tlli);
2412 OSMO_ASSERT(!link_info->tlli.bss_validated);
2413 OSMO_ASSERT(!link_info->tlli.net_validated);
2414 OSMO_ASSERT(link_info->tlli.ptmsi == bss_ptmsi3);
2415 OSMO_ASSERT(link_info->sgsn_tlli.assigned == local_sgsn_tlli3);
2416 OSMO_ASSERT(link_info->sgsn_tlli.current == local_sgsn_tlli);
2417 OSMO_ASSERT(!link_info->sgsn_tlli.bss_validated);
2418 OSMO_ASSERT(!link_info->sgsn_tlli.net_validated);
2419 OSMO_ASSERT(link_info->sgsn_tlli.ptmsi == sgsn_ptmsi3);
Jacob Erlbeck52f070a2014-09-04 13:45:56 +02002420
2421 send_llc_ul_ui(nsi, "RA UPD COMPLETE", &bss_peer[0], 0x1002,
2422 local_bss_tlli3, &rai_bss, 0x7080,
2423 GPRS_SAPI_GMM, bss_nu++,
2424 dtap_ra_upd_complete, sizeof(dtap_ra_upd_complete));
2425
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +02002426 link_info = gbproxy_link_info_by_tlli(peer, local_bss_tlli3);
Jacob Erlbeck52f070a2014-09-04 13:45:56 +02002427
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +02002428 OSMO_ASSERT(link_info);
2429 OSMO_ASSERT(link_info->tlli.bss_validated);
2430 OSMO_ASSERT(!link_info->tlli.net_validated);
2431 OSMO_ASSERT(link_info->sgsn_tlli.bss_validated);
2432 OSMO_ASSERT(!link_info->sgsn_tlli.net_validated);
Jacob Erlbeck52f070a2014-09-04 13:45:56 +02002433
2434 send_llc_dl_ui(nsi, "GMM INFO", &sgsn_peer, 0x1002,
2435 local_sgsn_tlli3, 1, imsi, sizeof(imsi),
2436 GPRS_SAPI_GMM, sgsn_nu++,
2437 dtap_gmm_information, sizeof(dtap_gmm_information));
2438
2439 dump_peers(stdout, 0, 0, &gbcfg);
2440
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +02002441 link_info = gbproxy_link_info_by_sgsn_tlli(peer, local_sgsn_tlli3, SGSN_NSEI);
2442 OSMO_ASSERT(link_info);
2443 OSMO_ASSERT(link_info->tlli.current == local_bss_tlli3);
2444 OSMO_ASSERT(link_info->tlli.assigned == 0);
2445 OSMO_ASSERT(link_info->sgsn_tlli.current == local_sgsn_tlli3);
2446 OSMO_ASSERT(link_info->sgsn_tlli.assigned == 0);
Jacob Erlbeck52f070a2014-09-04 13:45:56 +02002447
Jacob Erlbeck299389a2014-08-21 16:34:18 +02002448 /* Other messages */
2449 send_bssgp_llc_discarded(nsi, &bss_peer[0], 0x1002,
Jacob Erlbeck52f070a2014-09-04 13:45:56 +02002450 local_bss_tlli3, 1, 12);
Jacob Erlbeck299389a2014-08-21 16:34:18 +02002451
2452 dump_peers(stdout, 0, 0, &gbcfg);
2453
Jacob Erlbeck52f070a2014-09-04 13:45:56 +02002454 send_bssgp_suspend(nsi, &bss_peer[0], local_bss_tlli3, &rai_bss);
Jacob Erlbeck299389a2014-08-21 16:34:18 +02002455
2456 dump_peers(stdout, 0, 0, &gbcfg);
2457
Jacob Erlbeck52f070a2014-09-04 13:45:56 +02002458 send_bssgp_suspend_ack(nsi, &sgsn_peer, local_sgsn_tlli3, &rai_sgsn);
Jacob Erlbeck299389a2014-08-21 16:34:18 +02002459
2460 dump_peers(stdout, 0, 0, &gbcfg);
2461
Jacob Erlbeckc37ef6c2014-09-30 13:49:43 +02002462 old_ctr = peer->ctrg->ctr[GBPROX_PEER_CTR_PTMSI_PATCHED_SGSN].current;
2463
2464 send_bssgp_paging(nsi, &sgsn_peer, imsi, sizeof(imsi), &rai_bss, sgsn_ptmsi3);
2465
2466 dump_peers(stdout, 0, 0, &gbcfg);
2467
2468 OSMO_ASSERT(old_ctr + 1 ==
2469 peer->ctrg->ctr[GBPROX_PEER_CTR_PTMSI_PATCHED_SGSN].current);
2470
Jacob Erlbeck299389a2014-08-21 16:34:18 +02002471 /* Bad case: Invalid BVCI */
2472 send_bssgp_llc_discarded(nsi, &bss_peer[0], 0xeee1,
Jacob Erlbeck52f070a2014-09-04 13:45:56 +02002473 local_bss_tlli3, 1, 12);
Jacob Erlbeck299389a2014-08-21 16:34:18 +02002474 dump_global(stdout, 0);
2475
2476 /* Bad case: Invalid RAI */
Jacob Erlbeck52f070a2014-09-04 13:45:56 +02002477 send_bssgp_suspend_ack(nsi, &sgsn_peer, local_sgsn_tlli3, &rai_unknown);
Jacob Erlbeck299389a2014-08-21 16:34:18 +02002478
2479 dump_global(stdout, 0);
2480
2481 /* Bad case: Invalid MCC (LAC ok) */
Jacob Erlbeck52f070a2014-09-04 13:45:56 +02002482 send_bssgp_suspend_ack(nsi, &sgsn_peer, local_sgsn_tlli3,
Jacob Erlbeck299389a2014-08-21 16:34:18 +02002483 &rai_wrong_mcc_sgsn);
2484
2485 dump_global(stdout, 0);
2486
Jacob Erlbeck7fb26c22014-09-04 11:08:50 +02002487 /* Bad case: Invalid TLLI from SGSN (IMSI unknown) */
2488 send_llc_dl_ui(nsi, "GMM INFO", &sgsn_peer, 0x1002,
2489 unknown_sgsn_tlli, 1, NULL, 0,
2490 GPRS_SAPI_GMM, 2,
2491 dtap_gmm_information, sizeof(dtap_gmm_information));
2492
2493 /* Bad case: Invalid TLLI from SGSN (IMSI known) */
2494 send_llc_dl_ui(nsi, "GMM INFO", &sgsn_peer, 0x1002,
2495 unknown_sgsn_tlli, 1, imsi, sizeof(imsi),
2496 GPRS_SAPI_GMM, 3,
2497 dtap_gmm_information, sizeof(dtap_gmm_information));
2498
Jacob Erlbeck6bd7ded2014-08-15 17:20:06 +02002499 /* Detach */
2500 send_llc_ul_ui(nsi, "DETACH REQ", &bss_peer[0], 0x1002,
Jacob Erlbeck52f070a2014-09-04 13:45:56 +02002501 local_bss_tlli3, &rai_bss, cell_id,
Jacob Erlbeck6bd7ded2014-08-15 17:20:06 +02002502 GPRS_SAPI_GMM, bss_nu++,
2503 dtap_detach_req, sizeof(dtap_detach_req));
2504
2505 dump_peers(stdout, 0, 0, &gbcfg);
2506
2507 send_llc_dl_ui(nsi, "DETACH ACC", &sgsn_peer, 0x1002,
Jacob Erlbeck52f070a2014-09-04 13:45:56 +02002508 local_sgsn_tlli3, 1, imsi, sizeof(imsi),
Jacob Erlbeck6bd7ded2014-08-15 17:20:06 +02002509 GPRS_SAPI_GMM, sgsn_nu++,
2510 dtap_detach_acc, sizeof(dtap_detach_acc));
2511
2512 dump_peers(stdout, 0, 0, &gbcfg);
Jacob Erlbeck299389a2014-08-21 16:34:18 +02002513
Jacob Erlbeck6bd7ded2014-08-15 17:20:06 +02002514 dump_global(stdout, 0);
2515
2516 gbprox_reset(&gbcfg);
2517 gprs_ns_destroy(nsi);
2518 nsi = NULL;
Daniel Willmannd1554ec2015-10-12 19:36:34 +02002519
2520 cleanup_test();
Jacob Erlbeck6bd7ded2014-08-15 17:20:06 +02002521}
2522
Jacob Erlbecke99c3332014-10-20 16:25:01 +02002523static void test_gbproxy_ptmsi_patching_bad_cases()
2524{
2525 struct gprs_ns_inst *nsi = gprs_ns_instantiate(gprs_ns_callback, NULL);
2526 struct sockaddr_in bss_peer[1] = {{0},};
2527 struct sockaddr_in sgsn_peer= {0};
2528 struct gprs_ra_id rai_bss =
2529 {.mcc = 112, .mnc = 332, .lac = 16464, .rac = 96};
2530 struct gprs_ra_id rai_unknown =
2531 {.mcc = 1, .mnc = 99, .lac = 99, .rac = 96};
2532 uint16_t cell_id = 0x1234;
2533
2534 const uint32_t sgsn_ptmsi = 0xefe2b700;
2535 const uint32_t local_sgsn_tlli = 0xefe2b700;
Daniel Willmann537d4802015-10-12 19:36:35 +02002536 const uint32_t random_sgsn_tlli = 0x78dead00;
Jacob Erlbecke99c3332014-10-20 16:25:01 +02002537
Daniel Willmann537d4802015-10-12 19:36:35 +02002538 const uint32_t bss_ptmsi = 0xc0dead01;
2539 const uint32_t local_bss_tlli = 0xc0dead01;
Jacob Erlbecke99c3332014-10-20 16:25:01 +02002540 const uint32_t foreign_bss_tlli = 0x8000dead;
2541
2542
2543 const uint8_t imsi[] = {0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17, 0x18};
2544 struct gbproxy_link_info *link_info;
2545 struct gbproxy_peer *peer;
2546 unsigned bss_nu = 0;
2547 unsigned sgsn_nu = 0;
2548
2549 OSMO_ASSERT(local_sgsn_tlli == gprs_tmsi2tlli(sgsn_ptmsi, TLLI_LOCAL));
2550 OSMO_ASSERT(local_bss_tlli == gprs_tmsi2tlli(bss_ptmsi, TLLI_LOCAL));
2551
2552 bssgp_nsi = nsi;
2553 gbcfg.nsi = bssgp_nsi;
2554 gbcfg.nsip_sgsn_nsei = SGSN_NSEI;
2555 gbcfg.core_mcc = 123;
2556 gbcfg.core_mnc = 456;
2557 gbcfg.core_apn = talloc_zero_size(NULL, 100);
2558 gbcfg.core_apn_size = gprs_str_to_apn(gbcfg.core_apn, 100, "foo.bar");
2559 gbcfg.patch_ptmsi = 1;
Jacob Erlbecke99c3332014-10-20 16:25:01 +02002560
2561 configure_sgsn_peer(&sgsn_peer);
2562 configure_bss_peers(bss_peer, ARRAY_SIZE(bss_peer));
2563
2564 printf("=== %s ===\n", __func__);
2565 printf("--- Initialise SGSN ---\n\n");
2566
2567 connect_sgsn(nsi, &sgsn_peer, SGSN_NSEI);
2568
2569 printf("--- Initialise BSS 1 ---\n\n");
2570
2571 setup_ns(nsi, &bss_peer[0], 0x1001, 0x1000);
2572 setup_bssgp(nsi, &bss_peer[0], 0x1002);
2573
2574 peer = gbproxy_peer_by_nsei(&gbcfg, 0x1000);
2575 OSMO_ASSERT(peer != NULL);
2576
2577 send_bssgp_reset_ack(nsi, &sgsn_peer, 0x1002);
2578
2579 gprs_dump_nsi(nsi);
2580 dump_global(stdout, 0);
2581 dump_peers(stdout, 0, 0, &gbcfg);
2582
2583 printf("--- Send message from BSS 1 to SGSN, BVCI 0x1002 ---\n\n");
2584
2585 send_llc_ul_ui(nsi, "ATTACH REQUEST", &bss_peer[0], 0x1002,
2586 foreign_bss_tlli, &rai_unknown, cell_id,
2587 GPRS_SAPI_GMM, bss_nu++,
2588 dtap_attach_req, sizeof(dtap_attach_req));
2589
2590 dump_peers(stdout, 0, 0, &gbcfg);
2591
2592 send_llc_dl_ui(nsi, "IDENT REQUEST", &sgsn_peer, 0x1002,
2593 random_sgsn_tlli, 0, NULL, 0,
2594 GPRS_SAPI_GMM, sgsn_nu++,
2595 dtap_identity_req, sizeof(dtap_identity_req));
2596
2597 dump_peers(stdout, 0, 0, &gbcfg);
2598
2599 send_llc_ul_ui(nsi, "IDENT RESPONSE", &bss_peer[0], 0x1002,
2600 foreign_bss_tlli, &rai_bss, cell_id,
2601 GPRS_SAPI_GMM, bss_nu++,
2602 dtap_identity_resp, sizeof(dtap_identity_resp));
2603
2604 dump_peers(stdout, 0, 0, &gbcfg);
2605
2606 send_llc_dl_ui(nsi, "ATTACH ACCEPT", &sgsn_peer, 0x1002,
2607 random_sgsn_tlli, 1, imsi, sizeof(imsi),
2608 GPRS_SAPI_GMM, sgsn_nu++,
2609 dtap_attach_acc, sizeof(dtap_attach_acc));
2610
2611 dump_peers(stdout, 0, 0, &gbcfg);
2612
2613 link_info = gbproxy_link_info_by_sgsn_tlli(peer, random_sgsn_tlli, SGSN_NSEI);
2614 OSMO_ASSERT(link_info);
2615 OSMO_ASSERT(link_info->tlli.assigned == local_bss_tlli);
2616 OSMO_ASSERT(link_info->tlli.current == foreign_bss_tlli);
2617 OSMO_ASSERT(!link_info->tlli.bss_validated);
2618 OSMO_ASSERT(!link_info->tlli.net_validated);
2619 OSMO_ASSERT(link_info->tlli.ptmsi == bss_ptmsi);
2620 OSMO_ASSERT(link_info->sgsn_tlli.assigned == local_sgsn_tlli);
2621 OSMO_ASSERT(link_info->sgsn_tlli.current == random_sgsn_tlli);
2622 OSMO_ASSERT(!link_info->sgsn_tlli.bss_validated);
2623 OSMO_ASSERT(!link_info->sgsn_tlli.net_validated);
2624 OSMO_ASSERT(link_info->sgsn_tlli.ptmsi == sgsn_ptmsi);
2625
2626 send_llc_dl_ui(nsi, "ATTACH ACCEPT (duplicated)", &sgsn_peer, 0x1002,
2627 random_sgsn_tlli, 1, imsi, sizeof(imsi),
2628 GPRS_SAPI_GMM, sgsn_nu++,
2629 dtap_attach_acc, sizeof(dtap_attach_acc));
2630
2631 dump_peers(stdout, 0, 0, &gbcfg);
2632
2633 link_info = gbproxy_link_info_by_sgsn_tlli(peer, random_sgsn_tlli, SGSN_NSEI);
2634 OSMO_ASSERT(link_info);
Jacob Erlbeck91e9f552014-10-20 16:30:06 +02002635 OSMO_ASSERT(link_info->tlli.assigned == local_bss_tlli);
Jacob Erlbecke99c3332014-10-20 16:25:01 +02002636 OSMO_ASSERT(link_info->tlli.current == foreign_bss_tlli);
2637 OSMO_ASSERT(!link_info->tlli.bss_validated);
2638 OSMO_ASSERT(!link_info->tlli.net_validated);
Jacob Erlbeck91e9f552014-10-20 16:30:06 +02002639 OSMO_ASSERT(link_info->tlli.ptmsi == bss_ptmsi);
Jacob Erlbecke99c3332014-10-20 16:25:01 +02002640 OSMO_ASSERT(link_info->sgsn_tlli.assigned == local_sgsn_tlli);
2641 OSMO_ASSERT(link_info->sgsn_tlli.current == random_sgsn_tlli);
2642 OSMO_ASSERT(!link_info->sgsn_tlli.bss_validated);
2643 OSMO_ASSERT(!link_info->sgsn_tlli.net_validated);
2644 OSMO_ASSERT(link_info->sgsn_tlli.ptmsi == sgsn_ptmsi);
2645
2646 send_llc_ul_ui(nsi, "ATTACH COMPLETE", &bss_peer[0], 0x1002,
2647 local_bss_tlli, &rai_bss, cell_id,
2648 GPRS_SAPI_GMM, bss_nu++,
2649 dtap_attach_complete, sizeof(dtap_attach_complete));
2650
2651 dump_peers(stdout, 0, 0, &gbcfg);
2652
2653 link_info = gbproxy_link_info_by_sgsn_tlli(peer, local_sgsn_tlli, SGSN_NSEI);
2654 OSMO_ASSERT(link_info);
Jacob Erlbeck91e9f552014-10-20 16:30:06 +02002655 OSMO_ASSERT(link_info->tlli.assigned == local_bss_tlli);
Jacob Erlbecke99c3332014-10-20 16:25:01 +02002656 OSMO_ASSERT(link_info->tlli.current == foreign_bss_tlli);
Jacob Erlbeck91e9f552014-10-20 16:30:06 +02002657 OSMO_ASSERT(link_info->tlli.bss_validated);
Jacob Erlbecke99c3332014-10-20 16:25:01 +02002658 OSMO_ASSERT(!link_info->tlli.net_validated);
2659 OSMO_ASSERT(link_info->sgsn_tlli.assigned == local_sgsn_tlli);
2660 OSMO_ASSERT(link_info->sgsn_tlli.current == random_sgsn_tlli);
Jacob Erlbeck91e9f552014-10-20 16:30:06 +02002661 OSMO_ASSERT(link_info->sgsn_tlli.bss_validated);
Jacob Erlbecke99c3332014-10-20 16:25:01 +02002662 OSMO_ASSERT(!link_info->sgsn_tlli.net_validated);
2663
2664 send_llc_dl_ui(nsi, "GMM INFO", &sgsn_peer, 0x1002,
2665 local_sgsn_tlli, 1, imsi, sizeof(imsi),
2666 GPRS_SAPI_GMM, sgsn_nu++,
2667 dtap_gmm_information, sizeof(dtap_gmm_information));
2668
2669 dump_peers(stdout, 0, 0, &gbcfg);
2670
2671 link_info = gbproxy_link_info_by_sgsn_tlli(peer, local_sgsn_tlli, SGSN_NSEI);
2672 OSMO_ASSERT(link_info);
Jacob Erlbeck91e9f552014-10-20 16:30:06 +02002673 OSMO_ASSERT(link_info->tlli.current == local_bss_tlli);
2674 OSMO_ASSERT(link_info->tlli.assigned == 0);
2675 OSMO_ASSERT(link_info->sgsn_tlli.current == local_sgsn_tlli);
2676 OSMO_ASSERT(link_info->sgsn_tlli.assigned == 0);
Jacob Erlbecke99c3332014-10-20 16:25:01 +02002677
2678 /* Detach */
2679 send_llc_ul_ui(nsi, "DETACH REQ", &bss_peer[0], 0x1002,
2680 local_bss_tlli, &rai_bss, cell_id,
2681 GPRS_SAPI_GMM, bss_nu++,
2682 dtap_detach_req, sizeof(dtap_detach_req));
2683
2684 dump_peers(stdout, 0, 0, &gbcfg);
2685
2686 send_llc_dl_ui(nsi, "DETACH ACC", &sgsn_peer, 0x1002,
2687 local_sgsn_tlli, 1, imsi, sizeof(imsi),
2688 GPRS_SAPI_GMM, sgsn_nu++,
2689 dtap_detach_acc, sizeof(dtap_detach_acc));
2690
2691 dump_peers(stdout, 0, 0, &gbcfg);
2692
2693 dump_global(stdout, 0);
2694
2695 gbprox_reset(&gbcfg);
2696 gprs_ns_destroy(nsi);
2697 nsi = NULL;
Daniel Willmannd1554ec2015-10-12 19:36:34 +02002698
2699 cleanup_test();
Jacob Erlbecke99c3332014-10-20 16:25:01 +02002700}
2701
2702
Jacob Erlbeck28fe9882014-08-26 13:33:36 +02002703static void test_gbproxy_imsi_acquisition()
2704{
2705 struct gprs_ns_inst *nsi = gprs_ns_instantiate(gprs_ns_callback, NULL);
2706 struct sockaddr_in bss_peer[1] = {{0},};
2707 struct sockaddr_in sgsn_peer= {0};
2708 struct gprs_ra_id rai_bss =
2709 {.mcc = 112, .mnc = 332, .lac = 16464, .rac = 96};
2710 struct gprs_ra_id rai_sgsn =
2711 {.mcc = 123, .mnc = 456, .lac = 16464, .rac = 96};
2712 struct gprs_ra_id rai_wrong_mcc_sgsn =
2713 {.mcc = 999, .mnc = 456, .lac = 16464, .rac = 96};
2714 struct gprs_ra_id rai_unknown =
2715 {.mcc = 1, .mnc = 99, .lac = 99, .rac = 96};
2716 uint16_t cell_id = 0x1234;
2717
2718 const uint32_t sgsn_ptmsi = 0xefe2b700;
2719 const uint32_t local_sgsn_tlli = 0xefe2b700;
Daniel Willmann537d4802015-10-12 19:36:35 +02002720 const uint32_t random_sgsn_tlli = 0x78dead00;
2721 const uint32_t random_sgsn_tlli2 = 0x78dead02;
Jacob Erlbeck28fe9882014-08-26 13:33:36 +02002722
Daniel Willmann537d4802015-10-12 19:36:35 +02002723 const uint32_t bss_ptmsi = 0xc0dead01;
2724 const uint32_t local_bss_tlli = 0xc0dead01;
Jacob Erlbeck28fe9882014-08-26 13:33:36 +02002725 const uint32_t foreign_bss_tlli = 0x8000dead;
Jacob Erlbeck991606b2014-09-12 10:33:38 +02002726 const uint32_t other_bss_tlli = 0x8000beef;
Jacob Erlbeck28fe9882014-08-26 13:33:36 +02002727
2728 const uint8_t imsi[] = {0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17, 0x18};
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +02002729 struct gbproxy_link_info *link_info;
Jacob Erlbeck28fe9882014-08-26 13:33:36 +02002730 struct gbproxy_peer *peer;
2731 unsigned bss_nu = 0;
2732 unsigned sgsn_nu = 0;
2733
2734 OSMO_ASSERT(local_sgsn_tlli == gprs_tmsi2tlli(sgsn_ptmsi, TLLI_LOCAL));
2735
2736 bssgp_nsi = nsi;
2737 gbcfg.nsi = bssgp_nsi;
2738 gbcfg.nsip_sgsn_nsei = SGSN_NSEI;
2739 gbcfg.core_mcc = 123;
2740 gbcfg.core_mnc = 456;
2741 gbcfg.core_apn = talloc_zero_size(NULL, 100);
2742 gbcfg.core_apn_size = gprs_str_to_apn(gbcfg.core_apn, 100, "foo.bar");
2743 gbcfg.patch_ptmsi = 1;
Jacob Erlbeck5f4ef322014-08-22 17:10:01 +02002744 gbcfg.acquire_imsi = 1;
Jacob Erlbeck28fe9882014-08-26 13:33:36 +02002745
2746 configure_sgsn_peer(&sgsn_peer);
2747 configure_bss_peers(bss_peer, ARRAY_SIZE(bss_peer));
2748
2749 printf("=== %s ===\n", __func__);
2750 printf("--- Initialise SGSN ---\n\n");
2751
Jacob Erlbeckf181f9e2014-08-27 12:44:25 +02002752 connect_sgsn(nsi, &sgsn_peer, SGSN_NSEI);
Jacob Erlbeck28fe9882014-08-26 13:33:36 +02002753
2754 printf("--- Initialise BSS 1 ---\n\n");
2755
2756 setup_ns(nsi, &bss_peer[0], 0x1001, 0x1000);
2757 setup_bssgp(nsi, &bss_peer[0], 0x1002);
2758
2759 peer = gbproxy_peer_by_nsei(&gbcfg, 0x1000);
2760 OSMO_ASSERT(peer != NULL);
2761
2762 send_bssgp_reset_ack(nsi, &sgsn_peer, 0x1002);
2763
2764 gprs_dump_nsi(nsi);
2765 dump_global(stdout, 0);
2766 dump_peers(stdout, 0, 0, &gbcfg);
2767
2768 printf("--- Send message from BSS 1 to SGSN, BVCI 0x1002 ---\n\n");
2769
2770 send_llc_ul_ui(nsi, "ATTACH REQUEST", &bss_peer[0], 0x1002,
Jacob Erlbeck991606b2014-09-12 10:33:38 +02002771 foreign_bss_tlli, &rai_bss, cell_id,
Jacob Erlbeck28fe9882014-08-26 13:33:36 +02002772 GPRS_SAPI_GMM, bss_nu++,
2773 dtap_attach_req, sizeof(dtap_attach_req));
2774
2775 dump_peers(stdout, 0, 0, &gbcfg);
2776
Jacob Erlbeck5f4ef322014-08-22 17:10:01 +02002777 send_llc_ul_ui(nsi, "IDENT RESPONSE", &bss_peer[0], 0x1002,
2778 foreign_bss_tlli, &rai_bss, cell_id,
2779 GPRS_SAPI_GMM, bss_nu++,
2780 dtap_identity_resp, sizeof(dtap_identity_resp));
2781
2782 dump_peers(stdout, 0, 0, &gbcfg);
2783
Jacob Erlbeck28fe9882014-08-26 13:33:36 +02002784 send_llc_dl_ui(nsi, "IDENT REQUEST", &sgsn_peer, 0x1002,
2785 random_sgsn_tlli, 0, NULL, 0,
2786 GPRS_SAPI_GMM, sgsn_nu++,
2787 dtap_identity_req, sizeof(dtap_identity_req));
2788
2789 dump_peers(stdout, 0, 0, &gbcfg);
2790
2791 send_llc_ul_ui(nsi, "IDENT RESPONSE", &bss_peer[0], 0x1002,
2792 foreign_bss_tlli, &rai_bss, cell_id,
2793 GPRS_SAPI_GMM, bss_nu++,
2794 dtap_identity_resp, sizeof(dtap_identity_resp));
2795
2796 dump_peers(stdout, 0, 0, &gbcfg);
2797
2798 send_llc_dl_ui(nsi, "ATTACH ACCEPT", &sgsn_peer, 0x1002,
2799 random_sgsn_tlli, 1, imsi, sizeof(imsi),
2800 GPRS_SAPI_GMM, sgsn_nu++,
2801 dtap_attach_acc, sizeof(dtap_attach_acc));
2802
2803 dump_peers(stdout, 0, 0, &gbcfg);
2804
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +02002805 link_info = gbproxy_link_info_by_sgsn_tlli(peer, random_sgsn_tlli, SGSN_NSEI);
2806 OSMO_ASSERT(link_info);
2807 OSMO_ASSERT(link_info->tlli.assigned == local_bss_tlli);
2808 OSMO_ASSERT(link_info->tlli.current == foreign_bss_tlli);
2809 OSMO_ASSERT(!link_info->tlli.bss_validated);
2810 OSMO_ASSERT(!link_info->tlli.net_validated);
2811 OSMO_ASSERT(link_info->tlli.ptmsi == bss_ptmsi);
2812 OSMO_ASSERT(link_info->sgsn_tlli.assigned == local_sgsn_tlli);
2813 OSMO_ASSERT(link_info->sgsn_tlli.current == random_sgsn_tlli);
2814 OSMO_ASSERT(!link_info->sgsn_tlli.bss_validated);
2815 OSMO_ASSERT(!link_info->sgsn_tlli.net_validated);
2816 OSMO_ASSERT(link_info->sgsn_tlli.ptmsi == sgsn_ptmsi);
Jacob Erlbeck28fe9882014-08-26 13:33:36 +02002817
2818 send_llc_ul_ui(nsi, "ATTACH COMPLETE", &bss_peer[0], 0x1002,
2819 local_bss_tlli, &rai_bss, cell_id,
2820 GPRS_SAPI_GMM, bss_nu++,
2821 dtap_attach_complete, sizeof(dtap_attach_complete));
2822
2823 dump_peers(stdout, 0, 0, &gbcfg);
2824
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +02002825 link_info = gbproxy_link_info_by_sgsn_tlli(peer, local_sgsn_tlli, SGSN_NSEI);
2826 OSMO_ASSERT(link_info);
2827 OSMO_ASSERT(link_info->tlli.assigned == local_bss_tlli);
2828 OSMO_ASSERT(link_info->tlli.current == foreign_bss_tlli);
2829 OSMO_ASSERT(link_info->tlli.bss_validated);
2830 OSMO_ASSERT(!link_info->tlli.net_validated);
2831 OSMO_ASSERT(link_info->sgsn_tlli.assigned == local_sgsn_tlli);
2832 OSMO_ASSERT(link_info->sgsn_tlli.current == random_sgsn_tlli);
2833 OSMO_ASSERT(link_info->sgsn_tlli.bss_validated);
2834 OSMO_ASSERT(!link_info->sgsn_tlli.net_validated);
Jacob Erlbeck28fe9882014-08-26 13:33:36 +02002835
2836 send_llc_dl_ui(nsi, "GMM INFO", &sgsn_peer, 0x1002,
2837 local_sgsn_tlli, 1, imsi, sizeof(imsi),
2838 GPRS_SAPI_GMM, sgsn_nu++,
2839 dtap_gmm_information, sizeof(dtap_gmm_information));
2840
2841 dump_peers(stdout, 0, 0, &gbcfg);
2842
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +02002843 link_info = gbproxy_link_info_by_sgsn_tlli(peer, local_sgsn_tlli, SGSN_NSEI);
2844 OSMO_ASSERT(link_info);
2845 OSMO_ASSERT(link_info->tlli.current == local_bss_tlli);
2846 OSMO_ASSERT(link_info->tlli.assigned == 0);
2847 OSMO_ASSERT(link_info->sgsn_tlli.current == local_sgsn_tlli);
2848 OSMO_ASSERT(link_info->sgsn_tlli.assigned == 0);
Jacob Erlbeck28fe9882014-08-26 13:33:36 +02002849
2850 /* Non-DTAP */
2851 send_bssgp_ul_unitdata(nsi, "XID (UL)", &bss_peer[0], 0x1002,
2852 local_bss_tlli, &rai_bss, cell_id,
2853 llc_u_xid_ul, sizeof(llc_u_xid_ul));
2854
2855 send_bssgp_dl_unitdata(nsi, "XID (DL)", &sgsn_peer, 0x1002,
2856 local_sgsn_tlli, 1, imsi, sizeof(imsi),
2857 llc_u_xid_dl, sizeof(llc_u_xid_dl));
2858
2859 send_bssgp_ul_unitdata(nsi, "LL11 DNS QUERY (UL)", &bss_peer[0], 0x1002,
2860 local_bss_tlli, &rai_bss, cell_id,
2861 llc_ui_ll11_dns_query_ul,
2862 sizeof(llc_ui_ll11_dns_query_ul));
2863
2864 send_bssgp_dl_unitdata(nsi, "LL11 DNS RESP (DL)", &sgsn_peer, 0x1002,
2865 local_sgsn_tlli, 1, imsi, sizeof(imsi),
2866 llc_ui_ll11_dns_resp_dl,
2867 sizeof(llc_ui_ll11_dns_resp_dl));
2868
2869 dump_peers(stdout, 0, 0, &gbcfg);
2870
2871 /* Other messages */
2872 send_bssgp_llc_discarded(nsi, &bss_peer[0], 0x1002,
2873 local_bss_tlli, 1, 12);
2874
2875 dump_peers(stdout, 0, 0, &gbcfg);
2876
2877 send_bssgp_llc_discarded(nsi, &sgsn_peer, 0x1002,
2878 local_sgsn_tlli, 1, 12);
2879
2880 dump_peers(stdout, 0, 0, &gbcfg);
2881
2882 send_bssgp_suspend(nsi, &bss_peer[0], local_bss_tlli, &rai_bss);
2883
2884 dump_peers(stdout, 0, 0, &gbcfg);
2885
2886 send_bssgp_suspend_ack(nsi, &sgsn_peer, local_sgsn_tlli, &rai_sgsn);
2887
2888 dump_peers(stdout, 0, 0, &gbcfg);
2889
2890 /* Bad case: Invalid BVCI */
2891 send_bssgp_llc_discarded(nsi, &bss_peer[0], 0xeee1,
2892 local_bss_tlli, 1, 12);
2893 dump_global(stdout, 0);
2894
2895 /* Bad case: Invalid RAI */
2896 send_bssgp_suspend_ack(nsi, &sgsn_peer, local_sgsn_tlli, &rai_unknown);
2897
2898 dump_global(stdout, 0);
2899
2900 /* Bad case: Invalid MCC (LAC ok) */
2901 send_bssgp_suspend_ack(nsi, &sgsn_peer, local_sgsn_tlli,
2902 &rai_wrong_mcc_sgsn);
2903
2904 dump_global(stdout, 0);
2905
2906 /* Detach */
2907 send_llc_ul_ui(nsi, "DETACH REQ", &bss_peer[0], 0x1002,
2908 local_bss_tlli, &rai_bss, cell_id,
2909 GPRS_SAPI_GMM, bss_nu++,
2910 dtap_detach_req, sizeof(dtap_detach_req));
2911
2912 dump_peers(stdout, 0, 0, &gbcfg);
2913
2914 send_llc_dl_ui(nsi, "DETACH ACC", &sgsn_peer, 0x1002,
2915 local_sgsn_tlli, 1, imsi, sizeof(imsi),
2916 GPRS_SAPI_GMM, sgsn_nu++,
2917 dtap_detach_acc, sizeof(dtap_detach_acc));
2918
2919 dump_peers(stdout, 0, 0, &gbcfg);
2920
Jacob Erlbeck2ec27572014-09-18 09:57:47 +02002921 /* RA Update request */
2922
2923 send_llc_ul_ui(nsi, "RA UPD REQ", &bss_peer[0], 0x1002,
2924 foreign_bss_tlli, &rai_unknown, 0x7080,
2925 GPRS_SAPI_GMM, bss_nu++,
2926 dtap_ra_upd_req, sizeof(dtap_ra_upd_req));
2927
2928 send_llc_ul_ui(nsi, "IDENT RESPONSE", &bss_peer[0], 0x1002,
2929 foreign_bss_tlli, &rai_bss, cell_id,
2930 GPRS_SAPI_GMM, bss_nu++,
2931 dtap_identity_resp, sizeof(dtap_identity_resp));
2932
2933 dump_peers(stdout, 0, 0, &gbcfg);
2934
2935 send_llc_dl_ui(nsi, "RA UDP ACC", &sgsn_peer, 0x1002,
2936 random_sgsn_tlli2, 1, imsi, sizeof(imsi),
2937 GPRS_SAPI_GMM, sgsn_nu++,
2938 dtap_ra_upd_acc, sizeof(dtap_ra_upd_acc));
2939
2940 dump_peers(stdout, 0, 0, &gbcfg);
2941
2942 /* Detach */
2943
2944 send_llc_ul_ui(nsi, "DETACH REQ", &bss_peer[0], 0x1002,
2945 local_bss_tlli, &rai_bss, cell_id,
2946 GPRS_SAPI_GMM, bss_nu++,
2947 dtap_detach_req, sizeof(dtap_detach_req));
2948
2949 dump_peers(stdout, 0, 0, &gbcfg);
2950
2951 send_llc_dl_ui(nsi, "DETACH ACC", &sgsn_peer, 0x1002,
2952 local_sgsn_tlli, 1, imsi, sizeof(imsi),
2953 GPRS_SAPI_GMM, sgsn_nu++,
2954 dtap_detach_acc, sizeof(dtap_detach_acc));
2955
2956 dump_peers(stdout, 0, 0, &gbcfg);
2957
Jacob Erlbeckea1698e2014-09-02 14:40:11 +02002958 /* Special case: Repeated Attach Requests */
2959
2960 send_llc_ul_ui(nsi, "ATTACH REQUEST", &bss_peer[0], 0x1002,
2961 foreign_bss_tlli, &rai_unknown, cell_id,
2962 GPRS_SAPI_GMM, bss_nu++,
2963 dtap_attach_req, sizeof(dtap_attach_req));
2964
2965 send_llc_ul_ui(nsi, "ATTACH REQUEST", &bss_peer[0], 0x1002,
2966 foreign_bss_tlli, &rai_unknown, cell_id,
2967 GPRS_SAPI_GMM, bss_nu++,
2968 dtap_attach_req, sizeof(dtap_attach_req));
2969
Jacob Erlbeck991606b2014-09-12 10:33:38 +02002970 send_llc_ul_ui(nsi, "DETACH REQ", &bss_peer[0], 0x1002,
2971 foreign_bss_tlli, &rai_bss, cell_id,
2972 GPRS_SAPI_GMM, bss_nu++,
2973 dtap_detach_req, sizeof(dtap_detach_req));
2974
2975 dump_peers(stdout, 0, 0, &gbcfg);
2976
2977 /* Special case: Detach from an unknown TLLI */
2978
2979 send_llc_ul_ui(nsi, "DETACH REQ (unknown TLLI)", &bss_peer[0], 0x1002,
2980 other_bss_tlli, &rai_bss, cell_id,
2981 GPRS_SAPI_GMM, bss_nu++,
2982 dtap_detach_req, sizeof(dtap_detach_req));
2983
Jacob Erlbeckea1698e2014-09-02 14:40:11 +02002984 dump_peers(stdout, 0, 0, &gbcfg);
2985
Jacob Erlbeck2ec27572014-09-18 09:57:47 +02002986 /* Special case: Repeated RA Update Requests */
2987
2988 send_llc_ul_ui(nsi, "RA UPD REQ", &bss_peer[0], 0x1002,
2989 foreign_bss_tlli, &rai_unknown, 0x7080,
2990 GPRS_SAPI_GMM, bss_nu++,
2991 dtap_ra_upd_req, sizeof(dtap_ra_upd_req));
2992
2993 send_llc_ul_ui(nsi, "RA UPD REQ", &bss_peer[0], 0x1002,
2994 foreign_bss_tlli, &rai_unknown, 0x7080,
2995 GPRS_SAPI_GMM, bss_nu++,
2996 dtap_ra_upd_req, sizeof(dtap_ra_upd_req));
2997
2998 send_llc_ul_ui(nsi, "DETACH REQ", &bss_peer[0], 0x1002,
2999 foreign_bss_tlli, &rai_bss, cell_id,
3000 GPRS_SAPI_GMM, bss_nu++,
3001 dtap_detach_req, sizeof(dtap_detach_req));
3002
3003 dump_peers(stdout, 0, 0, &gbcfg);
3004
Jacob Erlbeck28fe9882014-08-26 13:33:36 +02003005 dump_global(stdout, 0);
3006
3007 gbprox_reset(&gbcfg);
3008 gprs_ns_destroy(nsi);
3009 nsi = NULL;
Daniel Willmannd1554ec2015-10-12 19:36:34 +02003010
3011 cleanup_test();
Jacob Erlbeck28fe9882014-08-26 13:33:36 +02003012}
3013
Jacob Erlbeckf181f9e2014-08-27 12:44:25 +02003014static void test_gbproxy_secondary_sgsn()
3015{
3016 struct gprs_ns_inst *nsi = gprs_ns_instantiate(gprs_ns_callback, NULL);
3017 struct sockaddr_in bss_peer[1] = {{0},};
3018 struct sockaddr_in sgsn_peer[2]= {{0},};
3019 struct gprs_ra_id rai_bss =
3020 {.mcc = 112, .mnc = 332, .lac = 16464, .rac = 96};
3021 struct gprs_ra_id rai_sgsn =
3022 {.mcc = 123, .mnc = 456, .lac = 16464, .rac = 96};
3023 struct gprs_ra_id rai_unknown =
3024 {.mcc = 1, .mnc = 99, .lac = 99, .rac = 96};
3025 uint16_t cell_id = 0x1234;
3026
3027 const uint32_t sgsn_ptmsi = 0xefe2b700;
3028 const uint32_t local_sgsn_tlli = 0xefe2b700;
Daniel Willmann537d4802015-10-12 19:36:35 +02003029 const uint32_t random_sgsn_tlli = 0x78dead00;
Jacob Erlbeckf181f9e2014-08-27 12:44:25 +02003030
Daniel Willmann537d4802015-10-12 19:36:35 +02003031 const uint32_t bss_ptmsi = 0xc0dead01;
3032 const uint32_t local_bss_tlli = 0xc0dead01;
Jacob Erlbeckf181f9e2014-08-27 12:44:25 +02003033 const uint32_t foreign_bss_tlli = 0x8000dead;
3034
3035 const uint32_t sgsn_ptmsi2 = 0xe0987654;
3036 const uint32_t local_sgsn_tlli2 = 0xe0987654;
Daniel Willmann537d4802015-10-12 19:36:35 +02003037 const uint32_t random_sgsn_tlli2 = 0x78dead02;
3038 const uint32_t bss_ptmsi2 = 0xc0dead03;
3039 const uint32_t local_bss_tlli2 = 0xc0dead03;
Jacob Erlbeckf181f9e2014-08-27 12:44:25 +02003040 const uint32_t foreign_bss_tlli2 = 0x8000beef;
3041
Daniel Willmann537d4802015-10-12 19:36:35 +02003042 const uint32_t random_sgsn_tlli3 = 0x78dead04;
3043 const uint32_t bss_ptmsi3 = 0xc0dead05;
3044 const uint32_t local_bss_tlli3 = 0xc0dead05;
Jacob Erlbeckaf952ba2014-09-17 12:09:25 +02003045 const uint32_t foreign_bss_tlli3 = 0x8000feed;
3046
Jacob Erlbeckf181f9e2014-08-27 12:44:25 +02003047 const uint8_t imsi1[] = {0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17, 0x18};
3048 const uint8_t imsi2[] = {0x11, 0x12, 0x99, 0x99, 0x99, 0x16, 0x17, 0x18};
Jacob Erlbeckaf952ba2014-09-17 12:09:25 +02003049 const uint8_t imsi3[] = {0x11, 0x12, 0x99, 0x99, 0x99, 0x26, 0x27, 0x28};
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +02003050 struct gbproxy_link_info *link_info;
3051 struct gbproxy_link_info *other_info;
Jacob Erlbeckf181f9e2014-08-27 12:44:25 +02003052 struct gbproxy_peer *peer;
3053 unsigned bss_nu = 0;
3054 unsigned sgsn_nu = 0;
3055
3056 const char *err_msg = NULL;
3057 const char *filter_re = "999999";
3058
3059 OSMO_ASSERT(local_sgsn_tlli == gprs_tmsi2tlli(sgsn_ptmsi, TLLI_LOCAL));
3060 OSMO_ASSERT(local_sgsn_tlli2 == gprs_tmsi2tlli(sgsn_ptmsi2, TLLI_LOCAL));
3061
3062 bssgp_nsi = nsi;
3063 gbcfg.nsi = bssgp_nsi;
3064 gbcfg.nsip_sgsn_nsei = SGSN_NSEI;
3065 gbcfg.core_mcc = 123;
3066 gbcfg.core_mnc = 456;
3067 gbcfg.core_apn = talloc_zero_size(NULL, 100);
3068 gbcfg.core_apn_size = gprs_str_to_apn(gbcfg.core_apn, 100, "foo.bar");
3069 gbcfg.patch_ptmsi = 1;
3070 gbcfg.acquire_imsi = 1;
Daniel Willmann537d4802015-10-12 19:36:35 +02003071
Jacob Erlbeckf181f9e2014-08-27 12:44:25 +02003072 gbcfg.route_to_sgsn2 = 1;
3073 gbcfg.nsip_sgsn2_nsei = SGSN2_NSEI;
3074
Jacob Erlbeckb36032c2014-09-25 13:21:48 +02003075 if (gbproxy_set_patch_filter(&gbcfg.matches[GBPROX_MATCH_ROUTING],
Jacob Erlbeck9a83d7a2014-09-25 11:17:31 +02003076 filter_re, &err_msg) != 0) {
Jacob Erlbeckf181f9e2014-08-27 12:44:25 +02003077 fprintf(stderr, "gbprox_set_patch_filter: got error: %s\n",
3078 err_msg);
3079 OSMO_ASSERT(err_msg == NULL);
3080 }
3081
3082 configure_sgsn_peer(&sgsn_peer[0]);
3083 configure_sgsn2_peer(&sgsn_peer[1]);
3084 configure_bss_peers(bss_peer, ARRAY_SIZE(bss_peer));
3085
3086 printf("=== %s ===\n", __func__);
3087 printf("--- Initialise SGSN 1 ---\n\n");
3088
3089 connect_sgsn(nsi, &sgsn_peer[0], SGSN_NSEI);
3090
3091 printf("--- Initialise SGSN 2 ---\n\n");
3092
3093 connect_sgsn(nsi, &sgsn_peer[1], SGSN2_NSEI);
3094
3095 printf("--- Initialise BSS 1 ---\n\n");
3096
3097 setup_ns(nsi, &bss_peer[0], 0x1001, 0x1000);
3098 setup_bssgp(nsi, &bss_peer[0], 0x0);
3099 send_bssgp_reset_ack(nsi, &sgsn_peer[0], 0x0);
3100 setup_bssgp(nsi, &bss_peer[0], 0x1002);
3101 send_bssgp_reset_ack(nsi, &sgsn_peer[0], 0x1002);
3102 send_bssgp_reset_ack(nsi, &sgsn_peer[1], 0x1002);
3103
3104 peer = gbproxy_peer_by_nsei(&gbcfg, 0x1000);
3105 OSMO_ASSERT(peer != NULL);
3106
3107 gprs_dump_nsi(nsi);
3108 dump_global(stdout, 0);
3109 dump_peers(stdout, 0, 0, &gbcfg);
3110
3111 printf("--- Flow control ---\n\n");
3112
3113 send_bssgp_flow_control_bvc(nsi, &bss_peer[0], 0x1002, 1);
3114 send_bssgp_flow_control_bvc_ack(nsi, &sgsn_peer[0], 0x1002, 1);
3115 send_bssgp_flow_control_bvc_ack(nsi, &sgsn_peer[1], 0x1002, 1);
3116
3117 printf("--- Establish GPRS connection (SGSN 1) ---\n\n");
3118
3119 send_llc_ul_ui(nsi, "ATTACH REQUEST", &bss_peer[0], 0x1002,
3120 foreign_bss_tlli, &rai_unknown, cell_id,
3121 GPRS_SAPI_GMM, bss_nu++,
3122 dtap_attach_req, sizeof(dtap_attach_req));
3123
3124 dump_peers(stdout, 0, 0, &gbcfg);
3125
3126 send_llc_ul_ui(nsi, "IDENT RESPONSE", &bss_peer[0], 0x1002,
3127 foreign_bss_tlli, &rai_bss, cell_id,
3128 GPRS_SAPI_GMM, bss_nu++,
3129 dtap_identity_resp, sizeof(dtap_identity_resp));
3130
3131 dump_peers(stdout, 0, 0, &gbcfg);
3132
3133 send_llc_dl_ui(nsi, "IDENT REQUEST", &sgsn_peer[0], 0x1002,
3134 random_sgsn_tlli, 0, NULL, 0,
3135 GPRS_SAPI_GMM, sgsn_nu++,
3136 dtap_identity_req, sizeof(dtap_identity_req));
3137
3138 dump_peers(stdout, 0, 0, &gbcfg);
3139
3140 send_llc_ul_ui(nsi, "IDENT RESPONSE", &bss_peer[0], 0x1002,
3141 foreign_bss_tlli, &rai_bss, cell_id,
3142 GPRS_SAPI_GMM, bss_nu++,
3143 dtap_identity_resp, sizeof(dtap_identity_resp));
3144
3145 dump_peers(stdout, 0, 0, &gbcfg);
3146
3147 send_llc_dl_ui(nsi, "ATTACH ACCEPT", &sgsn_peer[0], 0x1002,
3148 random_sgsn_tlli, 1, imsi1, sizeof(imsi1),
3149 GPRS_SAPI_GMM, sgsn_nu++,
3150 dtap_attach_acc, sizeof(dtap_attach_acc));
3151
3152 dump_peers(stdout, 0, 0, &gbcfg);
3153
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +02003154 OSMO_ASSERT(!gbproxy_link_info_by_sgsn_tlli(peer, local_sgsn_tlli, SGSN2_NSEI));
3155 link_info = gbproxy_link_info_by_sgsn_tlli(peer, random_sgsn_tlli, SGSN_NSEI);
3156 OSMO_ASSERT(link_info);
3157 OSMO_ASSERT(link_info->tlli.assigned == local_bss_tlli);
3158 OSMO_ASSERT(link_info->tlli.current == foreign_bss_tlli);
3159 OSMO_ASSERT(!link_info->tlli.bss_validated);
3160 OSMO_ASSERT(!link_info->tlli.net_validated);
3161 OSMO_ASSERT(link_info->tlli.ptmsi == bss_ptmsi);
3162 OSMO_ASSERT(link_info->sgsn_tlli.assigned == local_sgsn_tlli);
3163 OSMO_ASSERT(link_info->sgsn_tlli.current == random_sgsn_tlli);
3164 OSMO_ASSERT(!link_info->sgsn_tlli.bss_validated);
3165 OSMO_ASSERT(!link_info->sgsn_tlli.net_validated);
3166 OSMO_ASSERT(link_info->sgsn_tlli.ptmsi == sgsn_ptmsi);
Jacob Erlbeckf181f9e2014-08-27 12:44:25 +02003167
3168 send_llc_ul_ui(nsi, "ATTACH COMPLETE", &bss_peer[0], 0x1002,
3169 local_bss_tlli, &rai_bss, cell_id,
3170 GPRS_SAPI_GMM, bss_nu++,
3171 dtap_attach_complete, sizeof(dtap_attach_complete));
3172
3173 dump_peers(stdout, 0, 0, &gbcfg);
3174
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +02003175 OSMO_ASSERT(!gbproxy_link_info_by_sgsn_tlli(peer, local_sgsn_tlli, SGSN2_NSEI));
3176 link_info = gbproxy_link_info_by_sgsn_tlli(peer, local_sgsn_tlli, SGSN_NSEI);
3177 OSMO_ASSERT(link_info);
3178 OSMO_ASSERT(link_info->tlli.assigned == local_bss_tlli);
3179 OSMO_ASSERT(link_info->tlli.current == foreign_bss_tlli);
3180 OSMO_ASSERT(link_info->tlli.bss_validated);
3181 OSMO_ASSERT(!link_info->tlli.net_validated);
3182 OSMO_ASSERT(link_info->sgsn_tlli.assigned == local_sgsn_tlli);
3183 OSMO_ASSERT(link_info->sgsn_tlli.current == random_sgsn_tlli);
3184 OSMO_ASSERT(link_info->sgsn_tlli.bss_validated);
3185 OSMO_ASSERT(!link_info->sgsn_tlli.net_validated);
Jacob Erlbeckf181f9e2014-08-27 12:44:25 +02003186
3187 send_llc_dl_ui(nsi, "GMM INFO", &sgsn_peer[0], 0x1002,
3188 local_sgsn_tlli, 1, imsi1, sizeof(imsi1),
3189 GPRS_SAPI_GMM, sgsn_nu++,
3190 dtap_gmm_information, sizeof(dtap_gmm_information));
3191
3192 dump_peers(stdout, 0, 0, &gbcfg);
3193
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +02003194 OSMO_ASSERT(!gbproxy_link_info_by_sgsn_tlli(peer, local_sgsn_tlli, SGSN2_NSEI));
3195 link_info = gbproxy_link_info_by_sgsn_tlli(peer, local_sgsn_tlli, SGSN_NSEI);
3196 OSMO_ASSERT(link_info);
3197 OSMO_ASSERT(link_info->tlli.current == local_bss_tlli);
3198 OSMO_ASSERT(link_info->tlli.assigned == 0);
3199 OSMO_ASSERT(link_info->sgsn_tlli.current == local_sgsn_tlli);
3200 OSMO_ASSERT(link_info->sgsn_tlli.assigned == 0);
Jacob Erlbeckf181f9e2014-08-27 12:44:25 +02003201
3202 /* Non-DTAP */
3203 send_bssgp_ul_unitdata(nsi, "XID (UL)", &bss_peer[0], 0x1002,
3204 local_bss_tlli, &rai_bss, cell_id,
3205 llc_u_xid_ul, sizeof(llc_u_xid_ul));
3206
3207 send_bssgp_dl_unitdata(nsi, "XID (DL)", &sgsn_peer[0], 0x1002,
3208 local_sgsn_tlli, 1, imsi1, sizeof(imsi1),
3209 llc_u_xid_dl, sizeof(llc_u_xid_dl));
3210
3211 send_bssgp_ul_unitdata(nsi, "LL11 DNS QUERY (UL)", &bss_peer[0], 0x1002,
3212 local_bss_tlli, &rai_bss, cell_id,
3213 llc_ui_ll11_dns_query_ul,
3214 sizeof(llc_ui_ll11_dns_query_ul));
3215
3216 send_bssgp_dl_unitdata(nsi, "LL11 DNS RESP (DL)", &sgsn_peer[0], 0x1002,
3217 local_sgsn_tlli, 1, imsi1, sizeof(imsi1),
3218 llc_ui_ll11_dns_resp_dl,
3219 sizeof(llc_ui_ll11_dns_resp_dl));
3220
3221 dump_peers(stdout, 0, 0, &gbcfg);
3222
3223 /* Other messages */
3224 send_bssgp_llc_discarded(nsi, &bss_peer[0], 0x1002,
3225 local_bss_tlli, 1, 12);
3226
3227 dump_peers(stdout, 0, 0, &gbcfg);
3228
3229 send_bssgp_llc_discarded(nsi, &sgsn_peer[0], 0x1002,
3230 local_sgsn_tlli, 1, 12);
3231
3232 dump_peers(stdout, 0, 0, &gbcfg);
3233
3234 send_bssgp_suspend(nsi, &bss_peer[0], local_bss_tlli, &rai_bss);
3235
3236 dump_peers(stdout, 0, 0, &gbcfg);
3237
3238 send_bssgp_suspend_ack(nsi, &sgsn_peer[0], local_sgsn_tlli, &rai_sgsn);
3239
3240 dump_peers(stdout, 0, 0, &gbcfg);
3241
3242 printf("--- Establish GPRS connection (SGSN 2) ---\n\n");
3243
3244 send_llc_ul_ui(nsi, "ATTACH REQUEST", &bss_peer[0], 0x1002,
3245 foreign_bss_tlli2, &rai_unknown, cell_id,
3246 GPRS_SAPI_GMM, bss_nu++,
3247 dtap_attach_req, sizeof(dtap_attach_req));
3248
3249 dump_peers(stdout, 0, 0, &gbcfg);
3250
3251 send_llc_ul_ui(nsi, "IDENT RESPONSE", &bss_peer[0], 0x1002,
3252 foreign_bss_tlli2, &rai_bss, cell_id,
3253 GPRS_SAPI_GMM, bss_nu++,
3254 dtap_identity2_resp, sizeof(dtap_identity2_resp));
3255
3256 dump_peers(stdout, 0, 0, &gbcfg);
3257
3258 send_llc_dl_ui(nsi, "IDENT REQUEST", &sgsn_peer[1], 0x1002,
3259 random_sgsn_tlli2, 0, NULL, 0,
3260 GPRS_SAPI_GMM, sgsn_nu++,
3261 dtap_identity_req, sizeof(dtap_identity_req));
3262
3263 dump_peers(stdout, 0, 0, &gbcfg);
3264
3265 send_llc_ul_ui(nsi, "IDENT RESPONSE", &bss_peer[0], 0x1002,
3266 foreign_bss_tlli2, &rai_bss, cell_id,
3267 GPRS_SAPI_GMM, bss_nu++,
Jacob Erlbeck2bb45432014-09-17 12:05:08 +02003268 dtap_identity2_resp, sizeof(dtap_identity2_resp));
Jacob Erlbeckf181f9e2014-08-27 12:44:25 +02003269
3270 dump_peers(stdout, 0, 0, &gbcfg);
3271
3272 send_llc_dl_ui(nsi, "ATTACH ACCEPT", &sgsn_peer[1], 0x1002,
3273 random_sgsn_tlli2, 1, imsi2, sizeof(imsi2),
3274 GPRS_SAPI_GMM, sgsn_nu++,
3275 dtap_attach_acc2, sizeof(dtap_attach_acc2));
3276
3277 dump_peers(stdout, 0, 0, &gbcfg);
3278
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +02003279 OSMO_ASSERT(!gbproxy_link_info_by_sgsn_tlli(peer, random_sgsn_tlli2, SGSN_NSEI));
3280 link_info = gbproxy_link_info_by_sgsn_tlli(peer, random_sgsn_tlli2, SGSN2_NSEI);
3281 OSMO_ASSERT(link_info);
3282 OSMO_ASSERT(link_info->tlli.assigned == local_bss_tlli2);
3283 OSMO_ASSERT(link_info->tlli.current == foreign_bss_tlli2);
3284 OSMO_ASSERT(!link_info->tlli.bss_validated);
3285 OSMO_ASSERT(!link_info->tlli.net_validated);
3286 OSMO_ASSERT(link_info->tlli.ptmsi == bss_ptmsi2);
3287 OSMO_ASSERT(link_info->sgsn_tlli.assigned == local_sgsn_tlli2);
3288 OSMO_ASSERT(link_info->sgsn_tlli.current == random_sgsn_tlli2);
3289 OSMO_ASSERT(!link_info->sgsn_tlli.bss_validated);
3290 OSMO_ASSERT(!link_info->sgsn_tlli.net_validated);
3291 OSMO_ASSERT(link_info->sgsn_tlli.ptmsi == sgsn_ptmsi2);
Jacob Erlbeckf181f9e2014-08-27 12:44:25 +02003292
3293 send_llc_ul_ui(nsi, "ATTACH COMPLETE", &bss_peer[0], 0x1002,
3294 local_bss_tlli2, &rai_bss, cell_id,
3295 GPRS_SAPI_GMM, bss_nu++,
3296 dtap_attach_complete, sizeof(dtap_attach_complete));
3297
3298 dump_peers(stdout, 0, 0, &gbcfg);
3299
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +02003300 OSMO_ASSERT(!gbproxy_link_info_by_sgsn_tlli(peer, local_sgsn_tlli2, SGSN_NSEI));
3301 link_info = gbproxy_link_info_by_sgsn_tlli(peer, local_sgsn_tlli2, SGSN2_NSEI);
3302 OSMO_ASSERT(link_info);
3303 OSMO_ASSERT(link_info->tlli.assigned == local_bss_tlli2);
3304 OSMO_ASSERT(link_info->tlli.current == foreign_bss_tlli2);
3305 OSMO_ASSERT(link_info->tlli.bss_validated);
3306 OSMO_ASSERT(!link_info->tlli.net_validated);
3307 OSMO_ASSERT(link_info->sgsn_tlli.assigned == local_sgsn_tlli2);
3308 OSMO_ASSERT(link_info->sgsn_tlli.current == random_sgsn_tlli2);
3309 OSMO_ASSERT(link_info->sgsn_tlli.bss_validated);
3310 OSMO_ASSERT(!link_info->sgsn_tlli.net_validated);
Jacob Erlbeckf181f9e2014-08-27 12:44:25 +02003311
3312 send_llc_dl_ui(nsi, "GMM INFO", &sgsn_peer[1], 0x1002,
3313 local_sgsn_tlli2, 1, imsi2, sizeof(imsi2),
3314 GPRS_SAPI_GMM, sgsn_nu++,
3315 dtap_gmm_information, sizeof(dtap_gmm_information));
3316
3317 dump_peers(stdout, 0, 0, &gbcfg);
3318
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +02003319 OSMO_ASSERT(!gbproxy_link_info_by_sgsn_tlli(peer, local_sgsn_tlli2, SGSN_NSEI));
3320 link_info = gbproxy_link_info_by_sgsn_tlli(peer, local_sgsn_tlli2, SGSN2_NSEI);
3321 OSMO_ASSERT(link_info);
3322 OSMO_ASSERT(link_info->tlli.current == local_bss_tlli2);
3323 OSMO_ASSERT(link_info->tlli.assigned == 0);
3324 OSMO_ASSERT(link_info->sgsn_tlli.current == local_sgsn_tlli2);
3325 OSMO_ASSERT(link_info->sgsn_tlli.assigned == 0);
Jacob Erlbeckf181f9e2014-08-27 12:44:25 +02003326
3327 /* Non-DTAP */
3328 send_bssgp_ul_unitdata(nsi, "XID (UL)", &bss_peer[0], 0x1002,
3329 local_bss_tlli2, &rai_bss, cell_id,
3330 llc_u_xid_ul, sizeof(llc_u_xid_ul));
3331
3332 send_bssgp_dl_unitdata(nsi, "XID (DL)", &sgsn_peer[1], 0x1002,
3333 local_sgsn_tlli2, 1, imsi2, sizeof(imsi2),
3334 llc_u_xid_dl, sizeof(llc_u_xid_dl));
3335
3336 send_bssgp_ul_unitdata(nsi, "LL11 DNS QUERY (UL)", &bss_peer[0], 0x1002,
3337 local_bss_tlli2, &rai_bss, cell_id,
3338 llc_ui_ll11_dns_query_ul,
3339 sizeof(llc_ui_ll11_dns_query_ul));
3340
3341 send_bssgp_dl_unitdata(nsi, "LL11 DNS RESP (DL)", &sgsn_peer[1], 0x1002,
3342 local_sgsn_tlli2, 1, imsi2, sizeof(imsi2),
3343 llc_ui_ll11_dns_resp_dl,
3344 sizeof(llc_ui_ll11_dns_resp_dl));
3345
3346 dump_peers(stdout, 0, 0, &gbcfg);
3347
3348 /* Other messages */
3349 send_bssgp_llc_discarded(nsi, &bss_peer[0], 0x1002,
3350 local_bss_tlli2, 1, 12);
3351
3352 dump_peers(stdout, 0, 0, &gbcfg);
3353
3354 send_bssgp_llc_discarded(nsi, &sgsn_peer[1], 0x1002,
3355 local_sgsn_tlli2, 1, 12);
3356
3357 dump_peers(stdout, 0, 0, &gbcfg);
3358
3359 send_bssgp_suspend(nsi, &bss_peer[0], local_bss_tlli2, &rai_bss);
3360
3361 dump_peers(stdout, 0, 0, &gbcfg);
3362
3363 send_bssgp_suspend_ack(nsi, &sgsn_peer[1], local_sgsn_tlli2, &rai_sgsn);
3364
3365 dump_peers(stdout, 0, 0, &gbcfg);
3366
Jacob Erlbeckaf952ba2014-09-17 12:09:25 +02003367 printf("--- Establish GPRS connection (SGSN 2, P-TMSI collision) ---\n\n");
3368
3369 send_llc_ul_ui(nsi, "ATTACH REQUEST", &bss_peer[0], 0x1002,
3370 foreign_bss_tlli3, &rai_unknown, cell_id,
3371 GPRS_SAPI_GMM, bss_nu++,
3372 dtap_attach_req, sizeof(dtap_attach_req));
3373
3374 dump_peers(stdout, 0, 0, &gbcfg);
3375
3376 send_llc_ul_ui(nsi, "IDENT RESPONSE", &bss_peer[0], 0x1002,
3377 foreign_bss_tlli3, &rai_bss, cell_id,
3378 GPRS_SAPI_GMM, bss_nu++,
3379 dtap_identity3_resp, sizeof(dtap_identity3_resp));
3380
3381 dump_peers(stdout, 0, 0, &gbcfg);
3382
3383 send_llc_dl_ui(nsi, "IDENT REQUEST", &sgsn_peer[1], 0x1002,
3384 random_sgsn_tlli3, 0, NULL, 0,
3385 GPRS_SAPI_GMM, sgsn_nu++,
3386 dtap_identity_req, sizeof(dtap_identity_req));
3387
3388 dump_peers(stdout, 0, 0, &gbcfg);
3389
3390 send_llc_ul_ui(nsi, "IDENT RESPONSE", &bss_peer[0], 0x1002,
3391 foreign_bss_tlli3, &rai_bss, cell_id,
3392 GPRS_SAPI_GMM, bss_nu++,
3393 dtap_identity3_resp, sizeof(dtap_identity3_resp));
3394
3395 dump_peers(stdout, 0, 0, &gbcfg);
3396
3397 send_llc_dl_ui(nsi, "ATTACH ACCEPT (P-TMSI 1)", &sgsn_peer[1], 0x1002,
3398 random_sgsn_tlli3, 1, imsi3, sizeof(imsi3),
3399 GPRS_SAPI_GMM, sgsn_nu++,
3400 dtap_attach_acc, sizeof(dtap_attach_acc));
3401
3402 dump_peers(stdout, 0, 0, &gbcfg);
3403
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +02003404 OSMO_ASSERT(!gbproxy_link_info_by_sgsn_tlli(peer, random_sgsn_tlli3, SGSN_NSEI));
3405 link_info = gbproxy_link_info_by_sgsn_tlli(peer, random_sgsn_tlli3, SGSN2_NSEI);
3406 OSMO_ASSERT(link_info);
3407 OSMO_ASSERT(link_info->tlli.assigned == local_bss_tlli3);
3408 OSMO_ASSERT(link_info->tlli.current == foreign_bss_tlli3);
3409 OSMO_ASSERT(!link_info->tlli.bss_validated);
3410 OSMO_ASSERT(!link_info->tlli.net_validated);
3411 OSMO_ASSERT(link_info->tlli.ptmsi == bss_ptmsi3);
3412 OSMO_ASSERT(link_info->sgsn_tlli.assigned == local_sgsn_tlli);
3413 OSMO_ASSERT(link_info->sgsn_tlli.current == random_sgsn_tlli3);
3414 OSMO_ASSERT(!link_info->sgsn_tlli.bss_validated);
3415 OSMO_ASSERT(!link_info->sgsn_tlli.net_validated);
3416 OSMO_ASSERT(link_info->sgsn_tlli.ptmsi == sgsn_ptmsi);
Jacob Erlbeck91a0e862014-09-17 10:56:38 +02003417
Jacob Erlbeckaf952ba2014-09-17 12:09:25 +02003418 send_llc_ul_ui(nsi, "ATTACH COMPLETE", &bss_peer[0], 0x1002,
3419 local_bss_tlli3, &rai_bss, cell_id,
3420 GPRS_SAPI_GMM, bss_nu++,
3421 dtap_attach_complete, sizeof(dtap_attach_complete));
3422
3423 dump_peers(stdout, 0, 0, &gbcfg);
3424
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +02003425 other_info = gbproxy_link_info_by_sgsn_tlli(peer, local_sgsn_tlli, SGSN_NSEI);
Jacob Erlbeck91a0e862014-09-17 10:56:38 +02003426 OSMO_ASSERT(other_info);
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +02003427 link_info = gbproxy_link_info_by_sgsn_tlli(peer, local_sgsn_tlli, SGSN2_NSEI);
3428 OSMO_ASSERT(link_info);
3429 OSMO_ASSERT(link_info != other_info);
3430 OSMO_ASSERT(link_info->tlli.assigned == local_bss_tlli3);
3431 OSMO_ASSERT(link_info->tlli.current == foreign_bss_tlli3);
3432 OSMO_ASSERT(link_info->tlli.bss_validated);
3433 OSMO_ASSERT(!link_info->tlli.net_validated);
3434 OSMO_ASSERT(link_info->sgsn_tlli.assigned == local_sgsn_tlli);
3435 OSMO_ASSERT(link_info->sgsn_tlli.current == random_sgsn_tlli3);
3436 OSMO_ASSERT(link_info->sgsn_tlli.bss_validated);
3437 OSMO_ASSERT(!link_info->sgsn_tlli.net_validated);
Jacob Erlbeck91a0e862014-09-17 10:56:38 +02003438
Jacob Erlbeckaf952ba2014-09-17 12:09:25 +02003439 send_llc_dl_ui(nsi, "GMM INFO", &sgsn_peer[1], 0x1002,
3440 local_sgsn_tlli, 1, imsi3, sizeof(imsi3),
3441 GPRS_SAPI_GMM, sgsn_nu++,
3442 dtap_gmm_information, sizeof(dtap_gmm_information));
3443
3444 dump_peers(stdout, 0, 0, &gbcfg);
3445
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +02003446 other_info = gbproxy_link_info_by_sgsn_tlli(peer, local_sgsn_tlli, SGSN_NSEI);
Jacob Erlbeck91a0e862014-09-17 10:56:38 +02003447 OSMO_ASSERT(other_info);
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +02003448 link_info = gbproxy_link_info_by_sgsn_tlli(peer, local_sgsn_tlli, SGSN2_NSEI);
3449 OSMO_ASSERT(link_info);
3450 OSMO_ASSERT(link_info != other_info);
3451 OSMO_ASSERT(link_info->tlli.current == local_bss_tlli3);
3452 OSMO_ASSERT(link_info->tlli.assigned == 0);
3453 OSMO_ASSERT(link_info->sgsn_tlli.current == local_sgsn_tlli);
3454 OSMO_ASSERT(link_info->sgsn_tlli.assigned == 0);
Jacob Erlbeck91a0e862014-09-17 10:56:38 +02003455
3456
Jacob Erlbeckf181f9e2014-08-27 12:44:25 +02003457 printf("--- Shutdown GPRS connection (SGSN 1) ---\n\n");
3458
3459 /* Detach */
3460 send_llc_ul_ui(nsi, "DETACH REQ", &bss_peer[0], 0x1002,
3461 local_bss_tlli, &rai_bss, cell_id,
3462 GPRS_SAPI_GMM, bss_nu++,
3463 dtap_detach_req, sizeof(dtap_detach_req));
3464
3465 dump_peers(stdout, 0, 0, &gbcfg);
3466
3467 send_llc_dl_ui(nsi, "DETACH ACC", &sgsn_peer[0], 0x1002,
3468 local_sgsn_tlli, 1, imsi1, sizeof(imsi1),
3469 GPRS_SAPI_GMM, sgsn_nu++,
3470 dtap_detach_acc, sizeof(dtap_detach_acc));
3471
3472 dump_peers(stdout, 0, 0, &gbcfg);
3473
3474 printf("--- Shutdown GPRS connection (SGSN 2) ---\n\n");
3475
3476 send_llc_ul_ui(nsi, "DETACH REQ", &bss_peer[0], 0x1002,
3477 local_bss_tlli2, &rai_bss, cell_id,
3478 GPRS_SAPI_GMM, bss_nu++,
3479 dtap_detach_req, sizeof(dtap_detach_req));
3480
3481 dump_peers(stdout, 0, 0, &gbcfg);
3482
3483 send_llc_dl_ui(nsi, "DETACH ACC", &sgsn_peer[1], 0x1002,
3484 local_sgsn_tlli2, 1, imsi2, sizeof(imsi2),
3485 GPRS_SAPI_GMM, sgsn_nu++,
3486 dtap_detach_acc, sizeof(dtap_detach_acc));
3487
3488 dump_peers(stdout, 0, 0, &gbcfg);
3489
Jacob Erlbeckaf952ba2014-09-17 12:09:25 +02003490 printf("--- Shutdown GPRS connection (SGSN 2, P-TMSI 1) ---\n\n");
3491
3492 send_llc_ul_ui(nsi, "DETACH REQ", &bss_peer[0], 0x1002,
3493 local_bss_tlli3, &rai_bss, cell_id,
3494 GPRS_SAPI_GMM, bss_nu++,
3495 dtap_detach_req, sizeof(dtap_detach_req));
3496
3497 dump_peers(stdout, 0, 0, &gbcfg);
3498
3499 send_llc_dl_ui(nsi, "DETACH ACC", &sgsn_peer[1], 0x1002,
3500 local_sgsn_tlli, 1, imsi3, sizeof(imsi3),
3501 GPRS_SAPI_GMM, sgsn_nu++,
3502 dtap_detach_acc, sizeof(dtap_detach_acc));
3503
3504 dump_peers(stdout, 0, 0, &gbcfg);
3505
Jacob Erlbeckf181f9e2014-08-27 12:44:25 +02003506 dump_global(stdout, 0);
3507
Jacob Erlbeckb36032c2014-09-25 13:21:48 +02003508 gbproxy_clear_patch_filter(&gbcfg.matches[GBPROX_MATCH_ROUTING]);
Jacob Erlbeckf181f9e2014-08-27 12:44:25 +02003509 gbprox_reset(&gbcfg);
3510 gprs_ns_destroy(nsi);
3511 nsi = NULL;
Daniel Willmannd1554ec2015-10-12 19:36:34 +02003512
3513 cleanup_test();
Jacob Erlbeckf181f9e2014-08-27 12:44:25 +02003514}
3515
Jacob Erlbeck772a22b2014-09-15 14:18:09 +02003516static void test_gbproxy_keep_info()
3517{
3518 struct gprs_ns_inst *nsi = gprs_ns_instantiate(gprs_ns_callback, NULL);
3519 struct sockaddr_in bss_peer[1] = {{0},};
3520 struct sockaddr_in sgsn_peer= {0};
3521 struct gprs_ra_id rai_bss =
3522 {.mcc = 112, .mnc = 332, .lac = 16464, .rac = 96};
3523 uint16_t cell_id = 0x1234;
3524
3525 const uint32_t ptmsi = 0xefe2b700;
3526 const uint32_t local_tlli = 0xefe2b700;
3527 const uint32_t foreign_tlli = 0xafe2b700;
3528
3529 const uint8_t imsi[] = {0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17, 0x18};
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +02003530 struct gbproxy_link_info *link_info, *link_info2;
Jacob Erlbeck772a22b2014-09-15 14:18:09 +02003531 struct gbproxy_peer *peer;
3532 unsigned bss_nu = 0;
3533 unsigned sgsn_nu = 0;
3534
Jacob Erlbeckfb83ed32014-09-22 19:16:06 +02003535 LLIST_HEAD(rcv_list);
3536
Jacob Erlbeck772a22b2014-09-15 14:18:09 +02003537 OSMO_ASSERT(local_tlli == gprs_tmsi2tlli(ptmsi, TLLI_LOCAL));
3538
3539 bssgp_nsi = nsi;
3540 gbcfg.nsi = bssgp_nsi;
3541 gbcfg.nsip_sgsn_nsei = SGSN_NSEI;
3542 gbcfg.patch_ptmsi = 0;
3543 gbcfg.acquire_imsi = 1;
Jacob Erlbeck772a22b2014-09-15 14:18:09 +02003544 gbcfg.core_mcc = 0;
3545 gbcfg.core_mnc = 0;
3546 gbcfg.core_apn = NULL;
3547 gbcfg.core_apn_size = 0;
3548 gbcfg.route_to_sgsn2 = 0;
3549 gbcfg.nsip_sgsn2_nsei = 0xffff;
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +02003550 gbcfg.keep_link_infos = GBPROX_KEEP_ALWAYS;
Jacob Erlbeck772a22b2014-09-15 14:18:09 +02003551
3552 configure_sgsn_peer(&sgsn_peer);
3553 configure_bss_peers(bss_peer, ARRAY_SIZE(bss_peer));
3554
3555 printf("=== %s ===\n", __func__);
3556 printf("--- Initialise SGSN ---\n\n");
3557
3558 connect_sgsn(nsi, &sgsn_peer, SGSN_NSEI);
3559
3560 printf("--- Initialise BSS 1 ---\n\n");
3561
3562 setup_ns(nsi, &bss_peer[0], 0x1001, 0x1000);
3563 setup_bssgp(nsi, &bss_peer[0], 0x1002);
3564
3565 peer = gbproxy_peer_by_nsei(&gbcfg, 0x1000);
3566 OSMO_ASSERT(peer != NULL);
3567
3568 send_bssgp_reset_ack(nsi, &sgsn_peer, 0x1002);
3569
3570 gprs_dump_nsi(nsi);
3571 dump_global(stdout, 0);
3572 dump_peers(stdout, 0, 0, &gbcfg);
3573
3574 printf("--- Send message from BSS 1 to SGSN, BVCI 0x1002 ---\n\n");
3575
Jacob Erlbeckfb83ed32014-09-22 19:16:06 +02003576 received_messages = &rcv_list;
3577
Jacob Erlbeck772a22b2014-09-15 14:18:09 +02003578 send_llc_ul_ui(nsi, "ATTACH REQUEST", &bss_peer[0], 0x1002,
3579 foreign_tlli, &rai_bss, cell_id,
3580 GPRS_SAPI_GMM, bss_nu++,
3581 dtap_attach_req, sizeof(dtap_attach_req));
3582
Jacob Erlbeckfb83ed32014-09-22 19:16:06 +02003583 OSMO_ASSERT(expect_gmm_msg(0x1000, 0x1002, GSM48_MT_GMM_ID_REQ));
3584
Jacob Erlbeck772a22b2014-09-15 14:18:09 +02003585 dump_peers(stdout, 0, 0, &gbcfg);
3586
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +02003587 link_info = gbproxy_link_info_by_tlli(peer, foreign_tlli);
3588 OSMO_ASSERT(link_info);
3589 OSMO_ASSERT(link_info->imsi_len == 0);
3590 OSMO_ASSERT(!link_info->is_deregistered);
3591 OSMO_ASSERT(link_info->imsi_acq_pending);
Jacob Erlbeck772a22b2014-09-15 14:18:09 +02003592
3593 send_llc_ul_ui(nsi, "IDENT RESPONSE", &bss_peer[0], 0x1002,
3594 foreign_tlli, &rai_bss, cell_id,
3595 GPRS_SAPI_GMM, bss_nu++,
3596 dtap_identity_resp, sizeof(dtap_identity_resp));
3597
Jacob Erlbeckfb83ed32014-09-22 19:16:06 +02003598 OSMO_ASSERT(expect_gmm_msg(SGSN_NSEI, 0x1002, GSM48_MT_GMM_ATTACH_REQ));
3599
Jacob Erlbeck772a22b2014-09-15 14:18:09 +02003600 dump_peers(stdout, 0, 0, &gbcfg);
3601
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +02003602 link_info = gbproxy_link_info_by_tlli(peer, foreign_tlli);
3603 OSMO_ASSERT(link_info);
3604 OSMO_ASSERT(link_info->imsi_len > 0);
3605 OSMO_ASSERT(!link_info->imsi_acq_pending);
Jacob Erlbeck9d0fb1e2014-10-31 10:43:44 +01003606 OSMO_ASSERT(gprs_tlli_type(link_info->sgsn_tlli.current) == TLLI_FOREIGN);
Jacob Erlbeck7430da62014-09-12 15:09:56 +02003607
Jacob Erlbeck772a22b2014-09-15 14:18:09 +02003608 send_llc_dl_ui(nsi, "IDENT REQUEST", &sgsn_peer, 0x1002,
3609 foreign_tlli, 0, NULL, 0,
3610 GPRS_SAPI_GMM, sgsn_nu++,
3611 dtap_identity_req, sizeof(dtap_identity_req));
3612
Jacob Erlbeckfb83ed32014-09-22 19:16:06 +02003613 OSMO_ASSERT(expect_gmm_msg(0x1000, 0x1002, GSM48_MT_GMM_ID_REQ));
3614
Jacob Erlbeck772a22b2014-09-15 14:18:09 +02003615 dump_peers(stdout, 0, 0, &gbcfg);
3616
3617 send_llc_ul_ui(nsi, "IDENT RESPONSE", &bss_peer[0], 0x1002,
3618 foreign_tlli, &rai_bss, cell_id,
3619 GPRS_SAPI_GMM, bss_nu++,
3620 dtap_identity_resp, sizeof(dtap_identity_resp));
3621
Jacob Erlbeckfb83ed32014-09-22 19:16:06 +02003622 OSMO_ASSERT(expect_gmm_msg(SGSN_NSEI, 0x1002, GSM48_MT_GMM_ID_RESP));
3623
Jacob Erlbeck772a22b2014-09-15 14:18:09 +02003624 dump_peers(stdout, 0, 0, &gbcfg);
3625
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +02003626 link_info = gbproxy_link_info_by_tlli(peer, foreign_tlli);
3627 OSMO_ASSERT(link_info);
3628 OSMO_ASSERT(link_info->imsi_len > 0);
3629 OSMO_ASSERT(gbproxy_link_info_by_imsi(peer, imsi, sizeof(imsi)));
Jacob Erlbeck772a22b2014-09-15 14:18:09 +02003630
3631 send_llc_dl_ui(nsi, "ATTACH ACCEPT", &sgsn_peer, 0x1002,
3632 foreign_tlli, 1, imsi, sizeof(imsi),
3633 GPRS_SAPI_GMM, sgsn_nu++,
3634 dtap_attach_acc, sizeof(dtap_attach_acc));
3635
Jacob Erlbeckfb83ed32014-09-22 19:16:06 +02003636 OSMO_ASSERT(expect_gmm_msg(0x1000, 0x1002, GSM48_MT_GMM_ATTACH_ACK));
3637
Jacob Erlbeck772a22b2014-09-15 14:18:09 +02003638 dump_peers(stdout, 0, 0, &gbcfg);
3639
3640 send_llc_ul_ui(nsi, "ATTACH COMPLETE", &bss_peer[0], 0x1002,
3641 local_tlli, &rai_bss, cell_id,
3642 GPRS_SAPI_GMM, bss_nu++,
3643 dtap_attach_complete, sizeof(dtap_attach_complete));
3644
Jacob Erlbeckfb83ed32014-09-22 19:16:06 +02003645 OSMO_ASSERT(expect_gmm_msg(SGSN_NSEI, 0x1002, GSM48_MT_GMM_ATTACH_COMPL));
3646
Jacob Erlbeck772a22b2014-09-15 14:18:09 +02003647 dump_peers(stdout, 0, 0, &gbcfg);
3648
3649 send_llc_dl_ui(nsi, "GMM INFO", &sgsn_peer, 0x1002,
3650 local_tlli, 1, imsi, sizeof(imsi),
3651 GPRS_SAPI_GMM, sgsn_nu++,
3652 dtap_gmm_information, sizeof(dtap_gmm_information));
3653
Jacob Erlbeckfb83ed32014-09-22 19:16:06 +02003654 OSMO_ASSERT(expect_gmm_msg(0x1000, 0x1002, GSM48_MT_GMM_INFO));
3655
Jacob Erlbeck772a22b2014-09-15 14:18:09 +02003656 dump_peers(stdout, 0, 0, &gbcfg);
3657
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +02003658 link_info = gbproxy_link_info_by_tlli(peer, local_tlli);
3659 OSMO_ASSERT(link_info);
Jacob Erlbeck772a22b2014-09-15 14:18:09 +02003660
3661 /* Detach (MO) */
3662 send_llc_ul_ui(nsi, "DETACH REQ", &bss_peer[0], 0x1002,
3663 local_tlli, &rai_bss, cell_id,
3664 GPRS_SAPI_GMM, bss_nu++,
3665 dtap_detach_req, sizeof(dtap_detach_req));
3666
Jacob Erlbeckfb83ed32014-09-22 19:16:06 +02003667 OSMO_ASSERT(expect_gmm_msg(SGSN_NSEI, 0x1002, GSM48_MT_GMM_DETACH_REQ));
3668
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +02003669 link_info = gbproxy_link_info_by_tlli(peer, local_tlli);
3670 OSMO_ASSERT(link_info);
Jacob Erlbeck772a22b2014-09-15 14:18:09 +02003671
3672 dump_peers(stdout, 0, 0, &gbcfg);
3673
3674 send_llc_dl_ui(nsi, "DETACH ACC", &sgsn_peer, 0x1002,
3675 local_tlli, 1, imsi, sizeof(imsi),
3676 GPRS_SAPI_GMM, sgsn_nu++,
3677 dtap_detach_acc, sizeof(dtap_detach_acc));
3678
Jacob Erlbeckfb83ed32014-09-22 19:16:06 +02003679 OSMO_ASSERT(expect_gmm_msg(0x1000, 0x1002, GSM48_MT_GMM_DETACH_ACK));
3680
Jacob Erlbeck772a22b2014-09-15 14:18:09 +02003681 dump_peers(stdout, 0, 0, &gbcfg);
3682
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +02003683 OSMO_ASSERT(!gbproxy_link_info_by_tlli(peer, local_tlli));
3684 link_info = gbproxy_link_info_by_imsi(peer, imsi, sizeof(imsi));
3685 OSMO_ASSERT(link_info);
3686 OSMO_ASSERT(link_info->is_deregistered);
Jacob Erlbeck772a22b2014-09-15 14:18:09 +02003687
Jacob Erlbeckfb83ed32014-09-22 19:16:06 +02003688 OSMO_ASSERT(!expect_msg());
3689
Jacob Erlbeck772a22b2014-09-15 14:18:09 +02003690 /* Re-Attach */
3691 send_llc_ul_ui(nsi, "ATTACH REQUEST", &bss_peer[0], 0x1002,
3692 foreign_tlli, &rai_bss, cell_id,
3693 GPRS_SAPI_GMM, bss_nu++,
3694 dtap_attach_req3, sizeof(dtap_attach_req3));
3695
Jacob Erlbeckfb83ed32014-09-22 19:16:06 +02003696 OSMO_ASSERT(expect_gmm_msg(SGSN_NSEI, 0x1002, GSM48_MT_GMM_ATTACH_REQ));
3697
Jacob Erlbeck772a22b2014-09-15 14:18:09 +02003698 dump_peers(stdout, 0, 0, &gbcfg);
3699
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +02003700 link_info2 = gbproxy_link_info_by_imsi(peer, imsi, sizeof(imsi));
3701 link_info = gbproxy_link_info_by_tlli(peer, foreign_tlli);
3702 OSMO_ASSERT(link_info);
3703 OSMO_ASSERT(link_info == link_info2);
3704 OSMO_ASSERT(link_info->imsi_len != 0);
3705 OSMO_ASSERT(!link_info->is_deregistered);
3706 OSMO_ASSERT(!link_info->imsi_acq_pending);
Jacob Erlbeck9d0fb1e2014-10-31 10:43:44 +01003707 OSMO_ASSERT(gprs_tlli_type(link_info->sgsn_tlli.current) == TLLI_FOREIGN);
Jacob Erlbeck7430da62014-09-12 15:09:56 +02003708
Jacob Erlbeck772a22b2014-09-15 14:18:09 +02003709 send_llc_dl_ui(nsi, "ATTACH ACCEPT", &sgsn_peer, 0x1002,
3710 foreign_tlli, 1, imsi, sizeof(imsi),
3711 GPRS_SAPI_GMM, sgsn_nu++,
3712 dtap_attach_acc, sizeof(dtap_attach_acc));
3713
Jacob Erlbeckfb83ed32014-09-22 19:16:06 +02003714 OSMO_ASSERT(expect_gmm_msg(0x1000, 0x1002, GSM48_MT_GMM_ATTACH_ACK));
3715
Jacob Erlbeck772a22b2014-09-15 14:18:09 +02003716 dump_peers(stdout, 0, 0, &gbcfg);
3717
3718 send_llc_ul_ui(nsi, "ATTACH COMPLETE", &bss_peer[0], 0x1002,
3719 local_tlli, &rai_bss, cell_id,
3720 GPRS_SAPI_GMM, bss_nu++,
3721 dtap_attach_complete, sizeof(dtap_attach_complete));
3722
Jacob Erlbeckfb83ed32014-09-22 19:16:06 +02003723 OSMO_ASSERT(expect_gmm_msg(SGSN_NSEI, 0x1002, GSM48_MT_GMM_ATTACH_COMPL));
3724
Jacob Erlbeck772a22b2014-09-15 14:18:09 +02003725 dump_peers(stdout, 0, 0, &gbcfg);
3726
3727 /* Detach (MT) */
3728 send_llc_dl_ui(nsi, "DETACH REQ (re-attach)", &sgsn_peer, 0x1002,
3729 local_tlli, 1, imsi, sizeof(imsi),
3730 GPRS_SAPI_GMM, sgsn_nu++,
3731 dtap_mt_detach_rea_req, sizeof(dtap_mt_detach_rea_req));
3732
Jacob Erlbeckfb83ed32014-09-22 19:16:06 +02003733 OSMO_ASSERT(expect_gmm_msg(0x1000, 0x1002, GSM48_MT_GMM_DETACH_REQ));
3734
Jacob Erlbeck772a22b2014-09-15 14:18:09 +02003735 dump_peers(stdout, 0, 0, &gbcfg);
3736
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +02003737 link_info = gbproxy_link_info_by_tlli(peer, local_tlli);
3738 OSMO_ASSERT(link_info);
Jacob Erlbeck772a22b2014-09-15 14:18:09 +02003739
Jacob Erlbeckfb83ed32014-09-22 19:16:06 +02003740 send_llc_ul_ui(nsi, "DETACH ACC", &bss_peer[0], 0x1002,
Jacob Erlbeck772a22b2014-09-15 14:18:09 +02003741 local_tlli, &rai_bss, cell_id,
3742 GPRS_SAPI_GMM, bss_nu++,
3743 dtap_mt_detach_acc, sizeof(dtap_mt_detach_acc));
3744
Jacob Erlbeckfb83ed32014-09-22 19:16:06 +02003745 OSMO_ASSERT(expect_gmm_msg(SGSN_NSEI, 0x1002, GSM48_MT_GMM_DETACH_ACK));
3746 OSMO_ASSERT(!expect_msg());
3747
Jacob Erlbeck772a22b2014-09-15 14:18:09 +02003748 dump_peers(stdout, 0, 0, &gbcfg);
3749
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +02003750 OSMO_ASSERT(!gbproxy_link_info_by_tlli(peer, local_tlli));
3751 link_info = gbproxy_link_info_by_imsi(peer, imsi, sizeof(imsi));
3752 OSMO_ASSERT(link_info);
3753 OSMO_ASSERT(link_info->is_deregistered);
Jacob Erlbeck772a22b2014-09-15 14:18:09 +02003754
3755 /* Re-Attach */
3756 send_llc_ul_ui(nsi, "ATTACH REQUEST", &bss_peer[0], 0x1002,
3757 foreign_tlli, &rai_bss, cell_id,
3758 GPRS_SAPI_GMM, bss_nu++,
3759 dtap_attach_req3, sizeof(dtap_attach_req3));
3760
Jacob Erlbeckfb83ed32014-09-22 19:16:06 +02003761 OSMO_ASSERT(expect_gmm_msg(SGSN_NSEI, 0x1002, GSM48_MT_GMM_ATTACH_REQ));
3762
Jacob Erlbeck772a22b2014-09-15 14:18:09 +02003763 dump_peers(stdout, 0, 0, &gbcfg);
3764
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +02003765 link_info2 = gbproxy_link_info_by_imsi(peer, imsi, sizeof(imsi));
3766 link_info = gbproxy_link_info_by_tlli(peer, foreign_tlli);
3767 OSMO_ASSERT(link_info);
3768 OSMO_ASSERT(link_info == link_info2);
3769 OSMO_ASSERT(link_info->imsi_len != 0);
3770 OSMO_ASSERT(!link_info->is_deregistered);
3771 OSMO_ASSERT(!link_info->imsi_acq_pending);
Jacob Erlbeck7430da62014-09-12 15:09:56 +02003772
Jacob Erlbeck772a22b2014-09-15 14:18:09 +02003773 send_llc_dl_ui(nsi, "ATTACH ACCEPT", &sgsn_peer, 0x1002,
3774 foreign_tlli, 1, imsi, sizeof(imsi),
3775 GPRS_SAPI_GMM, sgsn_nu++,
3776 dtap_attach_acc, sizeof(dtap_attach_acc));
3777
Jacob Erlbeckfb83ed32014-09-22 19:16:06 +02003778 OSMO_ASSERT(expect_gmm_msg(0x1000, 0x1002, GSM48_MT_GMM_ATTACH_ACK));
3779
Jacob Erlbeck772a22b2014-09-15 14:18:09 +02003780 dump_peers(stdout, 0, 0, &gbcfg);
3781
3782 send_llc_ul_ui(nsi, "ATTACH COMPLETE", &bss_peer[0], 0x1002,
3783 local_tlli, &rai_bss, cell_id,
3784 GPRS_SAPI_GMM, bss_nu++,
3785 dtap_attach_complete, sizeof(dtap_attach_complete));
3786
Jacob Erlbeckfb83ed32014-09-22 19:16:06 +02003787 OSMO_ASSERT(expect_gmm_msg(SGSN_NSEI, 0x1002, GSM48_MT_GMM_ATTACH_COMPL));
3788
Jacob Erlbeck772a22b2014-09-15 14:18:09 +02003789 dump_peers(stdout, 0, 0, &gbcfg);
3790
3791 /* Detach (MT) */
3792 send_llc_dl_ui(nsi, "DETACH REQ", &sgsn_peer, 0x1002,
3793 local_tlli, 1, imsi, sizeof(imsi),
3794 GPRS_SAPI_GMM, sgsn_nu++,
3795 dtap_mt_detach_req, sizeof(dtap_mt_detach_req));
3796
Jacob Erlbeckfb83ed32014-09-22 19:16:06 +02003797 OSMO_ASSERT(expect_gmm_msg(0x1000, 0x1002, GSM48_MT_GMM_DETACH_REQ));
3798
Jacob Erlbeck772a22b2014-09-15 14:18:09 +02003799 dump_peers(stdout, 0, 0, &gbcfg);
3800
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +02003801 link_info = gbproxy_link_info_by_tlli(peer, local_tlli);
3802 OSMO_ASSERT(link_info);
Jacob Erlbeck772a22b2014-09-15 14:18:09 +02003803
Jacob Erlbeckfb83ed32014-09-22 19:16:06 +02003804 send_llc_ul_ui(nsi, "DETACH ACC", &bss_peer[0], 0x1002,
Jacob Erlbeck772a22b2014-09-15 14:18:09 +02003805 local_tlli, &rai_bss, cell_id,
3806 GPRS_SAPI_GMM, bss_nu++,
3807 dtap_mt_detach_acc, sizeof(dtap_mt_detach_acc));
3808
Jacob Erlbeckfb83ed32014-09-22 19:16:06 +02003809 OSMO_ASSERT(expect_gmm_msg(SGSN_NSEI, 0x1002, GSM48_MT_GMM_DETACH_ACK));
3810 OSMO_ASSERT(!expect_msg());
3811
Jacob Erlbeck772a22b2014-09-15 14:18:09 +02003812 dump_peers(stdout, 0, 0, &gbcfg);
3813
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +02003814 OSMO_ASSERT(!gbproxy_link_info_by_tlli(peer, local_tlli));
3815 link_info = gbproxy_link_info_by_imsi(peer, imsi, sizeof(imsi));
3816 OSMO_ASSERT(link_info);
3817 OSMO_ASSERT(link_info->is_deregistered);
Jacob Erlbeck772a22b2014-09-15 14:18:09 +02003818
Jacob Erlbeck9d0fb1e2014-10-31 10:43:44 +01003819 /* Re-Attach with IMSI */
3820 send_llc_ul_ui(nsi, "ATTACH REQUEST (IMSI)", &bss_peer[0], 0x1002,
3821 foreign_tlli, &rai_bss, cell_id,
3822 GPRS_SAPI_GMM, bss_nu++,
3823 dtap_attach_req4, sizeof(dtap_attach_req4));
3824
3825 OSMO_ASSERT(expect_gmm_msg(SGSN_NSEI, 0x1002, GSM48_MT_GMM_ATTACH_REQ));
3826
3827 dump_peers(stdout, 0, 0, &gbcfg);
3828
3829 link_info2 = gbproxy_link_info_by_imsi(peer, imsi, sizeof(imsi));
3830 link_info = gbproxy_link_info_by_tlli(peer, foreign_tlli);
3831 OSMO_ASSERT(link_info);
3832 OSMO_ASSERT(link_info == link_info2);
3833 OSMO_ASSERT(link_info->imsi_len != 0);
3834 OSMO_ASSERT(!link_info->is_deregistered);
3835 OSMO_ASSERT(!link_info->imsi_acq_pending);
3836 OSMO_ASSERT(link_info->sgsn_tlli.current == foreign_tlli);
3837
3838 send_llc_dl_ui(nsi, "ATTACH ACCEPT", &sgsn_peer, 0x1002,
3839 foreign_tlli, 1, imsi, sizeof(imsi),
3840 GPRS_SAPI_GMM, sgsn_nu++,
3841 dtap_attach_acc, sizeof(dtap_attach_acc));
3842
3843 OSMO_ASSERT(expect_gmm_msg(0x1000, 0x1002, GSM48_MT_GMM_ATTACH_ACK));
3844
3845 dump_peers(stdout, 0, 0, &gbcfg);
3846
3847 send_llc_ul_ui(nsi, "ATTACH COMPLETE", &bss_peer[0], 0x1002,
3848 local_tlli, &rai_bss, cell_id,
3849 GPRS_SAPI_GMM, bss_nu++,
3850 dtap_attach_complete, sizeof(dtap_attach_complete));
3851
3852 OSMO_ASSERT(expect_gmm_msg(SGSN_NSEI, 0x1002, GSM48_MT_GMM_ATTACH_COMPL));
3853
3854 dump_peers(stdout, 0, 0, &gbcfg);
3855
3856 /* Detach (MT) */
3857 send_llc_dl_ui(nsi, "DETACH REQ", &sgsn_peer, 0x1002,
3858 local_tlli, 1, imsi, sizeof(imsi),
3859 GPRS_SAPI_GMM, sgsn_nu++,
3860 dtap_mt_detach_req, sizeof(dtap_mt_detach_req));
3861
3862 OSMO_ASSERT(expect_gmm_msg(0x1000, 0x1002, GSM48_MT_GMM_DETACH_REQ));
3863
3864 dump_peers(stdout, 0, 0, &gbcfg);
3865
3866 link_info = gbproxy_link_info_by_tlli(peer, local_tlli);
3867 OSMO_ASSERT(link_info);
3868
3869 send_llc_ul_ui(nsi, "DETACH ACC", &bss_peer[0], 0x1002,
3870 local_tlli, &rai_bss, cell_id,
3871 GPRS_SAPI_GMM, bss_nu++,
3872 dtap_mt_detach_acc, sizeof(dtap_mt_detach_acc));
3873
3874 OSMO_ASSERT(expect_gmm_msg(SGSN_NSEI, 0x1002, GSM48_MT_GMM_DETACH_ACK));
3875 OSMO_ASSERT(!expect_msg());
3876
3877 dump_peers(stdout, 0, 0, &gbcfg);
3878
3879 OSMO_ASSERT(!gbproxy_link_info_by_tlli(peer, local_tlli));
3880 link_info = gbproxy_link_info_by_imsi(peer, imsi, sizeof(imsi));
3881 OSMO_ASSERT(link_info);
3882 OSMO_ASSERT(link_info->is_deregistered);
3883
Jacob Erlbeck772a22b2014-09-15 14:18:09 +02003884 /* Re-Attach */
3885 send_llc_ul_ui(nsi, "ATTACH REQUEST", &bss_peer[0], 0x1002,
3886 foreign_tlli, &rai_bss, cell_id,
3887 GPRS_SAPI_GMM, bss_nu++,
3888 dtap_attach_req3, sizeof(dtap_attach_req3));
3889
Jacob Erlbeckfb83ed32014-09-22 19:16:06 +02003890 OSMO_ASSERT(expect_gmm_msg(SGSN_NSEI, 0x1002, GSM48_MT_GMM_ATTACH_REQ));
3891
Jacob Erlbeck772a22b2014-09-15 14:18:09 +02003892 dump_peers(stdout, 0, 0, &gbcfg);
3893
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +02003894 link_info2 = gbproxy_link_info_by_imsi(peer, imsi, sizeof(imsi));
3895 link_info = gbproxy_link_info_by_tlli(peer, foreign_tlli);
3896 OSMO_ASSERT(link_info);
3897 OSMO_ASSERT(link_info == link_info2);
3898 OSMO_ASSERT(link_info->imsi_len != 0);
3899 OSMO_ASSERT(!link_info->is_deregistered);
3900 OSMO_ASSERT(!link_info->imsi_acq_pending);
Jacob Erlbeck7430da62014-09-12 15:09:56 +02003901
Jacob Erlbeck772a22b2014-09-15 14:18:09 +02003902 send_llc_dl_ui(nsi, "ATTACH ACCEPT", &sgsn_peer, 0x1002,
3903 foreign_tlli, 1, imsi, sizeof(imsi),
3904 GPRS_SAPI_GMM, sgsn_nu++,
3905 dtap_attach_acc, sizeof(dtap_attach_acc));
3906
Jacob Erlbeckfb83ed32014-09-22 19:16:06 +02003907 OSMO_ASSERT(expect_gmm_msg(0x1000, 0x1002, GSM48_MT_GMM_ATTACH_ACK));
3908
Jacob Erlbeck772a22b2014-09-15 14:18:09 +02003909 dump_peers(stdout, 0, 0, &gbcfg);
3910
3911 send_llc_ul_ui(nsi, "ATTACH COMPLETE", &bss_peer[0], 0x1002,
3912 local_tlli, &rai_bss, cell_id,
3913 GPRS_SAPI_GMM, bss_nu++,
3914 dtap_attach_complete, sizeof(dtap_attach_complete));
3915
Jacob Erlbeckfb83ed32014-09-22 19:16:06 +02003916 OSMO_ASSERT(expect_gmm_msg(SGSN_NSEI, 0x1002, GSM48_MT_GMM_ATTACH_COMPL));
3917
Jacob Erlbeck772a22b2014-09-15 14:18:09 +02003918 dump_peers(stdout, 0, 0, &gbcfg);
3919
3920 /* RA update procedure (reject -> Detach) */
3921 send_llc_ul_ui(nsi, "RA UPD REQ", &bss_peer[0], 0x1002,
3922 local_tlli, &rai_bss, 0x7080,
3923 GPRS_SAPI_GMM, bss_nu++,
3924 dtap_ra_upd_req, sizeof(dtap_ra_upd_req));
3925
Jacob Erlbeckfb83ed32014-09-22 19:16:06 +02003926 OSMO_ASSERT(expect_gmm_msg(SGSN_NSEI, 0x1002, GSM48_MT_GMM_RA_UPD_REQ));
3927
Jacob Erlbeck772a22b2014-09-15 14:18:09 +02003928 send_llc_dl_ui(nsi, "RA UDP REJ", &sgsn_peer, 0x1002,
3929 local_tlli, 1, imsi, sizeof(imsi),
3930 GPRS_SAPI_GMM, sgsn_nu++,
3931 dtap_ra_upd_rej, sizeof(dtap_ra_upd_rej));
3932
Jacob Erlbeckfb83ed32014-09-22 19:16:06 +02003933 OSMO_ASSERT(expect_gmm_msg(0x1000, 0x1002, GSM48_MT_GMM_RA_UPD_REJ));
3934 OSMO_ASSERT(!expect_msg());
3935
Jacob Erlbeck772a22b2014-09-15 14:18:09 +02003936 dump_peers(stdout, 0, 0, &gbcfg);
3937
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +02003938 OSMO_ASSERT(!gbproxy_link_info_by_tlli(peer, local_tlli));
3939 link_info = gbproxy_link_info_by_imsi(peer, imsi, sizeof(imsi));
3940 OSMO_ASSERT(link_info);
3941 OSMO_ASSERT(link_info->is_deregistered);
Jacob Erlbeck7430da62014-09-12 15:09:56 +02003942
Jacob Erlbeck772a22b2014-09-15 14:18:09 +02003943 /* Bad case: Re-Attach with wrong (initial) P-TMSI */
3944 send_llc_ul_ui(nsi, "ATTACH REQUEST", &bss_peer[0], 0x1002,
3945 foreign_tlli, &rai_bss, cell_id,
3946 GPRS_SAPI_GMM, bss_nu++,
3947 dtap_attach_req, sizeof(dtap_attach_req));
3948
Jacob Erlbeckfb83ed32014-09-22 19:16:06 +02003949 OSMO_ASSERT(expect_gmm_msg(0x1000, 0x1002, GSM48_MT_GMM_ID_REQ));
3950
Jacob Erlbeck772a22b2014-09-15 14:18:09 +02003951 dump_peers(stdout, 0, 0, &gbcfg);
3952
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +02003953 link_info2 = gbproxy_link_info_by_imsi(peer, imsi, sizeof(imsi));
3954 link_info = gbproxy_link_info_by_tlli(peer, foreign_tlli);
3955 OSMO_ASSERT(link_info);
3956 OSMO_ASSERT(link_info != link_info2);
3957 OSMO_ASSERT(link_info->imsi_len == 0);
3958 OSMO_ASSERT(!link_info->is_deregistered);
3959 OSMO_ASSERT(link_info->imsi_acq_pending);
Jacob Erlbeck7430da62014-09-12 15:09:56 +02003960
Jacob Erlbeck2bf32612014-09-22 11:26:58 +02003961 send_llc_ul_ui(nsi, "IDENT RESPONSE", &bss_peer[0], 0x1002,
3962 foreign_tlli, &rai_bss, cell_id,
3963 GPRS_SAPI_GMM, bss_nu++,
3964 dtap_identity_resp, sizeof(dtap_identity_resp));
3965
Jacob Erlbeckfb83ed32014-09-22 19:16:06 +02003966 OSMO_ASSERT(expect_gmm_msg(SGSN_NSEI, 0x1002, GSM48_MT_GMM_ATTACH_REQ));
3967
Jacob Erlbeck2bf32612014-09-22 11:26:58 +02003968 dump_peers(stdout, 0, 0, &gbcfg);
3969
3970 link_info2 = gbproxy_link_info_by_imsi(peer, imsi, sizeof(imsi));
3971 link_info = gbproxy_link_info_by_tlli(peer, foreign_tlli);
3972 OSMO_ASSERT(link_info);
3973 OSMO_ASSERT(link_info == link_info2);
3974 OSMO_ASSERT(link_info->imsi_len != 0);
3975 OSMO_ASSERT(!link_info->is_deregistered);
3976 OSMO_ASSERT(!link_info->imsi_acq_pending);
3977
Jacob Erlbeck772a22b2014-09-15 14:18:09 +02003978 send_llc_dl_ui(nsi, "ATTACH ACCEPT", &sgsn_peer, 0x1002,
3979 foreign_tlli, 1, imsi, sizeof(imsi),
3980 GPRS_SAPI_GMM, sgsn_nu++,
3981 dtap_attach_acc, sizeof(dtap_attach_acc));
3982
Jacob Erlbeckfb83ed32014-09-22 19:16:06 +02003983 OSMO_ASSERT(expect_gmm_msg(0x1000, 0x1002, GSM48_MT_GMM_ATTACH_ACK));
3984
Jacob Erlbeck772a22b2014-09-15 14:18:09 +02003985 dump_peers(stdout, 0, 0, &gbcfg);
3986
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +02003987 link_info2 = gbproxy_link_info_by_imsi(peer, imsi, sizeof(imsi));
3988 link_info = gbproxy_link_info_by_tlli(peer, foreign_tlli);
3989 OSMO_ASSERT(link_info);
3990 OSMO_ASSERT(link_info == link_info2);
Jacob Erlbeckea71b482014-09-22 09:28:27 +02003991 OSMO_ASSERT(link_info->imsi_len > 0);
Jacob Erlbeck7430da62014-09-12 15:09:56 +02003992
Jacob Erlbeck772a22b2014-09-15 14:18:09 +02003993 send_llc_ul_ui(nsi, "ATTACH COMPLETE", &bss_peer[0], 0x1002,
3994 local_tlli, &rai_bss, cell_id,
3995 GPRS_SAPI_GMM, bss_nu++,
3996 dtap_attach_complete, sizeof(dtap_attach_complete));
3997
Jacob Erlbeckfb83ed32014-09-22 19:16:06 +02003998 OSMO_ASSERT(expect_gmm_msg(SGSN_NSEI, 0x1002, GSM48_MT_GMM_ATTACH_COMPL));
3999
Jacob Erlbeck772a22b2014-09-15 14:18:09 +02004000 dump_peers(stdout, 0, 0, &gbcfg);
4001
4002 /* Detach (MT) */
4003 send_llc_dl_ui(nsi, "DETACH REQ", &sgsn_peer, 0x1002,
4004 local_tlli, 1, imsi, sizeof(imsi),
4005 GPRS_SAPI_GMM, sgsn_nu++,
4006 dtap_mt_detach_req, sizeof(dtap_mt_detach_req));
4007
Jacob Erlbeckfb83ed32014-09-22 19:16:06 +02004008 OSMO_ASSERT(expect_gmm_msg(0x1000, 0x1002, GSM48_MT_GMM_DETACH_REQ));
4009
Jacob Erlbeck772a22b2014-09-15 14:18:09 +02004010 dump_peers(stdout, 0, 0, &gbcfg);
4011
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +02004012 link_info = gbproxy_link_info_by_tlli(peer, local_tlli);
4013 OSMO_ASSERT(link_info);
Jacob Erlbeck772a22b2014-09-15 14:18:09 +02004014
Jacob Erlbeckfb83ed32014-09-22 19:16:06 +02004015 send_llc_ul_ui(nsi, "DETACH ACC", &bss_peer[0], 0x1002,
Jacob Erlbeck772a22b2014-09-15 14:18:09 +02004016 local_tlli, &rai_bss, cell_id,
4017 GPRS_SAPI_GMM, bss_nu++,
4018 dtap_mt_detach_acc, sizeof(dtap_mt_detach_acc));
4019
Jacob Erlbeckfb83ed32014-09-22 19:16:06 +02004020 OSMO_ASSERT(expect_gmm_msg(SGSN_NSEI, 0x1002, GSM48_MT_GMM_DETACH_ACK));
4021
Jacob Erlbeck772a22b2014-09-15 14:18:09 +02004022 dump_peers(stdout, 0, 0, &gbcfg);
4023
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +02004024 OSMO_ASSERT(!gbproxy_link_info_by_tlli(peer, local_tlli));
4025 link_info = gbproxy_link_info_by_imsi(peer, imsi, sizeof(imsi));
4026 OSMO_ASSERT(link_info);
4027 OSMO_ASSERT(link_info->is_deregistered);
Jacob Erlbeck7430da62014-09-12 15:09:56 +02004028
Jacob Erlbeckfb83ed32014-09-22 19:16:06 +02004029 OSMO_ASSERT(!expect_msg());
4030
Jacob Erlbeck9d0fb1e2014-10-31 10:43:44 +01004031 /* Bad case: Re-Attach with local TLLI */
4032 send_llc_ul_ui(nsi, "ATTACH REQUEST (local TLLI)", &bss_peer[0], 0x1002,
4033 local_tlli, &rai_bss, cell_id,
4034 GPRS_SAPI_GMM, bss_nu++,
4035 dtap_attach_req3, sizeof(dtap_attach_req3));
4036
4037 OSMO_ASSERT(expect_gmm_msg(SGSN_NSEI, 0x1002, GSM48_MT_GMM_ATTACH_REQ));
4038
4039 dump_peers(stdout, 0, 0, &gbcfg);
4040
4041 link_info2 = gbproxy_link_info_by_imsi(peer, imsi, sizeof(imsi));
4042 link_info = gbproxy_link_info_by_tlli(peer, local_tlli);
4043 OSMO_ASSERT(link_info);
4044 OSMO_ASSERT(link_info == link_info2);
4045 OSMO_ASSERT(link_info->imsi_len != 0);
4046 OSMO_ASSERT(!link_info->is_deregistered);
4047 OSMO_ASSERT(!link_info->imsi_acq_pending);
4048 OSMO_ASSERT(link_info->sgsn_tlli.current == local_tlli);
4049
4050 send_llc_dl_ui(nsi, "ATTACH ACCEPT", &sgsn_peer, 0x1002,
4051 local_tlli, 1, imsi, sizeof(imsi),
4052 GPRS_SAPI_GMM, sgsn_nu++,
4053 dtap_attach_acc, sizeof(dtap_attach_acc));
4054
4055 OSMO_ASSERT(expect_gmm_msg(0x1000, 0x1002, GSM48_MT_GMM_ATTACH_ACK));
4056
4057 dump_peers(stdout, 0, 0, &gbcfg);
4058
4059 send_llc_ul_ui(nsi, "ATTACH COMPLETE", &bss_peer[0], 0x1002,
4060 local_tlli, &rai_bss, cell_id,
4061 GPRS_SAPI_GMM, bss_nu++,
4062 dtap_attach_complete, sizeof(dtap_attach_complete));
4063
4064 OSMO_ASSERT(expect_gmm_msg(SGSN_NSEI, 0x1002, GSM48_MT_GMM_ATTACH_COMPL));
4065
4066 dump_peers(stdout, 0, 0, &gbcfg);
4067
4068 /* Detach (MT) */
4069 send_llc_dl_ui(nsi, "DETACH REQ (re-attach)", &sgsn_peer, 0x1002,
4070 local_tlli, 1, imsi, sizeof(imsi),
4071 GPRS_SAPI_GMM, sgsn_nu++,
4072 dtap_mt_detach_rea_req, sizeof(dtap_mt_detach_rea_req));
4073
4074 OSMO_ASSERT(expect_gmm_msg(0x1000, 0x1002, GSM48_MT_GMM_DETACH_REQ));
4075
4076 dump_peers(stdout, 0, 0, &gbcfg);
4077
4078 link_info = gbproxy_link_info_by_tlli(peer, local_tlli);
4079 OSMO_ASSERT(link_info);
4080
4081 send_llc_ul_ui(nsi, "DETACH ACC", &bss_peer[0], 0x1002,
4082 local_tlli, &rai_bss, cell_id,
4083 GPRS_SAPI_GMM, bss_nu++,
4084 dtap_mt_detach_acc, sizeof(dtap_mt_detach_acc));
4085
4086 OSMO_ASSERT(expect_gmm_msg(SGSN_NSEI, 0x1002, GSM48_MT_GMM_DETACH_ACK));
4087 OSMO_ASSERT(!expect_msg());
4088
4089 dump_peers(stdout, 0, 0, &gbcfg);
4090
4091 OSMO_ASSERT(!gbproxy_link_info_by_tlli(peer, local_tlli));
4092 link_info = gbproxy_link_info_by_imsi(peer, imsi, sizeof(imsi));
4093 OSMO_ASSERT(link_info);
4094 OSMO_ASSERT(link_info->is_deregistered);
4095
4096 /* Bad case: Unexpected Re-Attach with IMSI after completed attachment
4097 * procedure */
4098 send_llc_ul_ui(nsi, "ATTACH REQUEST", &bss_peer[0], 0x1002,
4099 foreign_tlli, &rai_bss, cell_id,
4100 GPRS_SAPI_GMM, bss_nu++,
4101 dtap_attach_req3, sizeof(dtap_attach_req3));
4102
4103 OSMO_ASSERT(expect_gmm_msg(SGSN_NSEI, 0x1002, GSM48_MT_GMM_ATTACH_REQ));
4104
4105 dump_peers(stdout, 0, 0, &gbcfg);
4106
4107 link_info2 = gbproxy_link_info_by_imsi(peer, imsi, sizeof(imsi));
4108 link_info = gbproxy_link_info_by_tlli(peer, foreign_tlli);
4109 OSMO_ASSERT(link_info);
4110 OSMO_ASSERT(link_info == link_info2);
4111 OSMO_ASSERT(link_info->imsi_len != 0);
4112 OSMO_ASSERT(!link_info->is_deregistered);
4113 OSMO_ASSERT(!link_info->imsi_acq_pending);
4114
4115 send_llc_dl_ui(nsi, "ATTACH ACCEPT", &sgsn_peer, 0x1002,
4116 foreign_tlli, 1, imsi, sizeof(imsi),
4117 GPRS_SAPI_GMM, sgsn_nu++,
4118 dtap_attach_acc, sizeof(dtap_attach_acc));
4119
4120 OSMO_ASSERT(expect_gmm_msg(0x1000, 0x1002, GSM48_MT_GMM_ATTACH_ACK));
4121
4122 dump_peers(stdout, 0, 0, &gbcfg);
4123
4124 send_llc_ul_ui(nsi, "ATTACH COMPLETE", &bss_peer[0], 0x1002,
4125 local_tlli, &rai_bss, cell_id,
4126 GPRS_SAPI_GMM, bss_nu++,
4127 dtap_attach_complete, sizeof(dtap_attach_complete));
4128
4129 OSMO_ASSERT(expect_gmm_msg(SGSN_NSEI, 0x1002, GSM48_MT_GMM_ATTACH_COMPL));
4130
4131 dump_peers(stdout, 0, 0, &gbcfg);
4132
4133 send_llc_dl_ui(nsi, "GMM INFO", &sgsn_peer, 0x1002,
4134 local_tlli, 1, imsi, sizeof(imsi),
4135 GPRS_SAPI_GMM, sgsn_nu++,
4136 dtap_gmm_information, sizeof(dtap_gmm_information));
4137
4138 OSMO_ASSERT(expect_gmm_msg(0x1000, 0x1002, GSM48_MT_GMM_INFO));
4139
4140 dump_peers(stdout, 0, 0, &gbcfg);
4141
4142 send_llc_ul_ui(nsi, "ATTACH REQUEST (unexpected, IMSI)",
4143 &bss_peer[0], 0x1002,
4144 foreign_tlli, &rai_bss, cell_id,
4145 GPRS_SAPI_GMM, bss_nu++,
4146 dtap_attach_req4, sizeof(dtap_attach_req4));
4147
4148 OSMO_ASSERT(expect_gmm_msg(SGSN_NSEI, 0x1002, GSM48_MT_GMM_ATTACH_REQ));
4149
4150 dump_peers(stdout, 0, 0, &gbcfg);
4151
4152 link_info2 = gbproxy_link_info_by_imsi(peer, imsi, sizeof(imsi));
4153 link_info = gbproxy_link_info_by_tlli(peer, foreign_tlli);
Jacob Erlbeck59ac49d2014-10-30 17:15:43 +01004154 OSMO_ASSERT(link_info);
Jacob Erlbeck9d0fb1e2014-10-31 10:43:44 +01004155 OSMO_ASSERT(link_info == link_info2);
4156 OSMO_ASSERT(link_info->imsi_len != 0);
4157 OSMO_ASSERT(!link_info->is_deregistered);
4158 OSMO_ASSERT(!link_info->imsi_acq_pending);
Jacob Erlbeck59ac49d2014-10-30 17:15:43 +01004159 OSMO_ASSERT(link_info->sgsn_tlli.current == foreign_tlli);
Jacob Erlbeck9d0fb1e2014-10-31 10:43:44 +01004160 OSMO_ASSERT(link_info->sgsn_tlli.assigned == 0);
4161
4162 send_llc_dl_ui(nsi, "ATTACH ACCEPT", &sgsn_peer, 0x1002,
4163 foreign_tlli, 1, imsi, sizeof(imsi),
4164 GPRS_SAPI_GMM, sgsn_nu++,
4165 dtap_attach_acc, sizeof(dtap_attach_acc));
4166
4167 OSMO_ASSERT(expect_gmm_msg(0x1000, 0x1002, GSM48_MT_GMM_ATTACH_ACK));
4168
4169 dump_peers(stdout, 0, 0, &gbcfg);
4170
4171 send_llc_ul_ui(nsi, "ATTACH COMPLETE", &bss_peer[0], 0x1002,
4172 local_tlli, &rai_bss, cell_id,
4173 GPRS_SAPI_GMM, bss_nu++,
4174 dtap_attach_complete, sizeof(dtap_attach_complete));
4175
4176 OSMO_ASSERT(expect_gmm_msg(SGSN_NSEI, 0x1002, GSM48_MT_GMM_ATTACH_COMPL));
4177
4178 dump_peers(stdout, 0, 0, &gbcfg);
4179
4180 /* Detach (MT) */
4181 send_llc_dl_ui(nsi, "DETACH REQ", &sgsn_peer, 0x1002,
4182 local_tlli, 1, imsi, sizeof(imsi),
4183 GPRS_SAPI_GMM, sgsn_nu++,
4184 dtap_mt_detach_req, sizeof(dtap_mt_detach_req));
4185
4186 OSMO_ASSERT(expect_gmm_msg(0x1000, 0x1002, GSM48_MT_GMM_DETACH_REQ));
4187
4188 dump_peers(stdout, 0, 0, &gbcfg);
4189
4190 link_info = gbproxy_link_info_by_tlli(peer, local_tlli);
4191 OSMO_ASSERT(link_info);
4192
4193 send_llc_ul_ui(nsi, "DETACH ACC", &bss_peer[0], 0x1002,
4194 local_tlli, &rai_bss, cell_id,
4195 GPRS_SAPI_GMM, bss_nu++,
4196 dtap_mt_detach_acc, sizeof(dtap_mt_detach_acc));
4197
4198 OSMO_ASSERT(expect_gmm_msg(SGSN_NSEI, 0x1002, GSM48_MT_GMM_DETACH_ACK));
4199 OSMO_ASSERT(!expect_msg());
4200
4201 dump_peers(stdout, 0, 0, &gbcfg);
4202
4203 OSMO_ASSERT(!gbproxy_link_info_by_tlli(peer, local_tlli));
4204 link_info = gbproxy_link_info_by_imsi(peer, imsi, sizeof(imsi));
4205 OSMO_ASSERT(link_info);
4206 OSMO_ASSERT(link_info->is_deregistered);
4207
4208 /* Bad case: Unexpected Re-Attach with P-TMSI after completed attachment
4209 * procedure */
4210 send_llc_ul_ui(nsi, "ATTACH REQUEST", &bss_peer[0], 0x1002,
4211 foreign_tlli, &rai_bss, cell_id,
4212 GPRS_SAPI_GMM, bss_nu++,
4213 dtap_attach_req3, sizeof(dtap_attach_req3));
4214
4215 OSMO_ASSERT(expect_gmm_msg(SGSN_NSEI, 0x1002, GSM48_MT_GMM_ATTACH_REQ));
4216
4217 dump_peers(stdout, 0, 0, &gbcfg);
4218
4219 link_info2 = gbproxy_link_info_by_imsi(peer, imsi, sizeof(imsi));
4220 link_info = gbproxy_link_info_by_tlli(peer, foreign_tlli);
4221 OSMO_ASSERT(link_info);
4222 OSMO_ASSERT(link_info == link_info2);
4223 OSMO_ASSERT(link_info->imsi_len != 0);
4224 OSMO_ASSERT(!link_info->is_deregistered);
4225 OSMO_ASSERT(!link_info->imsi_acq_pending);
4226
4227 send_llc_dl_ui(nsi, "ATTACH ACCEPT", &sgsn_peer, 0x1002,
4228 foreign_tlli, 1, imsi, sizeof(imsi),
4229 GPRS_SAPI_GMM, sgsn_nu++,
4230 dtap_attach_acc, sizeof(dtap_attach_acc));
4231
4232 OSMO_ASSERT(expect_gmm_msg(0x1000, 0x1002, GSM48_MT_GMM_ATTACH_ACK));
4233
4234 dump_peers(stdout, 0, 0, &gbcfg);
4235
4236 send_llc_ul_ui(nsi, "ATTACH COMPLETE", &bss_peer[0], 0x1002,
4237 local_tlli, &rai_bss, cell_id,
4238 GPRS_SAPI_GMM, bss_nu++,
4239 dtap_attach_complete, sizeof(dtap_attach_complete));
4240
4241 OSMO_ASSERT(expect_gmm_msg(SGSN_NSEI, 0x1002, GSM48_MT_GMM_ATTACH_COMPL));
4242
4243 dump_peers(stdout, 0, 0, &gbcfg);
4244
4245 send_llc_dl_ui(nsi, "GMM INFO", &sgsn_peer, 0x1002,
4246 local_tlli, 1, imsi, sizeof(imsi),
4247 GPRS_SAPI_GMM, sgsn_nu++,
4248 dtap_gmm_information, sizeof(dtap_gmm_information));
4249
4250 OSMO_ASSERT(expect_gmm_msg(0x1000, 0x1002, GSM48_MT_GMM_INFO));
4251
4252 dump_peers(stdout, 0, 0, &gbcfg);
4253
4254 send_llc_ul_ui(nsi, "ATTACH REQUEST (unexpected)", &bss_peer[0], 0x1002,
4255 foreign_tlli, &rai_bss, cell_id,
4256 GPRS_SAPI_GMM, bss_nu++,
4257 dtap_attach_req3, sizeof(dtap_attach_req3));
4258
4259 OSMO_ASSERT(expect_gmm_msg(SGSN_NSEI, 0x1002, GSM48_MT_GMM_ATTACH_REQ));
4260
4261 dump_peers(stdout, 0, 0, &gbcfg);
4262
4263 link_info2 = gbproxy_link_info_by_imsi(peer, imsi, sizeof(imsi));
4264 link_info = gbproxy_link_info_by_tlli(peer, foreign_tlli);
Jacob Erlbeck59ac49d2014-10-30 17:15:43 +01004265 OSMO_ASSERT(link_info);
Jacob Erlbeck9d0fb1e2014-10-31 10:43:44 +01004266 OSMO_ASSERT(link_info == link_info2);
4267 OSMO_ASSERT(link_info->imsi_len != 0);
4268 OSMO_ASSERT(!link_info->is_deregistered);
4269 OSMO_ASSERT(!link_info->imsi_acq_pending);
Jacob Erlbeck59ac49d2014-10-30 17:15:43 +01004270 OSMO_ASSERT(link_info->sgsn_tlli.current == foreign_tlli);
Jacob Erlbeck9d0fb1e2014-10-31 10:43:44 +01004271 OSMO_ASSERT(link_info->sgsn_tlli.assigned == 0);
4272
4273 send_llc_dl_ui(nsi, "ATTACH ACCEPT", &sgsn_peer, 0x1002,
4274 foreign_tlli, 1, imsi, sizeof(imsi),
4275 GPRS_SAPI_GMM, sgsn_nu++,
4276 dtap_attach_acc, sizeof(dtap_attach_acc));
4277
4278 OSMO_ASSERT(expect_gmm_msg(0x1000, 0x1002, GSM48_MT_GMM_ATTACH_ACK));
4279
4280 dump_peers(stdout, 0, 0, &gbcfg);
4281
4282 send_llc_ul_ui(nsi, "ATTACH COMPLETE", &bss_peer[0], 0x1002,
4283 local_tlli, &rai_bss, cell_id,
4284 GPRS_SAPI_GMM, bss_nu++,
4285 dtap_attach_complete, sizeof(dtap_attach_complete));
4286
4287 OSMO_ASSERT(expect_gmm_msg(SGSN_NSEI, 0x1002, GSM48_MT_GMM_ATTACH_COMPL));
4288
4289 dump_peers(stdout, 0, 0, &gbcfg);
4290
4291 /* Detach (MT) */
4292 send_llc_dl_ui(nsi, "DETACH REQ", &sgsn_peer, 0x1002,
4293 local_tlli, 1, imsi, sizeof(imsi),
4294 GPRS_SAPI_GMM, sgsn_nu++,
4295 dtap_mt_detach_req, sizeof(dtap_mt_detach_req));
4296
4297 OSMO_ASSERT(expect_gmm_msg(0x1000, 0x1002, GSM48_MT_GMM_DETACH_REQ));
4298
4299 dump_peers(stdout, 0, 0, &gbcfg);
4300
4301 link_info = gbproxy_link_info_by_tlli(peer, local_tlli);
4302 OSMO_ASSERT(link_info);
4303
4304 send_llc_ul_ui(nsi, "DETACH ACC", &bss_peer[0], 0x1002,
4305 local_tlli, &rai_bss, cell_id,
4306 GPRS_SAPI_GMM, bss_nu++,
4307 dtap_mt_detach_acc, sizeof(dtap_mt_detach_acc));
4308
4309 OSMO_ASSERT(expect_gmm_msg(SGSN_NSEI, 0x1002, GSM48_MT_GMM_DETACH_ACK));
4310 OSMO_ASSERT(!expect_msg());
4311
4312 dump_peers(stdout, 0, 0, &gbcfg);
4313
4314 OSMO_ASSERT(!gbproxy_link_info_by_tlli(peer, local_tlli));
4315 link_info = gbproxy_link_info_by_imsi(peer, imsi, sizeof(imsi));
4316 OSMO_ASSERT(link_info);
4317 OSMO_ASSERT(link_info->is_deregistered);
4318
4319
Jacob Erlbeck2bf32612014-09-22 11:26:58 +02004320 /* Attach rejected */
4321
4322 gbproxy_delete_link_infos(peer);
4323
4324 send_llc_ul_ui(nsi, "ATTACH REQUEST", &bss_peer[0], 0x1002,
4325 foreign_tlli, &rai_bss, cell_id,
4326 GPRS_SAPI_GMM, bss_nu++,
4327 dtap_attach_req, sizeof(dtap_attach_req));
4328
Jacob Erlbeckfb83ed32014-09-22 19:16:06 +02004329 OSMO_ASSERT(expect_gmm_msg(0x1000, 0x1002, GSM48_MT_GMM_ID_REQ));
4330
Jacob Erlbeck2bf32612014-09-22 11:26:58 +02004331 dump_peers(stdout, 0, 0, &gbcfg);
4332
4333 link_info = gbproxy_link_info_by_tlli(peer, foreign_tlli);
4334 OSMO_ASSERT(link_info);
4335 OSMO_ASSERT(link_info->imsi_len == 0);
4336 OSMO_ASSERT(!link_info->is_deregistered);
4337 OSMO_ASSERT(link_info->imsi_acq_pending);
4338
4339 send_llc_ul_ui(nsi, "IDENT RESPONSE", &bss_peer[0], 0x1002,
4340 foreign_tlli, &rai_bss, cell_id,
4341 GPRS_SAPI_GMM, bss_nu++,
4342 dtap_identity_resp, sizeof(dtap_identity_resp));
4343
Jacob Erlbeckfb83ed32014-09-22 19:16:06 +02004344 OSMO_ASSERT(expect_gmm_msg(SGSN_NSEI, 0x1002, GSM48_MT_GMM_ATTACH_REQ));
4345
Jacob Erlbeck2bf32612014-09-22 11:26:58 +02004346 dump_peers(stdout, 0, 0, &gbcfg);
4347
4348 link_info2 = gbproxy_link_info_by_imsi(peer, imsi, sizeof(imsi));
4349 link_info = gbproxy_link_info_by_tlli(peer, foreign_tlli);
4350 OSMO_ASSERT(link_info);
4351 OSMO_ASSERT(link_info == link_info2);
4352 OSMO_ASSERT(link_info->imsi_len != 0);
4353 OSMO_ASSERT(!link_info->is_deregistered);
4354 OSMO_ASSERT(!link_info->imsi_acq_pending);
4355
4356 send_llc_dl_ui(nsi, "ATTACH REJECT", &sgsn_peer, 0x1002,
4357 foreign_tlli, 1, imsi, sizeof(imsi),
4358 GPRS_SAPI_GMM, sgsn_nu++,
4359 dtap_attach_rej7, sizeof(dtap_attach_rej7));
4360
Jacob Erlbeckfb83ed32014-09-22 19:16:06 +02004361 OSMO_ASSERT(expect_gmm_msg(0x1000, 0x1002, GSM48_MT_GMM_ATTACH_REJ));
4362
Jacob Erlbeck2bf32612014-09-22 11:26:58 +02004363 dump_peers(stdout, 0, 0, &gbcfg);
4364
Jacob Erlbeck9c65c812014-09-22 10:42:05 +02004365 OSMO_ASSERT(!gbproxy_link_info_by_tlli(peer, foreign_tlli));
4366
Jacob Erlbeckfb83ed32014-09-22 19:16:06 +02004367 OSMO_ASSERT(!expect_msg());
4368
Jacob Erlbeck2bf32612014-09-22 11:26:58 +02004369 /* Attach (incomplete) and Detach (MO) */
4370
4371 gbproxy_delete_link_infos(peer);
4372
4373 send_llc_ul_ui(nsi, "ATTACH REQUEST", &bss_peer[0], 0x1002,
4374 foreign_tlli, &rai_bss, cell_id,
4375 GPRS_SAPI_GMM, bss_nu++,
4376 dtap_attach_req, sizeof(dtap_attach_req));
4377
Jacob Erlbeckfb83ed32014-09-22 19:16:06 +02004378 OSMO_ASSERT(expect_gmm_msg(0x1000, 0x1002, GSM48_MT_GMM_ID_REQ));
4379
Jacob Erlbeck2bf32612014-09-22 11:26:58 +02004380 dump_peers(stdout, 0, 0, &gbcfg);
4381
4382 link_info = gbproxy_link_info_by_tlli(peer, foreign_tlli);
4383 OSMO_ASSERT(link_info);
4384 OSMO_ASSERT(link_info->imsi_len == 0);
4385 OSMO_ASSERT(!link_info->is_deregistered);
4386 OSMO_ASSERT(link_info->imsi_acq_pending);
4387
4388 send_llc_ul_ui(nsi, "DETACH REQ (MO)", &bss_peer[0], 0x1002,
4389 foreign_tlli, &rai_bss, cell_id,
4390 GPRS_SAPI_GMM, bss_nu++,
4391 dtap_detach_req, sizeof(dtap_detach_req));
4392
Jacob Erlbeckfb83ed32014-09-22 19:16:06 +02004393 OSMO_ASSERT(expect_gmm_msg(0x1000, 0x1002, GSM48_MT_GMM_DETACH_ACK));
4394
Jacob Erlbeck2bf32612014-09-22 11:26:58 +02004395 dump_peers(stdout, 0, 0, &gbcfg);
4396
Jacob Erlbeckfb83ed32014-09-22 19:16:06 +02004397 OSMO_ASSERT(!expect_msg());
4398
Jacob Erlbeck2bf32612014-09-22 11:26:58 +02004399 /* Attach (incomplete) and Detach (MT) */
4400
4401 gbproxy_delete_link_infos(peer);
4402
4403 send_llc_ul_ui(nsi, "ATTACH REQUEST", &bss_peer[0], 0x1002,
4404 foreign_tlli, &rai_bss, cell_id,
4405 GPRS_SAPI_GMM, bss_nu++,
4406 dtap_attach_req, sizeof(dtap_attach_req));
4407
Jacob Erlbeckfb83ed32014-09-22 19:16:06 +02004408 OSMO_ASSERT(expect_gmm_msg(0x1000, 0x1002, GSM48_MT_GMM_ID_REQ));
4409
Jacob Erlbeck2bf32612014-09-22 11:26:58 +02004410 dump_peers(stdout, 0, 0, &gbcfg);
4411
4412 link_info = gbproxy_link_info_by_tlli(peer, foreign_tlli);
4413 OSMO_ASSERT(link_info);
4414 OSMO_ASSERT(link_info->imsi_len == 0);
4415 OSMO_ASSERT(!link_info->is_deregistered);
4416 OSMO_ASSERT(link_info->imsi_acq_pending);
4417
4418 send_llc_dl_ui(nsi, "DETACH REQ (MT)", &sgsn_peer, 0x1002,
4419 foreign_tlli, 1, imsi, sizeof(imsi),
4420 GPRS_SAPI_GMM, sgsn_nu++,
4421 dtap_mt_detach_req, sizeof(dtap_mt_detach_req));
4422
Jacob Erlbeckfb83ed32014-09-22 19:16:06 +02004423 OSMO_ASSERT(expect_gmm_msg(0x1000, 0x1002, GSM48_MT_GMM_DETACH_REQ));
4424
Jacob Erlbeck2bf32612014-09-22 11:26:58 +02004425 dump_peers(stdout, 0, 0, &gbcfg);
4426
4427 link_info = gbproxy_link_info_by_tlli(peer, foreign_tlli);
4428 OSMO_ASSERT(link_info);
4429
Jacob Erlbeckfb83ed32014-09-22 19:16:06 +02004430 send_llc_ul_ui(nsi, "DETACH ACC", &bss_peer[0], 0x1002,
Jacob Erlbeck2bf32612014-09-22 11:26:58 +02004431 foreign_tlli, &rai_bss, cell_id,
4432 GPRS_SAPI_GMM, bss_nu++,
4433 dtap_mt_detach_acc, sizeof(dtap_mt_detach_acc));
4434
Jacob Erlbeckfb83ed32014-09-22 19:16:06 +02004435 /* TODO: The stored messaged should be cleaned when receiving a Detach
4436 * Ack. Remove the first OSMO_ASSERT when this is fixed. */
4437 OSMO_ASSERT(expect_gmm_msg(SGSN_NSEI, 0x1002, GSM48_MT_GMM_ATTACH_REQ));
4438 OSMO_ASSERT(expect_gmm_msg(SGSN_NSEI, 0x1002, GSM48_MT_GMM_DETACH_ACK));
4439
Jacob Erlbeck2bf32612014-09-22 11:26:58 +02004440 dump_peers(stdout, 0, 0, &gbcfg);
4441
4442 OSMO_ASSERT(!gbproxy_link_info_by_tlli(peer, foreign_tlli));
4443 link_info = gbproxy_link_info_by_imsi(peer, imsi, sizeof(imsi));
4444 OSMO_ASSERT(link_info);
4445 OSMO_ASSERT(link_info->is_deregistered);
4446
Jacob Erlbeckfb83ed32014-09-22 19:16:06 +02004447 OSMO_ASSERT(!expect_msg());
4448 received_messages = NULL;
4449
Jacob Erlbeck772a22b2014-09-15 14:18:09 +02004450 dump_global(stdout, 0);
4451
4452 gbprox_reset(&gbcfg);
4453 gprs_ns_destroy(nsi);
4454 nsi = NULL;
Daniel Willmannd1554ec2015-10-12 19:36:34 +02004455
4456 cleanup_test();
Jacob Erlbeck772a22b2014-09-15 14:18:09 +02004457}
4458
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +02004459struct gbproxy_link_info *register_tlli(
Jacob Erlbecka42fe9f2014-09-12 14:15:02 +02004460 struct gbproxy_peer *peer, uint32_t tlli,
4461 const uint8_t *imsi, size_t imsi_len, time_t now)
4462{
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +02004463 struct gbproxy_link_info *link_info;
Jacob Erlbeck8992f302014-09-19 13:17:55 +02004464 int imsi_matches = -1;
Jacob Erlbecka42fe9f2014-09-12 14:15:02 +02004465 int tlli_already_known = 0;
Jacob Erlbeck9a83d7a2014-09-25 11:17:31 +02004466 struct gbproxy_config *cfg = peer->cfg;
Jacob Erlbecka42fe9f2014-09-12 14:15:02 +02004467
4468 /* Check, whether the IMSI matches */
4469 if (gprs_is_mi_imsi(imsi, imsi_len)) {
Jacob Erlbeck9a83d7a2014-09-25 11:17:31 +02004470 imsi_matches = gbproxy_check_imsi(
4471 &cfg->matches[GBPROX_MATCH_PATCHING], imsi, imsi_len);
Jacob Erlbeck8992f302014-09-19 13:17:55 +02004472 if (imsi_matches < 0)
Jacob Erlbecka42fe9f2014-09-12 14:15:02 +02004473 return NULL;
4474 }
4475
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +02004476 link_info = gbproxy_link_info_by_tlli(peer, tlli);
Jacob Erlbecka42fe9f2014-09-12 14:15:02 +02004477
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +02004478 if (!link_info) {
4479 link_info = gbproxy_link_info_by_imsi(peer, imsi, imsi_len);
Jacob Erlbecka42fe9f2014-09-12 14:15:02 +02004480
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +02004481 if (link_info) {
Jacob Erlbecka42fe9f2014-09-12 14:15:02 +02004482 /* TLLI has changed somehow, adjust it */
4483 LOGP(DGPRS, LOGL_INFO,
4484 "The TLLI has changed from %08x to %08x\n",
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +02004485 link_info->tlli.current, tlli);
4486 link_info->tlli.current = tlli;
Jacob Erlbecka42fe9f2014-09-12 14:15:02 +02004487 }
4488 }
4489
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +02004490 if (!link_info) {
4491 link_info = gbproxy_link_info_alloc(peer);
4492 link_info->tlli.current = tlli;
Jacob Erlbecka42fe9f2014-09-12 14:15:02 +02004493 } else {
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +02004494 gbproxy_detach_link_info(peer, link_info);
Jacob Erlbecka42fe9f2014-09-12 14:15:02 +02004495 tlli_already_known = 1;
4496 }
4497
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +02004498 OSMO_ASSERT(link_info != NULL);
Jacob Erlbecka42fe9f2014-09-12 14:15:02 +02004499
4500 if (!tlli_already_known)
4501 LOGP(DGPRS, LOGL_INFO, "Adding TLLI %08x to list\n", tlli);
4502
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +02004503 gbproxy_attach_link_info(peer, now, link_info);
4504 gbproxy_update_link_info(link_info, imsi, imsi_len);
Jacob Erlbecka42fe9f2014-09-12 14:15:02 +02004505
Jacob Erlbeck8992f302014-09-19 13:17:55 +02004506 if (imsi_matches >= 0)
Jacob Erlbeck9a83d7a2014-09-25 11:17:31 +02004507 link_info->is_matching[GBPROX_MATCH_PATCHING] = imsi_matches;
Jacob Erlbecka42fe9f2014-09-12 14:15:02 +02004508
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +02004509 return link_info;
Jacob Erlbecka42fe9f2014-09-12 14:15:02 +02004510}
4511
Holger Hans Peter Freyther0196c992014-08-04 17:10:08 +02004512static void test_gbproxy_tlli_expire(void)
4513{
4514 struct gbproxy_config cfg = {0};
4515 struct gbproxy_peer *peer;
4516 const char *err_msg = NULL;
4517 const uint8_t imsi1[] = { GSM_MI_TYPE_IMSI, 0x23, 0x24, 0x25, 0x26 };
4518 const uint8_t imsi2[] = { GSM_MI_TYPE_IMSI, 0x26, 0x27, 0x28, 0x29 };
Jacob Erlbeckf4946202014-08-08 09:33:06 +02004519 const uint8_t imsi3[] = { GSM_MI_TYPE_IMSI | 0x10, 0x32, 0x54, 0x76, 0xf8 };
Holger Hans Peter Freyther0196c992014-08-04 17:10:08 +02004520 const uint32_t tlli1 = 1234 | 0xc0000000;
4521 const uint32_t tlli2 = 5678 | 0xc0000000;
Jacob Erlbeckf4946202014-08-08 09:33:06 +02004522 const uint32_t tlli3 = 3456 | 0xc0000000;
Holger Hans Peter Freyther0196c992014-08-04 17:10:08 +02004523 const char *filter_re = ".*";
Jacob Erlbeck7b821d02014-08-08 08:37:37 +02004524 time_t now = 1407479214;
Holger Hans Peter Freyther0196c992014-08-04 17:10:08 +02004525
4526 printf("Test TLLI info expiry\n\n");
4527
4528 gbproxy_init_config(&cfg);
4529
Jacob Erlbeck9a83d7a2014-09-25 11:17:31 +02004530 if (gbproxy_set_patch_filter(&cfg.matches[GBPROX_MATCH_PATCHING],
4531 filter_re, &err_msg) != 0) {
Holger Hans Peter Freyther0196c992014-08-04 17:10:08 +02004532 fprintf(stderr, "gbprox_set_patch_filter: got error: %s\n",
4533 err_msg);
4534 OSMO_ASSERT(err_msg == NULL);
4535 }
4536
4537 {
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +02004538 struct gbproxy_link_info *link_info;
Holger Hans Peter Freyther0196c992014-08-04 17:10:08 +02004539
4540 printf("Test TLLI replacement:\n");
4541
4542 cfg.tlli_max_len = 0;
4543 cfg.tlli_max_age = 0;
4544 peer = gbproxy_peer_alloc(&cfg, 20);
Jacob Erlbeckf8562e32014-09-19 16:03:07 +02004545 OSMO_ASSERT(peer->patch_state.logical_link_count == 0);
Holger Hans Peter Freyther0196c992014-08-04 17:10:08 +02004546
4547 printf(" Add TLLI 1, IMSI 1\n");
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +02004548 link_info = register_tlli(peer, tlli1,
Jacob Erlbeck9114bee2014-08-19 12:21:01 +02004549 imsi1, ARRAY_SIZE(imsi1), now);
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +02004550 OSMO_ASSERT(link_info);
4551 OSMO_ASSERT(link_info->tlli.current == tlli1);
Jacob Erlbeckf8562e32014-09-19 16:03:07 +02004552 OSMO_ASSERT(peer->patch_state.logical_link_count == 1);
Holger Hans Peter Freyther0196c992014-08-04 17:10:08 +02004553
4554 /* replace the old entry */
4555 printf(" Add TLLI 2, IMSI 1 (should replace TLLI 1)\n");
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +02004556 link_info = register_tlli(peer, tlli2,
Jacob Erlbeck9114bee2014-08-19 12:21:01 +02004557 imsi1, ARRAY_SIZE(imsi1), now);
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +02004558 OSMO_ASSERT(link_info);
4559 OSMO_ASSERT(link_info->tlli.current == tlli2);
Jacob Erlbeckf8562e32014-09-19 16:03:07 +02004560 OSMO_ASSERT(peer->patch_state.logical_link_count == 1);
Holger Hans Peter Freyther0196c992014-08-04 17:10:08 +02004561
Jacob Erlbeck7b821d02014-08-08 08:37:37 +02004562 dump_peers(stdout, 2, now, &cfg);
Holger Hans Peter Freyther0196c992014-08-04 17:10:08 +02004563
4564 /* verify that 5678 has survived */
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +02004565 link_info = gbproxy_link_info_by_imsi(peer, imsi1, ARRAY_SIZE(imsi1));
4566 OSMO_ASSERT(link_info);
4567 OSMO_ASSERT(link_info->tlli.current == tlli2);
4568 link_info = gbproxy_link_info_by_imsi(peer, imsi2, ARRAY_SIZE(imsi2));
4569 OSMO_ASSERT(!link_info);
Holger Hans Peter Freyther0196c992014-08-04 17:10:08 +02004570
4571 printf("\n");
4572
4573 gbproxy_peer_free(peer);
4574 }
4575
4576 {
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +02004577 struct gbproxy_link_info *link_info;
Holger Hans Peter Freyther0196c992014-08-04 17:10:08 +02004578
4579 printf("Test IMSI replacement:\n");
4580
4581 cfg.tlli_max_len = 0;
4582 cfg.tlli_max_age = 0;
4583 peer = gbproxy_peer_alloc(&cfg, 20);
Jacob Erlbeckf8562e32014-09-19 16:03:07 +02004584 OSMO_ASSERT(peer->patch_state.logical_link_count == 0);
Holger Hans Peter Freyther0196c992014-08-04 17:10:08 +02004585
4586 printf(" Add TLLI 1, IMSI 1\n");
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +02004587 link_info = register_tlli(peer, tlli1,
Jacob Erlbeck9114bee2014-08-19 12:21:01 +02004588 imsi1, ARRAY_SIZE(imsi1), now);
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +02004589 OSMO_ASSERT(link_info);
4590 OSMO_ASSERT(link_info->tlli.current == tlli1);
Jacob Erlbeckf8562e32014-09-19 16:03:07 +02004591 OSMO_ASSERT(peer->patch_state.logical_link_count == 1);
Holger Hans Peter Freyther0196c992014-08-04 17:10:08 +02004592
4593 /* try to replace the old entry */
4594 printf(" Add TLLI 1, IMSI 2 (should replace IMSI 1)\n");
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +02004595 link_info = register_tlli(peer, tlli1,
Jacob Erlbeck9114bee2014-08-19 12:21:01 +02004596 imsi2, ARRAY_SIZE(imsi2), now);
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +02004597 OSMO_ASSERT(link_info);
4598 OSMO_ASSERT(link_info->tlli.current == tlli1);
Jacob Erlbeckf8562e32014-09-19 16:03:07 +02004599 OSMO_ASSERT(peer->patch_state.logical_link_count == 1);
Holger Hans Peter Freyther0196c992014-08-04 17:10:08 +02004600
Jacob Erlbeck7b821d02014-08-08 08:37:37 +02004601 dump_peers(stdout, 2, now, &cfg);
Holger Hans Peter Freyther0196c992014-08-04 17:10:08 +02004602
4603 /* verify that 5678 has survived */
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +02004604 link_info = gbproxy_link_info_by_imsi(peer, imsi1, ARRAY_SIZE(imsi1));
4605 OSMO_ASSERT(!link_info);
4606 link_info = gbproxy_link_info_by_imsi(peer, imsi2, ARRAY_SIZE(imsi2));
4607 OSMO_ASSERT(link_info);
4608 OSMO_ASSERT(link_info->tlli.current == tlli1);
Holger Hans Peter Freyther0196c992014-08-04 17:10:08 +02004609
4610 printf("\n");
4611
4612 gbproxy_peer_free(peer);
4613 }
4614
4615 {
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +02004616 struct gbproxy_link_info *link_info;
Jacob Erlbeckaad32bc2014-08-07 17:23:00 +02004617 int num_removed;
Holger Hans Peter Freyther0196c992014-08-04 17:10:08 +02004618
4619 printf("Test TLLI expiry, max_len == 1:\n");
4620
4621 cfg.tlli_max_len = 1;
4622 cfg.tlli_max_age = 0;
4623 peer = gbproxy_peer_alloc(&cfg, 20);
Jacob Erlbeckf8562e32014-09-19 16:03:07 +02004624 OSMO_ASSERT(peer->patch_state.logical_link_count == 0);
Holger Hans Peter Freyther0196c992014-08-04 17:10:08 +02004625
4626 printf(" Add TLLI 1, IMSI 1\n");
Jacob Erlbecka42fe9f2014-09-12 14:15:02 +02004627 register_tlli(peer, tlli1, imsi1, ARRAY_SIZE(imsi1), now);
Jacob Erlbeckf8562e32014-09-19 16:03:07 +02004628 OSMO_ASSERT(peer->patch_state.logical_link_count == 1);
Holger Hans Peter Freyther0196c992014-08-04 17:10:08 +02004629
4630 /* replace the old entry */
4631 printf(" Add TLLI 2, IMSI 2 (should replace IMSI 1)\n");
Jacob Erlbecka42fe9f2014-09-12 14:15:02 +02004632 register_tlli(peer, tlli2, imsi2, ARRAY_SIZE(imsi2), now);
Jacob Erlbeckf8562e32014-09-19 16:03:07 +02004633 OSMO_ASSERT(peer->patch_state.logical_link_count == 2);
Jacob Erlbeckaad32bc2014-08-07 17:23:00 +02004634
Jacob Erlbeck51fde082014-09-19 16:40:21 +02004635 num_removed = gbproxy_remove_stale_link_infos(peer, now + 2);
Jacob Erlbeckaad32bc2014-08-07 17:23:00 +02004636 OSMO_ASSERT(num_removed == 1);
Jacob Erlbeckf8562e32014-09-19 16:03:07 +02004637 OSMO_ASSERT(peer->patch_state.logical_link_count == 1);
Holger Hans Peter Freyther0196c992014-08-04 17:10:08 +02004638
Jacob Erlbeck7b821d02014-08-08 08:37:37 +02004639 dump_peers(stdout, 2, now, &cfg);
Holger Hans Peter Freyther0196c992014-08-04 17:10:08 +02004640
4641 /* verify that 5678 has survived */
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +02004642 link_info = gbproxy_link_info_by_imsi(peer, imsi1, ARRAY_SIZE(imsi1));
4643 OSMO_ASSERT(!link_info);
4644 link_info = gbproxy_link_info_by_imsi(peer, imsi2, ARRAY_SIZE(imsi2));
4645 OSMO_ASSERT(link_info);
4646 OSMO_ASSERT(link_info->tlli.current == tlli2);
Holger Hans Peter Freyther0196c992014-08-04 17:10:08 +02004647
4648 printf("\n");
4649
4650 gbproxy_peer_free(peer);
4651 }
4652
4653 {
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +02004654 struct gbproxy_link_info *link_info;
Jacob Erlbeckaad32bc2014-08-07 17:23:00 +02004655 int num_removed;
Holger Hans Peter Freyther0196c992014-08-04 17:10:08 +02004656
4657 printf("Test TLLI expiry, max_age == 1:\n");
4658
4659 cfg.tlli_max_len = 0;
4660 cfg.tlli_max_age = 1;
4661 peer = gbproxy_peer_alloc(&cfg, 20);
Jacob Erlbeckf8562e32014-09-19 16:03:07 +02004662 OSMO_ASSERT(peer->patch_state.logical_link_count == 0);
Holger Hans Peter Freyther0196c992014-08-04 17:10:08 +02004663
4664 printf(" Add TLLI 1, IMSI 1 (should expire after timeout)\n");
Jacob Erlbecka42fe9f2014-09-12 14:15:02 +02004665 register_tlli(peer, tlli1, imsi1, ARRAY_SIZE(imsi1), now);
Jacob Erlbeckf8562e32014-09-19 16:03:07 +02004666 OSMO_ASSERT(peer->patch_state.logical_link_count == 1);
Holger Hans Peter Freyther0196c992014-08-04 17:10:08 +02004667
Jacob Erlbeckf4946202014-08-08 09:33:06 +02004668 printf(" Add TLLI 2, IMSI 2 (should not expire after timeout)\n");
Jacob Erlbecka42fe9f2014-09-12 14:15:02 +02004669 register_tlli(peer, tlli2, imsi2, ARRAY_SIZE(imsi2),
Jacob Erlbeckf4946202014-08-08 09:33:06 +02004670 now + 1);
Jacob Erlbeckf8562e32014-09-19 16:03:07 +02004671 OSMO_ASSERT(peer->patch_state.logical_link_count == 2);
Holger Hans Peter Freyther0196c992014-08-04 17:10:08 +02004672
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +02004673 num_removed = gbproxy_remove_stale_link_infos(peer, now + 2);
Jacob Erlbeckf4946202014-08-08 09:33:06 +02004674 OSMO_ASSERT(num_removed == 1);
Jacob Erlbeckf8562e32014-09-19 16:03:07 +02004675 OSMO_ASSERT(peer->patch_state.logical_link_count == 1);
Jacob Erlbeckf4946202014-08-08 09:33:06 +02004676
4677 dump_peers(stdout, 2, now + 2, &cfg);
4678
Jacob Erlbeck9057bc32014-08-12 16:30:30 +02004679 /* verify that 5678 has survived */
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +02004680 link_info = gbproxy_link_info_by_imsi(peer, imsi1, ARRAY_SIZE(imsi1));
4681 OSMO_ASSERT(!link_info);
4682 link_info = gbproxy_link_info_by_imsi(peer, imsi2, ARRAY_SIZE(imsi2));
4683 OSMO_ASSERT(link_info);
4684 OSMO_ASSERT(link_info->tlli.current == tlli2);
Jacob Erlbeck9057bc32014-08-12 16:30:30 +02004685
Jacob Erlbeckf4946202014-08-08 09:33:06 +02004686 printf("\n");
4687
4688 gbproxy_peer_free(peer);
4689 }
4690
4691 {
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +02004692 struct gbproxy_link_info *link_info;
Jacob Erlbeckf4946202014-08-08 09:33:06 +02004693 int num_removed;
4694
4695 printf("Test TLLI expiry, max_len == 2, max_age == 1:\n");
4696
4697 cfg.tlli_max_len = 0;
4698 cfg.tlli_max_age = 1;
4699 peer = gbproxy_peer_alloc(&cfg, 20);
Jacob Erlbeckf8562e32014-09-19 16:03:07 +02004700 OSMO_ASSERT(peer->patch_state.logical_link_count == 0);
Holger Hans Peter Freyther0196c992014-08-04 17:10:08 +02004701
Jacob Erlbeckf4946202014-08-08 09:33:06 +02004702 printf(" Add TLLI 1, IMSI 1 (should expire)\n");
Jacob Erlbecka42fe9f2014-09-12 14:15:02 +02004703 register_tlli(peer, tlli1, imsi1, ARRAY_SIZE(imsi1), now);
Jacob Erlbeckf8562e32014-09-19 16:03:07 +02004704 OSMO_ASSERT(peer->patch_state.logical_link_count == 1);
Jacob Erlbeckf4946202014-08-08 09:33:06 +02004705
4706 printf(" Add TLLI 2, IMSI 2 (should expire after timeout)\n");
Jacob Erlbecka42fe9f2014-09-12 14:15:02 +02004707 register_tlli(peer, tlli2, imsi2, ARRAY_SIZE(imsi2),
Jacob Erlbeckf4946202014-08-08 09:33:06 +02004708 now + 1);
Jacob Erlbeckf8562e32014-09-19 16:03:07 +02004709 OSMO_ASSERT(peer->patch_state.logical_link_count == 2);
Jacob Erlbeckf4946202014-08-08 09:33:06 +02004710
4711 printf(" Add TLLI 3, IMSI 3 (should not expire after timeout)\n");
Jacob Erlbecka42fe9f2014-09-12 14:15:02 +02004712 register_tlli(peer, tlli3, imsi3, ARRAY_SIZE(imsi3),
Jacob Erlbeck9114bee2014-08-19 12:21:01 +02004713 now + 2);
Jacob Erlbeckf8562e32014-09-19 16:03:07 +02004714 OSMO_ASSERT(peer->patch_state.logical_link_count == 3);
Jacob Erlbeckf4946202014-08-08 09:33:06 +02004715
4716 dump_peers(stdout, 2, now + 2, &cfg);
4717
4718 printf(" Remove stale TLLIs\n");
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +02004719 num_removed = gbproxy_remove_stale_link_infos(peer, now + 3);
Jacob Erlbeckf4946202014-08-08 09:33:06 +02004720 OSMO_ASSERT(num_removed == 2);
Jacob Erlbeckf8562e32014-09-19 16:03:07 +02004721 OSMO_ASSERT(peer->patch_state.logical_link_count == 1);
Jacob Erlbeckf4946202014-08-08 09:33:06 +02004722
4723 dump_peers(stdout, 2, now + 2, &cfg);
Holger Hans Peter Freyther0196c992014-08-04 17:10:08 +02004724
Jacob Erlbeck9057bc32014-08-12 16:30:30 +02004725 /* verify that tlli3 has survived */
Jacob Erlbeck91d2f8a2014-09-19 15:07:27 +02004726 link_info = gbproxy_link_info_by_imsi(peer, imsi1, ARRAY_SIZE(imsi1));
4727 OSMO_ASSERT(!link_info);
4728 link_info = gbproxy_link_info_by_imsi(peer, imsi2, ARRAY_SIZE(imsi2));
4729 OSMO_ASSERT(!link_info);
4730 link_info = gbproxy_link_info_by_imsi(peer, imsi3, ARRAY_SIZE(imsi3));
4731 OSMO_ASSERT(link_info);
4732 OSMO_ASSERT(link_info->tlli.current == tlli3);
Jacob Erlbeck9057bc32014-08-12 16:30:30 +02004733
Holger Hans Peter Freyther0196c992014-08-04 17:10:08 +02004734 printf("\n");
4735
4736 gbproxy_peer_free(peer);
4737 }
Jacob Erlbeck9ccc41e2014-09-25 11:21:34 +02004738 gbproxy_clear_patch_filter(&cfg.matches[GBPROX_MATCH_PATCHING]);
4739 gbprox_reset(&cfg);
Daniel Willmannd1554ec2015-10-12 19:36:34 +02004740
4741 cleanup_test();
Holger Hans Peter Freyther0196c992014-08-04 17:10:08 +02004742}
4743
Jacob Erlbeck291f0502014-08-07 10:46:29 +02004744static void test_gbproxy_imsi_matching(void)
4745{
Jacob Erlbeck291f0502014-08-07 10:46:29 +02004746 const char *err_msg = NULL;
4747 const uint8_t imsi1[] = { GSM_MI_TYPE_IMSI | 0x10, 0x32, 0x54, 0xf6 };
4748 const uint8_t imsi2[] = { GSM_MI_TYPE_IMSI | GSM_MI_ODD | 0x10, 0x32, 0x54, 0x76 };
4749 const uint8_t imsi3_bad[] = { GSM_MI_TYPE_IMSI | 0x10, 0xee, 0x54, 0xff };
4750 const uint8_t tmsi1[] = { GSM_MI_TYPE_TMSI | 0xf0, 0x11, 0x22, 0x33, 0x44 };
4751 const uint8_t tmsi2_bad[] = { GSM_MI_TYPE_TMSI | 0xf0, 0x11, 0x22 };
4752 const uint8_t imei1[] = { GSM_MI_TYPE_IMEI | 0x10, 0x32, 0x54, 0xf6 };
4753 const uint8_t imei2[] = { GSM_MI_TYPE_IMEI | GSM_MI_ODD | 0x10, 0x32, 0x54, 0x76 };
4754 const char *filter_re1 = ".*";
4755 const char *filter_re2 = "^1234";
4756 const char *filter_re3 = "^4321";
4757 const char *filter_re4_bad = "^12[";
Jacob Erlbeck9a83d7a2014-09-25 11:17:31 +02004758 struct gbproxy_match match = {0,};
Jacob Erlbeck291f0502014-08-07 10:46:29 +02004759
4760 printf("=== Test IMSI/TMSI matching ===\n\n");
4761
Jacob Erlbeck9a83d7a2014-09-25 11:17:31 +02004762 OSMO_ASSERT(match.enable == 0);
Jacob Erlbeck291f0502014-08-07 10:46:29 +02004763
Jacob Erlbeck9a83d7a2014-09-25 11:17:31 +02004764 OSMO_ASSERT(gbproxy_set_patch_filter(&match, filter_re1, &err_msg) == 0);
4765 OSMO_ASSERT(match.enable == 1);
Jacob Erlbeck291f0502014-08-07 10:46:29 +02004766
Jacob Erlbeck9a83d7a2014-09-25 11:17:31 +02004767 OSMO_ASSERT(gbproxy_set_patch_filter(&match, filter_re2, &err_msg) == 0);
4768 OSMO_ASSERT(match.enable == 1);
Jacob Erlbeck291f0502014-08-07 10:46:29 +02004769
4770 err_msg = NULL;
Jacob Erlbeck9a83d7a2014-09-25 11:17:31 +02004771 OSMO_ASSERT(gbproxy_set_patch_filter(&match, filter_re4_bad, &err_msg) == -1);
Jacob Erlbeck291f0502014-08-07 10:46:29 +02004772 OSMO_ASSERT(err_msg != NULL);
Jacob Erlbeck9a83d7a2014-09-25 11:17:31 +02004773 OSMO_ASSERT(match.enable == 0);
Jacob Erlbeck291f0502014-08-07 10:46:29 +02004774
Jacob Erlbeck9a83d7a2014-09-25 11:17:31 +02004775 OSMO_ASSERT(gbproxy_set_patch_filter(&match, filter_re2, &err_msg) == 0);
4776 OSMO_ASSERT(match.enable == 1);
Jacob Erlbeck291f0502014-08-07 10:46:29 +02004777
Jacob Erlbeck9a83d7a2014-09-25 11:17:31 +02004778 OSMO_ASSERT(gbproxy_set_patch_filter(&match, NULL, &err_msg) == 0);
4779 OSMO_ASSERT(match.enable == 0);
Jacob Erlbeck291f0502014-08-07 10:46:29 +02004780
Jacob Erlbeck9a83d7a2014-09-25 11:17:31 +02004781 OSMO_ASSERT(gbproxy_set_patch_filter(&match, filter_re2, &err_msg) == 0);
4782 OSMO_ASSERT(match.enable == 1);
Jacob Erlbeck29805da2014-08-14 08:57:04 +02004783
Jacob Erlbeck9a83d7a2014-09-25 11:17:31 +02004784 gbproxy_clear_patch_filter(&match);
4785 OSMO_ASSERT(match.enable == 0);
Jacob Erlbeck29805da2014-08-14 08:57:04 +02004786
Jacob Erlbeck9a83d7a2014-09-25 11:17:31 +02004787 OSMO_ASSERT(gbproxy_set_patch_filter(&match, filter_re2, &err_msg) == 0);
4788 OSMO_ASSERT(match.enable == 1);
Jacob Erlbeck291f0502014-08-07 10:46:29 +02004789
Jacob Erlbeck9a83d7a2014-09-25 11:17:31 +02004790 OSMO_ASSERT(gbproxy_check_imsi(&match, imsi1, ARRAY_SIZE(imsi1)) == 1);
4791 OSMO_ASSERT(gbproxy_check_imsi(&match, imsi2, ARRAY_SIZE(imsi2)) == 1);
Jacob Erlbeck291f0502014-08-07 10:46:29 +02004792 /* imsi3_bad contains 0xE and 0xF digits, but the conversion function
Jacob Erlbeck9114bee2014-08-19 12:21:01 +02004793 * doesn't complain, so gbproxy_check_imsi() doesn't return -1 in this
Jacob Erlbeck291f0502014-08-07 10:46:29 +02004794 * case. */
Jacob Erlbeck9a83d7a2014-09-25 11:17:31 +02004795 OSMO_ASSERT(gbproxy_check_imsi(&match, imsi3_bad, ARRAY_SIZE(imsi3_bad)) == 0);
4796 OSMO_ASSERT(gbproxy_check_imsi(&match, tmsi1, ARRAY_SIZE(tmsi1)) == -1);
4797 OSMO_ASSERT(gbproxy_check_imsi(&match, tmsi2_bad, ARRAY_SIZE(tmsi2_bad)) == -1);
4798 OSMO_ASSERT(gbproxy_check_imsi(&match, imei1, ARRAY_SIZE(imei1)) == -1);
4799 OSMO_ASSERT(gbproxy_check_imsi(&match, imei2, ARRAY_SIZE(imei2)) == -1);
Jacob Erlbeck291f0502014-08-07 10:46:29 +02004800
Jacob Erlbeck9a83d7a2014-09-25 11:17:31 +02004801 OSMO_ASSERT(gbproxy_set_patch_filter(&match, filter_re3, &err_msg) == 0);
4802 OSMO_ASSERT(match.enable == 1);
Jacob Erlbeck291f0502014-08-07 10:46:29 +02004803
Jacob Erlbeck9a83d7a2014-09-25 11:17:31 +02004804 OSMO_ASSERT(gbproxy_check_imsi(&match, imsi1, ARRAY_SIZE(imsi1)) == 0);
4805 OSMO_ASSERT(gbproxy_check_imsi(&match, imsi2, ARRAY_SIZE(imsi2)) == 0);
4806 OSMO_ASSERT(gbproxy_check_imsi(&match, imsi3_bad, ARRAY_SIZE(imsi3_bad)) == 0);
4807 OSMO_ASSERT(gbproxy_check_imsi(&match, tmsi1, ARRAY_SIZE(tmsi1)) == -1);
4808 OSMO_ASSERT(gbproxy_check_imsi(&match, tmsi2_bad, ARRAY_SIZE(tmsi2_bad)) == -1);
4809 OSMO_ASSERT(gbproxy_check_imsi(&match, imei1, ARRAY_SIZE(imei1)) == -1);
4810 OSMO_ASSERT(gbproxy_check_imsi(&match, imei2, ARRAY_SIZE(imei2)) == -1);
Jacob Erlbeck291f0502014-08-07 10:46:29 +02004811
4812 /* TODO: Check correct length but wrong type with is_mi_tmsi */
Jacob Erlbeck9ccc41e2014-09-25 11:21:34 +02004813
4814 gbproxy_clear_patch_filter(&match);
4815 OSMO_ASSERT(match.enable == 0);
Daniel Willmannd1554ec2015-10-12 19:36:34 +02004816
4817 cleanup_test();
Jacob Erlbeck291f0502014-08-07 10:46:29 +02004818}
4819
Daniel Willmannbb42eee2016-11-08 15:29:30 +01004820static void test_gbproxy_stored_messages()
4821{
4822 struct gprs_ns_inst *nsi = gprs_ns_instantiate(gprs_ns_callback, NULL);
4823 struct sockaddr_in bss_peer[1] = {{0},};
4824 struct sockaddr_in sgsn_peer= {0};
4825 struct gprs_ra_id rai_bss =
4826 {.mcc = 112, .mnc = 332, .lac = 16464, .rac = 96};
4827 struct gprs_ra_id rai_unknown =
4828 {.mcc = 1, .mnc = 99, .lac = 99, .rac = 96};
4829 uint16_t cell_id = 0x1234;
4830
4831 const uint32_t ptmsi = 0xefe2b700;
4832 const uint32_t local_tlli = 0xefe2b700;
4833
4834 const uint32_t foreign_tlli1 = 0x8000dead;
4835
4836 struct gbproxy_peer *peer;
4837 unsigned bss_nu = 0;
4838 unsigned sgsn_nu = 0;
4839
4840 OSMO_ASSERT(local_tlli == gprs_tmsi2tlli(ptmsi, TLLI_LOCAL));
4841
4842 bssgp_nsi = nsi;
4843 gbcfg.nsi = bssgp_nsi;
4844 gbcfg.nsip_sgsn_nsei = SGSN_NSEI;
4845 gbcfg.core_mcc = 0;
4846 gbcfg.core_mnc = 0;
4847 gbcfg.core_apn = talloc_zero_size(NULL, 100);
4848 gbcfg.core_apn_size = gprs_str_to_apn(gbcfg.core_apn, 100, "foo.bar");
4849 gbcfg.patch_ptmsi = 0;
4850 gbcfg.acquire_imsi = 1;
4851 gbcfg.keep_link_infos = 0;
4852
4853 configure_sgsn_peer(&sgsn_peer);
4854 configure_bss_peers(bss_peer, ARRAY_SIZE(bss_peer));
4855
4856 printf("=== %s ===\n", __func__);
4857 printf("--- Initialise SGSN ---\n\n");
4858
4859 connect_sgsn(nsi, &sgsn_peer, SGSN_NSEI);
4860
4861 printf("--- Initialise BSS 1 ---\n\n");
4862
4863 setup_ns(nsi, &bss_peer[0], 0x1001, 0x1000);
4864 setup_bssgp(nsi, &bss_peer[0], 0x1002);
4865
4866 peer = gbproxy_peer_by_nsei(&gbcfg, 0x1000);
4867 OSMO_ASSERT(peer != NULL);
4868
4869 send_bssgp_reset_ack(nsi, &sgsn_peer, 0x1002);
4870
4871 gprs_dump_nsi(nsi);
4872 dump_global(stdout, 0);
4873 dump_peers(stdout, 0, 0, &gbcfg);
4874
4875 printf("--- Establish first LLC connection ---\n\n");
4876
4877 send_llc_ul_ui(nsi, "ATTACH REQUEST", &bss_peer[0], 0x1002,
4878 foreign_tlli1, &rai_unknown, cell_id,
4879 GPRS_SAPI_GMM, bss_nu++,
4880 dtap_attach_req, sizeof(dtap_attach_req));
4881
4882 dump_peers(stdout, 0, 0, &gbcfg);
4883
4884 send_llc_dl_ui(nsi, "IDENT REQUEST", &sgsn_peer, 0x1002,
4885 foreign_tlli1, 0, NULL, 0,
4886 GPRS_SAPI_GMM, sgsn_nu++,
4887 dtap_identity_req, sizeof(dtap_identity_req));
4888
4889 dump_peers(stdout, 0, 0, &gbcfg);
4890
4891 send_llc_ul_ui(nsi, "DETACH ACCEPT", &bss_peer[0], 0x1002,
4892 foreign_tlli1, &rai_bss, cell_id,
4893 GPRS_SAPI_GMM, bss_nu++,
4894 dtap_detach_acc, sizeof(dtap_detach_acc));
4895
4896 dump_peers(stdout, 0, 0, &gbcfg);
4897
4898 send_llc_ul_ui(nsi, "IDENT RESPONSE", &bss_peer[0], 0x1002,
4899 foreign_tlli1, &rai_bss, cell_id,
4900 GPRS_SAPI_GMM, bss_nu++,
4901 dtap_identity_resp, sizeof(dtap_identity_resp));
4902
4903 dump_peers(stdout, 0, 0, &gbcfg);
4904
4905 dump_global(stdout, 0);
4906
4907 gbprox_reset(&gbcfg);
4908 gprs_ns_destroy(nsi);
4909 nsi = NULL;
4910
4911 cleanup_test();
4912}
4913
Jacob Erlbeck627e7d92014-07-03 13:28:13 +02004914static struct log_info_cat gprs_categories[] = {
4915 [DGPRS] = {
4916 .name = "DGPRS",
4917 .description = "GPRS Packet Service",
4918 .enabled = 1, .loglevel = LOGL_DEBUG,
4919 },
4920 [DNS] = {
4921 .name = "DNS",
4922 .description = "GPRS Network Service (NS)",
4923 .enabled = 1, .loglevel = LOGL_INFO,
4924 },
4925 [DBSSGP] = {
4926 .name = "DBSSGP",
4927 .description = "GPRS BSS Gateway Protocol (BSSGP)",
4928 .enabled = 1, .loglevel = LOGL_DEBUG,
4929 },
Holger Hans Peter Freyther2840b3f2014-07-07 19:48:14 +02004930};
Jacob Erlbeck51a869c2013-10-15 12:00:26 +02004931
Holger Hans Peter Freyther2840b3f2014-07-07 19:48:14 +02004932static struct log_info info = {
Jacob Erlbeck627e7d92014-07-03 13:28:13 +02004933 .cat = gprs_categories,
4934 .num_cat = ARRAY_SIZE(gprs_categories),
Holger Hans Peter Freyther2840b3f2014-07-07 19:48:14 +02004935};
Jacob Erlbeck51a869c2013-10-15 12:00:26 +02004936
4937int main(int argc, char **argv)
4938{
Neels Hofmeyr4c2d4ab2016-09-16 02:31:17 +02004939 msgb_talloc_ctx_init(NULL, 0);
4940
Jacob Erlbeck51a869c2013-10-15 12:00:26 +02004941 osmo_init_logging(&info);
4942 log_set_use_color(osmo_stderr_target, 0);
4943 log_set_print_filename(osmo_stderr_target, 0);
Holger Hans Peter Freythereece6272014-08-04 15:42:36 +02004944 osmo_signal_register_handler(SS_L_NS, &test_signal, &gbcfg);
Jacob Erlbeck51a869c2013-10-15 12:00:26 +02004945
Jacob Erlbeck72b401f2013-10-24 12:48:55 +02004946 log_set_print_filename(osmo_stderr_target, 0);
Jacob Erlbeck627e7d92014-07-03 13:28:13 +02004947 log_set_log_level(osmo_stderr_target, LOGL_DEBUG);
4948 log_set_all_filter(osmo_stderr_target, 1);
Jacob Erlbeck72b401f2013-10-24 12:48:55 +02004949
4950 rate_ctr_init(NULL);
4951
4952 setlinebuf(stdout);
4953
4954 printf("===== GbProxy test START\n");
Holger Hans Peter Freyther18739ea2014-08-04 11:10:09 +02004955 gbproxy_init_config(&gbcfg);
Jacob Erlbeck51a869c2013-10-15 12:00:26 +02004956 test_gbproxy();
Jacob Erlbeck72b401f2013-10-24 12:48:55 +02004957 test_gbproxy_ident_changes();
Jacob Erlbeck291f0502014-08-07 10:46:29 +02004958 test_gbproxy_imsi_matching();
Jacob Erlbeck04f679b2014-09-18 09:21:20 +02004959 test_gbproxy_ptmsi_assignment();
Jacob Erlbeck7fb42db2014-07-07 10:46:01 +02004960 test_gbproxy_ra_patching();
Jacob Erlbeck6bd7ded2014-08-15 17:20:06 +02004961 test_gbproxy_ptmsi_patching();
Jacob Erlbecke99c3332014-10-20 16:25:01 +02004962 test_gbproxy_ptmsi_patching_bad_cases();
Jacob Erlbeck28fe9882014-08-26 13:33:36 +02004963 test_gbproxy_imsi_acquisition();
Jacob Erlbeckf181f9e2014-08-27 12:44:25 +02004964 test_gbproxy_secondary_sgsn();
Jacob Erlbeck772a22b2014-09-15 14:18:09 +02004965 test_gbproxy_keep_info();
Holger Hans Peter Freyther0196c992014-08-04 17:10:08 +02004966 test_gbproxy_tlli_expire();
Daniel Willmannbb42eee2016-11-08 15:29:30 +01004967 test_gbproxy_stored_messages();
Jacob Erlbeck72b401f2013-10-24 12:48:55 +02004968 printf("===== GbProxy test END\n\n");
Jacob Erlbeck51a869c2013-10-15 12:00:26 +02004969
4970 exit(EXIT_SUCCESS);
4971}