add struct bsc_subscr, separating libbsc from gsm_subscriber

In a future commit, gsm_subscriber will be replaced by vlr_subscr, and it will
not make sense to use vlr_subscr in libbsc. Thus we need a dedicated BSC
subscriber: struct bsc_subscr.

Add rf_policy arg to bsc_grace_paging_request() because the bsc_subscr will no
longer have a backpointer to gsm_network (used to be via subscr->group).

Create a separate logging filter for the new BSC subscriber. The implementation
of adjusting the filter context is added in libbsc to not introduce
bsc_subscr_get/_put() dependencies to libcommon.

During Paging Response, fetch a bsc_subscr from the mobile identity, like we do
for the gsm_subscriber. It looks like a duplication now, but will make sense
for the VLR as well as for future MSC split patches.

Naming: it was requested to not name the new struct bsc_sub, because 'sub' is
too ambiguous. At the same time it would be fine to have 'bsc_sub_' as function
prefix. Instead of struct bsc_subscriber and bsc_sub_ prefix, I decided to
match both up as struct bsc_subscr and bsc_subscr_ function prefix. It's fast
to type, relatively short, unambiguous, and the naming is consistent.

Add bsc_subscr unit test.

Related: OS#1592, OS#1594
Change-Id: Ia61cc00e8bb186b976939a4fc8f7cf9ce6aa3d8e
diff --git a/openbsc/src/libmsc/gsm_04_08.c b/openbsc/src/libmsc/gsm_04_08.c
index fff902d..c910d71 100644
--- a/openbsc/src/libmsc/gsm_04_08.c
+++ b/openbsc/src/libmsc/gsm_04_08.c
@@ -1433,6 +1433,8 @@
 	uint8_t mi_type;
 	char mi_string[GSM48_MI_SIZE];
 	struct gsm_subscriber *subscr = NULL;
+	struct bsc_subscr *bsub;
+	uint32_t tmsi;
 	int rc = 0;
 
 	resp = (struct gsm48_pag_resp *) &gh->data[0];
@@ -1443,8 +1445,8 @@
 
 	switch (mi_type) {
 	case GSM_MI_TYPE_TMSI:
-		subscr = subscr_get_by_tmsi(conn->network->subscr_group,
-					    tmsi_from_string(mi_string));
+		tmsi = tmsi_from_string(mi_string);
+		subscr = subscr_get_by_tmsi(conn->network->subscr_group, tmsi);
 		break;
 	case GSM_MI_TYPE_IMSI:
 		subscr = subscr_get_by_imsi(conn->network->subscr_group,
@@ -1457,6 +1459,19 @@
 		/* FIXME: request id? close channel? */
 		return -EINVAL;
 	}
+
+	if (!conn->subscr) {
+		conn->subscr = subscr;
+	} else if (conn->subscr != subscr) {
+		LOGP(DRR, LOGL_ERROR, "<- Channel already owned by someone else?\n");
+		subscr_put(subscr);
+		return -EINVAL;
+	} else {
+		DEBUGP(DRR, "<- Channel already owned by us\n");
+		subscr_put(subscr);
+		subscr = conn->subscr;
+	}
+
 	log_set_context(LOG_CTX_VLR_SUBSCR, subscr);
 	DEBUGP(DRR, "<- Channel was requested by %s\n",
 		subscr->name && strlen(subscr->name) ? subscr->name : subscr->imsi);
@@ -1465,10 +1480,18 @@
 	memcpy(subscr->equipment.classmark2, classmark2_lv+1, *classmark2_lv);
 	db_sync_equipment(&subscr->equipment);
 
+	/* TODO MSC split -- creating a BSC subscriber directly from MSC data
+	 * structures in RAM. At some point the MSC will send a message to the
+	 * BSC instead. */
+	bsub = bsc_subscr_find_or_create_by_imsi(conn->network->bsc_subscribers,
+						 subscr->imsi);
+	bsub->tmsi = subscr->tmsi;
+	bsub->lac = subscr->lac;
+
 	/* We received a paging */
 	conn->expire_timer_stopped = 1;
 
-	rc = gsm48_handle_paging_resp(conn, msg, subscr);
+	rc = gsm48_handle_paging_resp(conn, msg, bsub);
 	return rc;
 }