sgsn: Add global require_update_location flag

This flag is used to determine, whether the Update Location procedure
shall be invoked. This is currently only set, when the 'remote'
authorization policy is set. When the flag is set, sgsn_auth_update
will not never be called directly by sgsn_auth_request, if an Attach
Request procedure is pending, even if the remote connection fails for
some reason.

Sponsored-by: On-Waves ehf
diff --git a/openbsc/include/openbsc/sgsn.h b/openbsc/include/openbsc/sgsn.h
index 798bfde..78064dd 100644
--- a/openbsc/include/openbsc/sgsn.h
+++ b/openbsc/include/openbsc/sgsn.h
@@ -32,6 +32,7 @@
 	int gsup_server_port;
 
 	int require_authentication;
+	int require_update_location;
 };
 
 struct sgsn_instance {
diff --git a/openbsc/src/gprs/sgsn_auth.c b/openbsc/src/gprs/sgsn_auth.c
index 83372e8..9cc67db 100644
--- a/openbsc/src/gprs/sgsn_auth.c
+++ b/openbsc/src/gprs/sgsn_auth.c
@@ -161,9 +161,9 @@
 		return 0;
 	}
 
-	need_update_location =
-		mmctx->subscr == NULL ||
-		mmctx->pending_req == GSM48_MT_GMM_ATTACH_REQ;
+	need_update_location = sgsn->cfg.require_update_location &&
+		(mmctx->subscr == NULL ||
+		 mmctx->pending_req == GSM48_MT_GMM_ATTACH_REQ);
 
 	/* This has the side effect of registering the subscr with the mmctx */
 	subscr = gprs_subscr_get_or_create_by_mmctx(mmctx);
@@ -191,8 +191,11 @@
 	} else if (need_update_location) {
 		LOGMMCTXP(LOGL_INFO, mmctx,
 			  "Missing information, requesting subscriber data\n");
-		if (gprs_subscr_request_update_location(mmctx) >= 0)
+		rc = gprs_subscr_request_update_location(mmctx);
+		if (rc >= 0)
 			return 0;
+
+		return rc;
 	}
 
 	sgsn_auth_update(mmctx);
diff --git a/openbsc/src/gprs/sgsn_vty.c b/openbsc/src/gprs/sgsn_vty.c
index 3ca1570..d847d91 100644
--- a/openbsc/src/gprs/sgsn_vty.c
+++ b/openbsc/src/gprs/sgsn_vty.c
@@ -377,6 +377,7 @@
 	OSMO_ASSERT(val >= SGSN_AUTH_POLICY_OPEN && val <= SGSN_AUTH_POLICY_REMOTE);
 	g_cfg->auth_policy = val;
 	g_cfg->require_authentication = (val == SGSN_AUTH_POLICY_REMOTE);
+	g_cfg->require_update_location = (val == SGSN_AUTH_POLICY_REMOTE);
 
 	return CMD_SUCCESS;
 }
diff --git a/openbsc/tests/sgsn/sgsn_test.c b/openbsc/tests/sgsn/sgsn_test.c
index 7c48eef..58d3a4f 100644
--- a/openbsc/tests/sgsn/sgsn_test.c
+++ b/openbsc/tests/sgsn/sgsn_test.c
@@ -877,6 +877,7 @@
 	subscr = gprs_subscr_get_or_create("123456789012345");
 	subscr->authorized = 1;
 	sgsn->cfg.require_authentication = 1;
+	sgsn->cfg.require_update_location = 1;
 	subscr_put(subscr);
 
 	printf("Auth policy 'remote', auth faked: ");
@@ -919,6 +920,7 @@
 	subscr = gprs_subscr_get_or_create("123456789012345");
 	subscr->authorized = 1;
 	sgsn->cfg.require_authentication = 1;
+	sgsn->cfg.require_update_location = 1;
 	subscr_put(subscr);
 
 	printf("Auth policy 'remote', triplet based auth: ");