/* Osmocom Visitor Location Register (VLR): Location Update FSMs */

/* (C) 2016 by Harald Welte <laforge@gnumonks.org>
 *
 * All Rights Reserved
 *
 * This program is free software; you can redistribute it and/or modify
 * it under the terms of the GNU Affero General Public License as published by
 * the Free Software Foundation; either version 3 of the License, or
 * (at your option) any later version.
 *
 * This program is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 * GNU Affero General Public License for more details.
 *
 * You should have received a copy of the GNU Affero General Public License
 * along with this program.  If not, see <http://www.gnu.org/licenses/>.
 *
 */

#include <osmocom/core/fsm.h>
#include <osmocom/gsm/gsm48.h>
#include <osmocom/msc/vlr.h>
#include <osmocom/msc/debug.h>

#include "vlr_core.h"
#include "vlr_auth_fsm.h"
#include "vlr_lu_fsm.h"

#define S(x)	(1 << (x))

#define LU_TIMEOUT_LONG		30

enum vlr_fsm_result {
	VLR_FSM_RESULT_NONE,
	VLR_FSM_RESULT_SUCCESS,
	VLR_FSM_RESULT_FAILURE,
};


/***********************************************************************
 * Update_HLR_VLR, TS 23.012 Chapter 4.1.2.4
 ***********************************************************************/

enum upd_hlr_vlr_state {
	UPD_HLR_VLR_S_INIT,
	UPD_HLR_VLR_S_WAIT_FOR_DATA,
	UPD_HLR_VLR_S_DONE,
};

enum upd_hlr_vlr_evt {
	UPD_HLR_VLR_E_START,
	UPD_HLR_VLR_E_INS_SUB_DATA,
	UPD_HLR_VLR_E_ACT_TRACE_MODE,
	UPD_HLR_VLR_E_FW_CHECK_SS_IND,
	UPD_HLR_VLR_E_UPD_LOC_ACK,
	UPD_HLR_VLR_E_UPD_LOC_NACK,
};

static const struct value_string upd_hlr_vlr_event_names[] = {
	OSMO_VALUE_STRING(UPD_HLR_VLR_E_START),
	OSMO_VALUE_STRING(UPD_HLR_VLR_E_INS_SUB_DATA),
	OSMO_VALUE_STRING(UPD_HLR_VLR_E_ACT_TRACE_MODE),
	OSMO_VALUE_STRING(UPD_HLR_VLR_E_FW_CHECK_SS_IND),
	OSMO_VALUE_STRING(UPD_HLR_VLR_E_UPD_LOC_ACK),
	OSMO_VALUE_STRING(UPD_HLR_VLR_E_UPD_LOC_NACK),
	{ 0, NULL }
};

static inline struct vlr_subscr *upd_hlr_vlr_fi_priv(struct osmo_fsm_inst *fi);

static void upd_hlr_vlr_fsm_init(struct osmo_fsm_inst *fi, uint32_t event,
				 void *data)
{
	struct vlr_subscr *vsub = upd_hlr_vlr_fi_priv(fi);
	int rc;

	OSMO_ASSERT(event == UPD_HLR_VLR_E_START);

	/* Send UpdateLocation to HLR */
	rc = vlr_subscr_req_lu(vsub);
	if (rc < 0)
		LOGPFSML(fi, LOGL_ERROR, "Failed to send UpdateLocation to HLR\n");
	osmo_fsm_inst_state_chg(fi, UPD_HLR_VLR_S_WAIT_FOR_DATA,
				LU_TIMEOUT_LONG, 0);
}

static void upd_hlr_vlr_fsm_wait_data(struct osmo_fsm_inst *fi, uint32_t event,
				      void *data)
{
	struct vlr_subscr *vsub = upd_hlr_vlr_fi_priv(fi);

	switch (event) {
	case UPD_HLR_VLR_E_INS_SUB_DATA:
		/* FIXME: Insert_Subscr_Data_VLR */
		break;
	case UPD_HLR_VLR_E_ACT_TRACE_MODE:
		/* TODO: Activate_Tracing_VLR */
		break;
	case UPD_HLR_VLR_E_FW_CHECK_SS_IND:
		/* TODO: Forward Check SS Ind to MSC */
		break;
	case UPD_HLR_VLR_E_UPD_LOC_ACK:
		/* Inside Update_HLR_VLR after UpdateLocationAck */
		vsub->sub_dataconf_by_hlr_ind = true;
		vsub->loc_conf_in_hlr_ind = true;
		osmo_fsm_inst_state_chg(fi, UPD_HLR_VLR_S_DONE, 0, 0);
		osmo_fsm_inst_term(fi, OSMO_FSM_TERM_REGULAR, NULL);
		break;
	case UPD_HLR_VLR_E_UPD_LOC_NACK:
		/* Inside Update_HLR_VLR after UpdateLocationNack */
		/* TODO: Check_User_Error_In_Serving_Network_Entity */
		vsub->sub_dataconf_by_hlr_ind = false;
		vsub->loc_conf_in_hlr_ind = false;
		osmo_fsm_inst_state_chg(fi, UPD_HLR_VLR_S_DONE, 0, 0);
		/* Data is a pointer to a gsm48_gmm_cause which we
		 * simply pass through */
		osmo_fsm_inst_term(fi, OSMO_FSM_TERM_REGULAR, data);
		break;
	}
}

static const struct osmo_fsm_state upd_hlr_vlr_states[] = {
	[UPD_HLR_VLR_S_INIT] = {
		.in_event_mask = S(UPD_HLR_VLR_E_START),
		.out_state_mask = S(UPD_HLR_VLR_S_WAIT_FOR_DATA),
		.name = OSMO_STRINGIFY(UPD_HLR_VLR_S_INIT),
		.action = upd_hlr_vlr_fsm_init,
	},
	[UPD_HLR_VLR_S_WAIT_FOR_DATA] = {
		.in_event_mask = S(UPD_HLR_VLR_E_INS_SUB_DATA) |
				 S(UPD_HLR_VLR_E_ACT_TRACE_MODE) |
				 S(UPD_HLR_VLR_E_FW_CHECK_SS_IND) |
				 S(UPD_HLR_VLR_E_UPD_LOC_ACK) |
				 S(UPD_HLR_VLR_E_UPD_LOC_NACK),
		.out_state_mask = S(UPD_HLR_VLR_S_DONE),
		.name = OSMO_STRINGIFY(UPD_HLR_VLR_S_WAIT_FOR_DATA),
		.action = upd_hlr_vlr_fsm_wait_data,
	},
	[UPD_HLR_VLR_S_DONE] = {
		.name = OSMO_STRINGIFY(UPD_HLR_VLR_S_DONE),
	},
};

static struct osmo_fsm upd_hlr_vlr_fsm = {
	.name = "upd_hlr_vlr_fsm",
	.states = upd_hlr_vlr_states,
	.num_states = ARRAY_SIZE(upd_hlr_vlr_states),
	.allstate_event_mask = 0,
	.allstate_action = NULL,
	.log_subsys = DVLR,
	.event_names = upd_hlr_vlr_event_names,
};

static inline struct vlr_subscr *upd_hlr_vlr_fi_priv(struct osmo_fsm_inst *fi)
{
	OSMO_ASSERT(fi->fsm == &upd_hlr_vlr_fsm);
	return (struct vlr_subscr*)fi->priv;
}

struct osmo_fsm_inst *
upd_hlr_vlr_proc_start(struct osmo_fsm_inst *parent,
		       struct vlr_subscr *vsub,
		       uint32_t parent_event)
{
	struct osmo_fsm_inst *fi;

	fi = osmo_fsm_inst_alloc_child(&upd_hlr_vlr_fsm, parent,
					parent_event);
	if (!fi)
		return NULL;

	fi->priv = vsub;
	osmo_fsm_inst_dispatch(fi, UPD_HLR_VLR_E_START, NULL);

	return fi;
}


/***********************************************************************
 * Subscriber_Present_VLR, TS 29.002 Chapter 25.10.1
 ***********************************************************************/

enum sub_pres_vlr_state {
	SUB_PRES_VLR_S_INIT,
	SUB_PRES_VLR_S_WAIT_FOR_HLR,
	SUB_PRES_VLR_S_DONE,
};

enum sub_pres_vlr_event {
	SUB_PRES_VLR_E_START,
	SUB_PRES_VLR_E_READY_SM_CNF,
	SUB_PRES_VLR_E_READY_SM_ERR,
};

static const struct value_string sub_pres_vlr_event_names[] = {
	OSMO_VALUE_STRING(SUB_PRES_VLR_E_START),
	OSMO_VALUE_STRING(SUB_PRES_VLR_E_READY_SM_CNF),
	OSMO_VALUE_STRING(SUB_PRES_VLR_E_READY_SM_ERR),
	{ 0, NULL }
};

static inline struct vlr_subscr *sub_pres_vlr_fi_priv(struct osmo_fsm_inst *fi);

static void sub_pres_vlr_fsm_init(struct osmo_fsm_inst *fi, uint32_t event,
				  void *data)
{
	struct vlr_subscr *vsub = sub_pres_vlr_fi_priv(fi);
	OSMO_ASSERT(event == SUB_PRES_VLR_E_START);

	if (!vsub->ms_not_reachable_flag) {
		osmo_fsm_inst_state_chg(fi, SUB_PRES_VLR_S_DONE, 0, 0);
		osmo_fsm_inst_term(fi, OSMO_FSM_TERM_REGULAR, NULL);
		return;
	}
	/* FIXME: Send READY_FOR_SM via GSUP */
	osmo_fsm_inst_state_chg(fi, SUB_PRES_VLR_S_WAIT_FOR_HLR,
				LU_TIMEOUT_LONG, 0);
}

static void sub_pres_vlr_fsm_wait_hlr(struct osmo_fsm_inst *fi, uint32_t event,
				      void *data)
{
	struct vlr_subscr *vsub = sub_pres_vlr_fi_priv(fi);

	switch (event) {
	case SUB_PRES_VLR_E_READY_SM_CNF:
		vsub->ms_not_reachable_flag = false;
		break;
	case SUB_PRES_VLR_E_READY_SM_ERR:
		break;
	}
	osmo_fsm_inst_state_chg(fi, SUB_PRES_VLR_S_DONE, 0, 0);
	osmo_fsm_inst_term(fi, OSMO_FSM_TERM_REGULAR, NULL);
}

static const struct osmo_fsm_state sub_pres_vlr_states[] = {
	[SUB_PRES_VLR_S_INIT] = {
		.in_event_mask = S(SUB_PRES_VLR_E_START),
		.out_state_mask = S(SUB_PRES_VLR_S_WAIT_FOR_HLR) |
				  S(SUB_PRES_VLR_S_DONE),
		.name = OSMO_STRINGIFY(SUB_PRES_VLR_S_INIT),
		.action = sub_pres_vlr_fsm_init,
	},
	[SUB_PRES_VLR_S_WAIT_FOR_HLR] = {
		.in_event_mask = S(SUB_PRES_VLR_E_READY_SM_CNF) |
				 S(SUB_PRES_VLR_E_READY_SM_ERR),
		.out_state_mask = S(SUB_PRES_VLR_S_DONE),
		.name = OSMO_STRINGIFY(SUB_PRES_VLR_S_WAIT_FOR_HLR),
		.action = sub_pres_vlr_fsm_wait_hlr,
	},
	[SUB_PRES_VLR_S_DONE] = {
		.name = OSMO_STRINGIFY(SUB_PRES_VLR_S_DONE),
	},
};

static struct osmo_fsm sub_pres_vlr_fsm = {
	.name = "sub_pres_vlr_fsm",
	.states = sub_pres_vlr_states,
	.num_states = ARRAY_SIZE(sub_pres_vlr_states),
	.allstate_event_mask = 0,
	.allstate_action = NULL,
	.log_subsys = DVLR,
	.event_names = sub_pres_vlr_event_names,
};

static inline struct vlr_subscr *sub_pres_vlr_fi_priv(struct osmo_fsm_inst *fi)
{
	OSMO_ASSERT(fi->fsm == &sub_pres_vlr_fsm);
	return (struct vlr_subscr*)fi->priv;
}

/* Note that the start event is dispatched right away, so in case the FSM immediately concludes from that
 * event, the created FSM struct may no longer be valid as it already deallocated again, and it may
 * furthermore already have invoked the parent FSM instance's deallocation as well. Hence, instead of
 * returning, store the created FSM instance address in *fi_p before dispatching the event. It is thus
 * possible to store the instance's pointer in a parent FSM instance without running danger of using
 * already freed memory. */
void sub_pres_vlr_fsm_start(struct osmo_fsm_inst **fi_p,
			    struct osmo_fsm_inst *parent,
			    struct vlr_subscr *vsub,
			    uint32_t term_event)
{
	struct osmo_fsm_inst *fi;

	OSMO_ASSERT(fi_p);

	fi = osmo_fsm_inst_alloc_child(&sub_pres_vlr_fsm, parent,
					term_event);
	*fi_p = fi;
	if (!fi)
		return;

	fi->priv = vsub;
	osmo_fsm_inst_dispatch(fi, SUB_PRES_VLR_E_START, NULL);
}

/***********************************************************************
 * Location_Update_Completion_VLR, TS 23.012 Chapter 4.1.2.3
 ***********************************************************************/

enum lu_compl_vlr_state {
	LU_COMPL_VLR_S_INIT,
	LU_COMPL_VLR_S_WAIT_SUB_PRES,
	LU_COMPL_VLR_S_WAIT_IMEI,
	LU_COMPL_VLR_S_WAIT_IMEI_TMSI,
	LU_COMPL_VLR_S_WAIT_TMSI_CNF,
	LU_COMPL_VLR_S_DONE,
};

enum lu_compl_vlr_event {
	LU_COMPL_VLR_E_START,
	LU_COMPL_VLR_E_SUB_PRES_COMPL,
	LU_COMPL_VLR_E_IMEI_CHECK_ACK,
	LU_COMPL_VLR_E_IMEI_CHECK_NACK,
	LU_COMPL_VLR_E_NEW_TMSI_ACK,
};

static const struct value_string lu_compl_vlr_event_names[] = {
	OSMO_VALUE_STRING(LU_COMPL_VLR_E_START),
	OSMO_VALUE_STRING(LU_COMPL_VLR_E_SUB_PRES_COMPL),
	OSMO_VALUE_STRING(LU_COMPL_VLR_E_IMEI_CHECK_ACK),
	OSMO_VALUE_STRING(LU_COMPL_VLR_E_IMEI_CHECK_NACK),
	OSMO_VALUE_STRING(LU_COMPL_VLR_E_NEW_TMSI_ACK),
	{ 0, NULL }
};

struct lu_compl_vlr_priv {
	struct vlr_subscr *vsub;
	void *msc_conn_ref;
	struct osmo_fsm_inst *sub_pres_vlr_fsm;
	uint32_t parent_event_success;
	uint32_t parent_event_failure;
	void *parent_event_data;
	enum vlr_fsm_result result;
	uint8_t cause;
	bool assign_tmsi;
};

static inline struct lu_compl_vlr_priv *lu_compl_vlr_fi_priv(struct osmo_fsm_inst *fi);

static void _vlr_lu_compl_fsm_done(struct osmo_fsm_inst *fi,
				   enum vlr_fsm_result result,
				   uint8_t cause)
{
	struct lu_compl_vlr_priv *lcvp = lu_compl_vlr_fi_priv(fi);
	lcvp->result = result;
	lcvp->cause = cause;
	osmo_fsm_inst_state_chg(fi, LU_COMPL_VLR_S_DONE, 0, 0);
}

static void vlr_lu_compl_fsm_success(struct osmo_fsm_inst *fi)
{
	struct lu_compl_vlr_priv *lcvp = lu_compl_vlr_fi_priv(fi);
	struct vlr_subscr *vsub = lcvp->vsub;
	if (!vsub->lu_complete) {
		vsub->lu_complete = true;
		/* Balanced by vlr_subscr_expire() */
		vlr_subscr_get(vsub);
	}
	_vlr_lu_compl_fsm_done(fi, VLR_FSM_RESULT_SUCCESS, 0);
}

static void vlr_lu_compl_fsm_failure(struct osmo_fsm_inst *fi, uint8_t cause)
{
	struct lu_compl_vlr_priv *lcvp = lu_compl_vlr_fi_priv(fi);
	lcvp->vsub->vlr->ops.tx_lu_rej(lcvp->msc_conn_ref, cause);
	_vlr_lu_compl_fsm_done(fi, VLR_FSM_RESULT_FAILURE, cause);
}

static void vlr_lu_compl_fsm_dispatch_result(struct osmo_fsm_inst *fi,
					     uint32_t prev_state)
{
	struct lu_compl_vlr_priv *lcvp = lu_compl_vlr_fi_priv(fi);
	if (!fi->proc.parent) {
		LOGPFSML(fi, LOGL_ERROR, "No parent FSM\n");
		return;
	}
	osmo_fsm_inst_dispatch(fi->proc.parent,
			       (lcvp->result == VLR_FSM_RESULT_SUCCESS)
			       ? lcvp->parent_event_success
			       : lcvp->parent_event_failure,
			       &lcvp->cause);
}

static void lu_compl_vlr_init(struct osmo_fsm_inst *fi, uint32_t event,
			      void *data)
{
	struct lu_compl_vlr_priv *lcvp = lu_compl_vlr_fi_priv(fi);
	struct vlr_subscr *vsub = lcvp->vsub;
	struct vlr_instance *vlr;
	OSMO_ASSERT(vsub);
	vlr = vsub->vlr;
	OSMO_ASSERT(vlr);

	OSMO_ASSERT(event == LU_COMPL_VLR_E_START);

	/* TODO: National Roaming restrictions? */
	/* TODO: Roaming restriction due to unsupported feature in subscriber
	 * data? */
	/* TODO: Regional subscription restriction? */
	/* TODO: Administrative restriction of subscribres' access feature? */
	/* TODO: AccessRestrictuionData parameter available? */
	/* TODO: AccessRestrictionData permits RAT? */
	/* Node 1 */
	/* TODO: Autonomous CSG supported in VPLMN and allowed by HPLMN? */
	/* TODO: Hybrid Cel / CSG Cell */
	/* Node 2 */
	vsub->la_allowed = true;
	vsub->imsi_detached_flag = false;
	/* Start Subscriber_Present_VLR Procedure */
	osmo_fsm_inst_state_chg(fi, LU_COMPL_VLR_S_WAIT_SUB_PRES,
				LU_TIMEOUT_LONG, 0);

	sub_pres_vlr_fsm_start(&lcvp->sub_pres_vlr_fsm, fi, vsub, LU_COMPL_VLR_E_SUB_PRES_COMPL);
}

static void lu_compl_vlr_new_tmsi(struct osmo_fsm_inst *fi)
{
	struct lu_compl_vlr_priv *lcvp = lu_compl_vlr_fi_priv(fi);
	struct vlr_subscr *vsub = lcvp->vsub;
	struct vlr_instance *vlr = vsub->vlr;

	LOGPFSM(fi, "%s()\n", __func__);

	if (vlr_subscr_alloc_tmsi(vsub)) {
		vlr_lu_compl_fsm_failure(fi,
					 GSM48_REJECT_SRV_OPT_TMP_OUT_OF_ORDER);
		return;
	}

	osmo_fsm_inst_state_chg(fi, LU_COMPL_VLR_S_WAIT_TMSI_CNF,
				vlr_timer(vlr, 3250), 3250);

	vlr->ops.tx_lu_acc(lcvp->msc_conn_ref, vsub->tmsi_new);
}

/* After completion of Subscriber_Present_VLR */
static void lu_compl_vlr_wait_subscr_pres(struct osmo_fsm_inst *fi,
					  uint32_t event,
					  void *data)
{
	struct lu_compl_vlr_priv *lcvp = lu_compl_vlr_fi_priv(fi);
	struct vlr_subscr *vsub = lcvp->vsub;
	struct vlr_instance *vlr = vsub->vlr;

	OSMO_ASSERT(event == LU_COMPL_VLR_E_SUB_PRES_COMPL);

	lcvp->sub_pres_vlr_fsm = NULL;

	/* TODO: Trace_Subscriber_Activity_VLR */

	if (vlr->cfg.check_imei_rqd) {
		/* Check IMEI VLR */
		osmo_fsm_inst_state_chg(fi,
					lcvp->assign_tmsi ?
					  LU_COMPL_VLR_S_WAIT_IMEI_TMSI
					: LU_COMPL_VLR_S_WAIT_IMEI,
					vlr_timer(vlr, 3270), 3270);
		vlr->ops.tx_id_req(lcvp->msc_conn_ref, GSM_MI_TYPE_IMEI);
		return;
	}

	/* Do we need to allocate a TMSI? */
	if (lcvp->assign_tmsi) {
		lu_compl_vlr_new_tmsi(fi);
		return;
	}

	/* Location Updating Accept */
	vlr->ops.tx_lu_acc(lcvp->msc_conn_ref, GSM_RESERVED_TMSI);
	vlr_lu_compl_fsm_success(fi);
}

/* Waiting for completion of CHECK_IMEI_VLR */
static void lu_compl_vlr_wait_imei(struct osmo_fsm_inst *fi, uint32_t event,
				   void *data)
{
	struct lu_compl_vlr_priv *lcvp = lu_compl_vlr_fi_priv(fi);
	struct vlr_subscr *vsub = lcvp->vsub;
	struct vlr_instance *vlr = vsub->vlr;

	switch (event) {
	case LU_COMPL_VLR_E_IMEI_CHECK_ACK:
		if (!vsub->imei[0]) {
			/* Abort: Do nothing */
			vlr_lu_compl_fsm_failure(fi,
						 GSM48_REJECT_PROTOCOL_ERROR);
			return;
		}
		/* Pass */
		break;

	case LU_COMPL_VLR_E_IMEI_CHECK_NACK:
		vlr_lu_compl_fsm_failure(fi, GSM48_REJECT_ILLEGAL_ME);
		/* FIXME: IMEI Check Fail to VLR Application (Detach IMSI VLR) */
		return;
	}

	/* IMEI is available. Allocate TMSI if needed. */
	if (lcvp->assign_tmsi) {
		if (fi->state != LU_COMPL_VLR_S_WAIT_IMEI_TMSI)
			LOGPFSML(fi, LOGL_ERROR,
				 "TMSI required, expected to be in state"
				 " LU_COMPL_VLR_S_WAIT_IMEI_TMSI,"
				 " am in %s instead\n",
				 osmo_fsm_state_name(fi->fsm, fi->state));
			/* Logged an error, continue anyway. */

		lu_compl_vlr_new_tmsi(fi);

		/* Wait for TMSI ack */
		return;
	}

	/* No TMSI needed, accept now. */
	vlr->ops.tx_lu_acc(lcvp->msc_conn_ref, GSM_RESERVED_TMSI);
	vlr_lu_compl_fsm_success(fi);
}

static inline struct lu_compl_vlr_priv *lu_compl_vlr_fi_priv(struct osmo_fsm_inst *fi);

/* Waiting for TMSI confirmation */
static void lu_compl_vlr_wait_tmsi(struct osmo_fsm_inst *fi, uint32_t event,
				   void *data)
{
	struct lu_compl_vlr_priv *lcvp = lu_compl_vlr_fi_priv(fi);
	struct vlr_subscr *vsub = lcvp->vsub;

	OSMO_ASSERT(event == LU_COMPL_VLR_E_NEW_TMSI_ACK);

	if (!vsub || vsub->tmsi_new == GSM_RESERVED_TMSI) {
		LOGPFSML(fi, LOGL_ERROR, "TMSI Realloc Compl implies that"
			 " the subscriber has a new TMSI allocated, but"
			 " the new TMSI is unset.\n");
		vlr_lu_compl_fsm_failure(fi, GSM48_REJECT_NETWORK_FAILURE);
		return;
	}

	vsub->tmsi = vsub->tmsi_new;
	vsub->tmsi_new = GSM_RESERVED_TMSI;

	vlr_lu_compl_fsm_success(fi);
}

static const struct osmo_fsm_state lu_compl_vlr_states[] = {
	[LU_COMPL_VLR_S_INIT] = {
		.in_event_mask = S(LU_COMPL_VLR_E_START),
		.out_state_mask = S(LU_COMPL_VLR_S_DONE) |
				  S(LU_COMPL_VLR_S_WAIT_SUB_PRES) |
				  S(LU_COMPL_VLR_S_WAIT_IMEI),
		.name = OSMO_STRINGIFY(LU_COMPL_VLR_S_INIT),
		.action = lu_compl_vlr_init,
	},
	[LU_COMPL_VLR_S_WAIT_SUB_PRES] = {
		.in_event_mask = S(LU_COMPL_VLR_E_SUB_PRES_COMPL),
		.out_state_mask = S(LU_COMPL_VLR_S_WAIT_IMEI) |
				  S(LU_COMPL_VLR_S_WAIT_IMEI_TMSI) |
				  S(LU_COMPL_VLR_S_WAIT_TMSI_CNF) |
				  S(LU_COMPL_VLR_S_DONE),
		.name = OSMO_STRINGIFY(LU_COMPL_VLR_S_WAIT_SUB_PRES),
		.action = lu_compl_vlr_wait_subscr_pres,
	},
	[LU_COMPL_VLR_S_WAIT_IMEI] = {
		.in_event_mask = S(LU_COMPL_VLR_E_IMEI_CHECK_ACK) |
				 S(LU_COMPL_VLR_E_IMEI_CHECK_NACK),
		.out_state_mask = S(LU_COMPL_VLR_S_DONE),
		.name = OSMO_STRINGIFY(LU_COMPL_VLR_S_WAIT_IMEI),
		.action = lu_compl_vlr_wait_imei,
	},
	[LU_COMPL_VLR_S_WAIT_IMEI_TMSI] = {
		.in_event_mask = S(LU_COMPL_VLR_E_IMEI_CHECK_ACK) |
				 S(LU_COMPL_VLR_E_IMEI_CHECK_NACK),
		.out_state_mask = S(LU_COMPL_VLR_S_DONE) |
				  S(LU_COMPL_VLR_S_WAIT_TMSI_CNF),
		.name = OSMO_STRINGIFY(LU_COMPL_VLR_S_WAIT_IMEI_TMSI),
		.action = lu_compl_vlr_wait_imei,
	},
	[LU_COMPL_VLR_S_WAIT_TMSI_CNF] = {
		.in_event_mask = S(LU_COMPL_VLR_E_NEW_TMSI_ACK),
		.out_state_mask = S(LU_COMPL_VLR_S_DONE),
		.name = OSMO_STRINGIFY(LU_COMPL_VLR_S_WAIT_TMSI_CNF),
		.action = lu_compl_vlr_wait_tmsi,
	},
	[LU_COMPL_VLR_S_DONE] = {
		.name = OSMO_STRINGIFY(LU_COMPL_VLR_S_DONE),
		.onenter = vlr_lu_compl_fsm_dispatch_result,
	},
};

static struct osmo_fsm lu_compl_vlr_fsm = {
	.name = "lu_compl_vlr_fsm",
	.states = lu_compl_vlr_states,
	.num_states = ARRAY_SIZE(lu_compl_vlr_states),
	.allstate_event_mask = 0,
	.allstate_action = NULL,
	.log_subsys = DVLR,
	.event_names = lu_compl_vlr_event_names,
};

static inline struct lu_compl_vlr_priv *lu_compl_vlr_fi_priv(struct osmo_fsm_inst *fi)
{
	OSMO_ASSERT(fi->fsm == &lu_compl_vlr_fsm);
	return (struct lu_compl_vlr_priv*)fi->priv;
}

struct osmo_fsm_inst *
lu_compl_vlr_proc_alloc(struct osmo_fsm_inst *parent,
			struct vlr_subscr *vsub,
			void *msc_conn_ref,
			uint32_t parent_event_success,
			uint32_t parent_event_failure,
			bool assign_tmsi)
{
	struct osmo_fsm_inst *fi;
	struct lu_compl_vlr_priv *lcvp;

	fi = osmo_fsm_inst_alloc_child(&lu_compl_vlr_fsm, parent,
				       parent_event_failure);
	if (!fi)
		return NULL;

	lcvp = talloc_zero(fi, struct lu_compl_vlr_priv);
	lcvp->vsub = vsub;
	lcvp->msc_conn_ref = msc_conn_ref;
	lcvp->parent_event_success = parent_event_success;
	lcvp->parent_event_failure = parent_event_failure;
	lcvp->assign_tmsi = assign_tmsi;
	fi->priv = lcvp;

	return fi;
}


/***********************************************************************
 * Update_Location_Area_VLR, TS 23.012 Chapter 4.1.2.1
 ***********************************************************************/

static const struct value_string fsm_lu_event_names[] = {
	OSMO_VALUE_STRING(VLR_ULA_E_UPDATE_LA),
	OSMO_VALUE_STRING(VLR_ULA_E_SEND_ID_ACK),
	OSMO_VALUE_STRING(VLR_ULA_E_SEND_ID_NACK),
	OSMO_VALUE_STRING(VLR_ULA_E_AUTH_RES),
	OSMO_VALUE_STRING(VLR_ULA_E_CIPH_RES),
	OSMO_VALUE_STRING(VLR_ULA_E_ID_IMSI),
	OSMO_VALUE_STRING(VLR_ULA_E_ID_IMEI),
	OSMO_VALUE_STRING(VLR_ULA_E_ID_IMEISV),
	OSMO_VALUE_STRING(VLR_ULA_E_HLR_LU_RES),
	OSMO_VALUE_STRING(VLR_ULA_E_UPD_HLR_COMPL),
	OSMO_VALUE_STRING(VLR_ULA_E_LU_COMPL_SUCCESS),
	OSMO_VALUE_STRING(VLR_ULA_E_LU_COMPL_FAILURE),
	OSMO_VALUE_STRING(VLR_ULA_E_NEW_TMSI_ACK),
	{ 0, NULL }
};

struct lu_fsm_priv {
	struct vlr_instance *vlr;
	struct vlr_subscr *vsub;
	void *msc_conn_ref;
	struct osmo_fsm_inst *upd_hlr_vlr_fsm;
	struct osmo_fsm_inst *lu_compl_vlr_fsm;
	uint32_t parent_event_success;
	uint32_t parent_event_failure;
	void *parent_event_data;
	enum vlr_fsm_result result;
	uint8_t rej_cause;

	enum vlr_lu_type type;
	bool lu_by_tmsi;
	char imsi[16];
	uint32_t tmsi;
	struct osmo_location_area_id old_lai;
	struct osmo_location_area_id new_lai;
	bool authentication_required;
	bool ciphering_required;
	bool is_r99;
	bool is_utran;
	bool assign_tmsi;
};


/* Determine if given location area is served by this VLR */
static bool lai_in_this_vlr(struct vlr_instance *vlr,
			    const struct osmo_location_area_id *lai)
{
	/* TODO: VLR needs to keep a locally configued list of LAIs */
	return true;
}

/* Determine if authentication is required */
static bool is_auth_required(struct lu_fsm_priv *lfp)
{
	/* The cases where the authentication procedure should be used
	 * are defined in 3GPP TS 33.102 */
	/* For now we use a default value passed in to vlr_lu_fsm(). */
	return lfp->authentication_required || lfp->ciphering_required;
}

/* Determine if ciphering is required */
static bool is_ciph_required(struct lu_fsm_priv *lfp)
{
	return lfp->ciphering_required;
}

/* Determine if a HLR Update is required */
static bool hlr_update_needed(struct vlr_subscr *vsub)
{
	/* TODO: properly decide this, rather than always assuming we
	 * need to update the HLR. */
	return true;
}

static inline struct lu_fsm_priv *lu_fsm_fi_priv(struct osmo_fsm_inst *fi);

static void lu_fsm_dispatch_result(struct osmo_fsm_inst *fi,
				   uint32_t prev_state)
{
	struct lu_fsm_priv *lfp = lu_fsm_fi_priv(fi);
	if (!fi->proc.parent) {
		LOGPFSML(fi, LOGL_ERROR, "No parent FSM\n");
		return;
	}
	osmo_fsm_inst_dispatch(fi->proc.parent,
			       (lfp->result == VLR_FSM_RESULT_SUCCESS)
			       ? lfp->parent_event_success
			       : lfp->parent_event_failure,
			       lfp->parent_event_data);
}

static void _lu_fsm_done(struct osmo_fsm_inst *fi,
			 enum vlr_fsm_result result)
{
	struct lu_fsm_priv *lfp = lu_fsm_fi_priv(fi);
	lfp->result = result;
	osmo_fsm_inst_state_chg(fi, VLR_ULA_S_DONE, 0, 0);
}

static void lu_fsm_success(struct osmo_fsm_inst *fi)
{
	_lu_fsm_done(fi, VLR_FSM_RESULT_SUCCESS);
}

static void lu_fsm_failure(struct osmo_fsm_inst *fi, enum gsm48_reject_value rej_cause)
{
	struct lu_fsm_priv *lfp = lu_fsm_fi_priv(fi);
	lfp->vlr->ops.tx_lu_rej(lfp->msc_conn_ref, rej_cause ? : GSM48_REJECT_NETWORK_FAILURE);
	_lu_fsm_done(fi, VLR_FSM_RESULT_FAILURE);
}

static void vlr_loc_upd_start_lu_compl_fsm(struct osmo_fsm_inst *fi)
{
	struct lu_fsm_priv *lfp = lu_fsm_fi_priv(fi);
	lfp->lu_compl_vlr_fsm =
		lu_compl_vlr_proc_alloc(fi, lfp->vsub, lfp->msc_conn_ref,
					VLR_ULA_E_LU_COMPL_SUCCESS,
					VLR_ULA_E_LU_COMPL_FAILURE,
					lfp->assign_tmsi);

	osmo_fsm_inst_dispatch(lfp->lu_compl_vlr_fsm, LU_COMPL_VLR_E_START, NULL);
}

static void lu_fsm_discard_lu_compl_fsm(struct osmo_fsm_inst *fi)
{
	struct lu_fsm_priv *lfp = lu_fsm_fi_priv(fi);
	if (!lfp->lu_compl_vlr_fsm)
		return;
	osmo_fsm_inst_term(lfp->lu_compl_vlr_fsm, OSMO_FSM_TERM_PARENT, NULL);
}

/* 4.1.2.1 Node 4 */
static void vlr_loc_upd_node_4(struct osmo_fsm_inst *fi)
{
	struct lu_fsm_priv *lfp = lu_fsm_fi_priv(fi);
	struct vlr_subscr *vsub = lfp->vsub;
	bool hlr_unknown = false;

	LOGPFSM(fi, "%s()\n", __func__);

	if (hlr_unknown) {
		/* FIXME: Delete subscriber record */
		/* LU REJ: Roaming not allowed */
		lu_fsm_failure(fi, GSM48_REJECT_ROAMING_NOT_ALLOWED);
	} else {
		/* Update_HLR_VLR */
		osmo_fsm_inst_state_chg(fi, VLR_ULA_S_WAIT_HLR_UPD,
					LU_TIMEOUT_LONG, 0);
		lfp->upd_hlr_vlr_fsm =
			upd_hlr_vlr_proc_start(fi, vsub, VLR_ULA_E_UPD_HLR_COMPL);
	}
}

/* 4.1.2.1 Node B */
static void vlr_loc_upd_node_b(struct osmo_fsm_inst *fi)
{
	LOGPFSM(fi, "%s()\n", __func__);

	/* OsmoHLR does not support PgA, neither stores the IMEISV, so we have no need to update the HLR
	 * with either. TODO: depend on actual HLR configuration. See 3GPP TS 23.012 Release 14, process
	 * Update_Location_Area_VLR (ULA_VLR2). */
	if (0) { /* IMEISV or PgA to send */
		vlr_loc_upd_node_4(fi);
	} else {
		/* Location_Update_Completion */
		osmo_fsm_inst_state_chg(fi, VLR_ULA_S_WAIT_LU_COMPL,
					LU_TIMEOUT_LONG, 0);
		vlr_loc_upd_start_lu_compl_fsm(fi);
	}
}

/* Non-standard: after Ciphering Mode Complete (or no ciph required) */
static void vlr_loc_upd_post_ciph(struct osmo_fsm_inst *fi)
{
	struct lu_fsm_priv *lfp = lu_fsm_fi_priv(fi);
	struct vlr_subscr *vsub = lfp->vsub;

	LOGPFSM(fi, "%s()\n", __func__);

	OSMO_ASSERT(vsub);

	if (lfp->is_utran) {
		int rc;
		rc = lfp->vlr->ops.tx_common_id(lfp->msc_conn_ref);
		if (rc)
			LOGPFSML(fi, LOGL_ERROR,
				 "Error while sending Common ID (%d)\n", rc);
	}

	vsub->conf_by_radio_contact_ind = true;
	/* Update LAI */
	vsub->cgi.lai = lfp->new_lai;
	vsub->dormant_ind = false;
	vsub->cancel_loc_rx = false;
	if (hlr_update_needed(vsub)) {
		vlr_loc_upd_node_4(fi);
	} else {
		/* TODO: ADD Support */
		/* TODO: Node A: PgA Support */
		vlr_loc_upd_node_b(fi);
	}
}

/* 4.1.2.1 after Authentication successful (or no auth rqd) */
static void vlr_loc_upd_post_auth(struct osmo_fsm_inst *fi)
{
	struct lu_fsm_priv *lfp = lu_fsm_fi_priv(fi);
	struct vlr_subscr *vsub = lfp->vsub;
	bool umts_aka;

	LOGPFSM(fi, "%s()\n", __func__);

	OSMO_ASSERT(vsub);

	if (!is_ciph_required(lfp)) {
		vlr_loc_upd_post_ciph(fi);
		return;
	}

	if (!vsub->last_tuple) {
		LOGPFSML(fi, LOGL_ERROR, "No auth tuple available\n");
		lu_fsm_failure(fi, GSM48_REJECT_NETWORK_FAILURE);
		return;
	}

	switch (vsub->sec_ctx) {
	case VLR_SEC_CTX_GSM:
		umts_aka = false;
		break;
	case VLR_SEC_CTX_UMTS:
		umts_aka = true;
		break;
	default:
		LOGPFSML(fi, LOGL_ERROR, "Cannot start ciphering, security context is not established\n");
		lu_fsm_failure(fi, GSM48_REJECT_NETWORK_FAILURE);
		return;
	}

	if (vlr_set_ciph_mode(vsub->vlr, fi, lfp->msc_conn_ref,
			      lfp->ciphering_required,
			      umts_aka,
			      vsub->vlr->cfg.retrieve_imeisv_ciphered)) {
		LOGPFSML(fi, LOGL_ERROR,
			 "Failed to send Ciphering Mode Command\n");
		lu_fsm_failure(fi, GSM48_REJECT_NETWORK_FAILURE);
		return;
	}

	osmo_fsm_inst_state_chg(fi, VLR_ULA_S_WAIT_CIPH, LU_TIMEOUT_LONG, 0);
}

static void vlr_loc_upd_node1(struct osmo_fsm_inst *fi)
{
	struct lu_fsm_priv *lfp = lu_fsm_fi_priv(fi);
	struct vlr_subscr *vsub = lfp->vsub;

	LOGPFSM(fi, "%s()\n", __func__);

	OSMO_ASSERT(vsub);

	if (is_auth_required(lfp)) {
		/* Authenticate_VLR */
		osmo_fsm_inst_state_chg(fi, VLR_ULA_S_WAIT_AUTH,
					LU_TIMEOUT_LONG, 0);
		vsub->auth_fsm = auth_fsm_start(lfp->vsub, fi->log_level,
						fi, VLR_ULA_E_AUTH_RES,
						lfp->is_r99,
						lfp->is_utran);
	} else {
		/* no need for authentication */
		vlr_loc_upd_post_auth(fi);
	}
}

static void vlr_loc_upd_want_imsi(struct osmo_fsm_inst *fi)
{
	struct lu_fsm_priv *lfp = lu_fsm_fi_priv(fi);
	struct vlr_instance *vlr = lfp->vlr;

	LOGPFSM(fi, "%s()\n", __func__);

	OSMO_ASSERT(lfp->vsub);

	/* Obtain_IMSI_VLR */
	osmo_fsm_inst_state_chg(fi, VLR_ULA_S_WAIT_IMSI,
				vlr_timer(vlr, 3270), 3270);
	vlr->ops.tx_id_req(lfp->msc_conn_ref, GSM_MI_TYPE_IMSI);
	/* will continue at vlr_loc_upd_node1() once IMSI arrives */
}

static int assoc_lfp_with_sub(struct osmo_fsm_inst *fi, struct vlr_subscr *vsub)
{
	struct lu_fsm_priv *lfp = lu_fsm_fi_priv(fi);
	struct vlr_instance *vlr = lfp->vlr;

	if (vsub->lu_fsm) {
		LOGPFSML(fi, LOGL_ERROR,
			 "A Location Updating process is already pending for"
			 " this subscriber. Aborting.\n");
		/* Also get rid of the other pending LU attempt? */
		/*lu_fsm_failure(vsub->lu_fsm, GSM48_REJECT_CONGESTION);*/
		lu_fsm_failure(fi, GSM48_REJECT_CONGESTION);
		return -EINVAL;
	}
	vsub->lu_fsm = fi;
	vsub->msc_conn_ref = lfp->msc_conn_ref;
	/* FIXME: send new LAC to HLR? */
	vsub->lac = lfp->new_lai.lac;
	lfp->vsub = vsub;
	/* Tell MSC to associate this subscriber with the given
	 * connection */
	vlr->ops.subscr_assoc(lfp->msc_conn_ref, lfp->vsub);
	return 0;
}

static int _lu_fsm_associate_vsub(struct osmo_fsm_inst *fi)
{
	struct lu_fsm_priv *lfp = lu_fsm_fi_priv(fi);
	struct vlr_instance *vlr = lfp->vlr;
	struct vlr_subscr *vsub = NULL;

	if (!lfp->imsi[0]) {
		/* TMSI was used */
		lfp->lu_by_tmsi = true;
		/* TMSI clash: if a different subscriber already has this TMSI,
		 * we will find that other subscriber in the VLR. So the IMSIs
		 * would mismatch, but we don't know about it. Theoretically,
		 * an authentication process would thwart any attempt to use
		 * someone else's TMSI.
		 * TODO: Otherwise we can ask for the IMSI and verify that it
		 * matches the IMSI on record. */
		vsub = vlr_subscr_find_or_create_by_tmsi(vlr, lfp->tmsi, NULL);

		if (!vsub) {
			LOGPFSML(fi, LOGL_ERROR, "VLR subscriber allocation failed\n");
			lu_fsm_failure(fi, GSM48_REJECT_SRV_OPT_TMP_OUT_OF_ORDER);
			return -1;
		}

		vsub->sub_dataconf_by_hlr_ind = false;
		if (assoc_lfp_with_sub(fi, vsub)) {
			vlr_subscr_put(vsub);
			return -1; /* error, fsm failure invoked in assoc_lfp_with_sub() */
		}
		vlr_subscr_put(vsub);
	} else {
		/* IMSI was used */
		vsub = vlr_subscr_find_or_create_by_imsi(vlr, lfp->imsi, NULL);

		if (!vsub) {
			LOGPFSML(fi, LOGL_ERROR, "VLR subscriber allocation failed\n");
			lu_fsm_failure(fi, GSM48_REJECT_SRV_OPT_TMP_OUT_OF_ORDER);
			vlr_subscr_put(vsub);
			return -1;
		}

		vsub->sub_dataconf_by_hlr_ind = false;
		if (assoc_lfp_with_sub(fi, vsub)) {
			vlr_subscr_put(vsub);
			return -1; /* error, fsm failure invoked in assoc_lfp_with_sub() */
		}
		vlr_subscr_put(vsub);
	}
	return 0;
}

/* 4.1.2.1: Subscriber (via MSC/SGSN) requests location update */
static void _start_lu_main(struct osmo_fsm_inst *fi)
{
	struct lu_fsm_priv *lfp = lu_fsm_fi_priv(fi);
	struct vlr_instance *vlr = lfp->vlr;

	/* TODO: PUESBINE related handling */

	/* Is previous LAI in this VLR? */
	if (!lai_in_this_vlr(vlr, &lfp->old_lai)) {
#if 0
		/* FIXME: check previous VLR, (3) */
		osmo_fsm_inst_state_chg(fi, VLR_ULA_S_WAIT_PVLR,
					LU_TIMEOUT_LONG, 0);
		return;
#endif
		LOGPFSML(fi, LOGL_NOTICE, "LAI change from %s,"
			 " but checking previous VLR not implemented\n",
			 osmo_lai_name(&lfp->old_lai));
	}

	/* If this is a TMSI based LU, we may not have the IMSI. Make sure that
	 * we know the IMSI, either on record, or request it. */
	if (!lfp->vsub->imsi[0])
		vlr_loc_upd_want_imsi(fi);
	else
		vlr_loc_upd_node1(fi);
}

static void lu_fsm_idle(struct osmo_fsm_inst *fi, uint32_t event,
			void *data)
{
	struct lu_fsm_priv *lfp = lu_fsm_fi_priv(fi);
	struct vlr_instance *vlr = lfp->vlr;

	OSMO_ASSERT(event == VLR_ULA_E_UPDATE_LA);

	if (_lu_fsm_associate_vsub(fi))
		return; /* error. FSM already terminated. */

	OSMO_ASSERT(lfp->vsub);

	/* See 3GPP TS 23.012, procedure Retrieve_IMEISV_If_Required */
	if ((!vlr->cfg.retrieve_imeisv_early)
	    || (lfp->type == VLR_LU_TYPE_PERIODIC && lfp->vsub->imeisv[0])) {
		/* R_IMEISV_IR1 passed */
		_start_lu_main(fi);
	} else {
		vlr->ops.tx_id_req(lfp->msc_conn_ref, GSM_MI_TYPE_IMEISV);
		osmo_fsm_inst_state_chg(fi, VLR_ULA_S_WAIT_IMEISV,
					vlr_timer(vlr, 3270), 3270);
	}
}

static void lu_fsm_wait_imeisv(struct osmo_fsm_inst *fi, uint32_t event,
			       void *data)
{
	switch (event) {
	case VLR_ULA_E_ID_IMEISV:
		/* IMEISV was copied in vlr_subscr_rx_id_resp(), and that's
		 * where we received this event from. */
		_start_lu_main(fi);
		break;
	default:
		LOGPFSML(fi, LOGL_ERROR, "event without effect: %s\n",
			 osmo_fsm_event_name(fi->fsm, event));
		break;
	}
}

/* Wait for response from Send_Identification to PVLR */
static void lu_fsm_wait_pvlr(struct osmo_fsm_inst *fi, uint32_t event,
			     void *data)
{
	switch (event) {
	case VLR_ULA_E_SEND_ID_ACK:
		vlr_loc_upd_node1(fi);
		break;
	case VLR_ULA_E_SEND_ID_NACK:
		vlr_loc_upd_want_imsi(fi);
		break;
	default:
		LOGPFSML(fi, LOGL_ERROR, "event without effect: %s\n",
			 osmo_fsm_event_name(fi->fsm, event));
		break;
	}
}

/* Wait for result of Authenticate_VLR procedure */
static void lu_fsm_wait_auth(struct osmo_fsm_inst *fi, uint32_t event,
			     void *data)
{
	struct lu_fsm_priv *lfp = lu_fsm_fi_priv(fi);
	enum gsm48_reject_value *res = data;

	OSMO_ASSERT(event == VLR_ULA_E_AUTH_RES);

	lfp->upd_hlr_vlr_fsm = NULL;

	if (!res || *res) {
		lu_fsm_failure(fi, res? *res : GSM48_REJECT_NETWORK_FAILURE);
		return;
	}

	/* Result == Pass */
	vlr_loc_upd_post_auth(fi);
}

static void lu_fsm_wait_ciph(struct osmo_fsm_inst *fi, uint32_t event,
			     void *data)
{
	struct lu_fsm_priv *lfp = lu_fsm_fi_priv(fi);
	struct vlr_subscr *vsub = lfp->vsub;
	struct vlr_ciph_result res = { .cause = VLR_CIPH_REJECT };

	OSMO_ASSERT(event == VLR_ULA_E_CIPH_RES);

	if (!data)
		LOGPFSML(fi, LOGL_ERROR, "invalid ciphering result: NULL\n");
	else
		res = *(struct vlr_ciph_result*)data;

	switch (res.cause) {
	case VLR_CIPH_COMPL:
		break;
	case VLR_CIPH_REJECT:
		LOGPFSM(fi, "ciphering rejected\n");
		lu_fsm_failure(fi, GSM48_REJECT_INVALID_MANDANTORY_INF);
		return;
	default:
		LOGPFSML(fi, LOGL_ERROR, "invalid ciphering result: %d\n",
			 res.cause);
		lu_fsm_failure(fi, GSM48_REJECT_INVALID_MANDANTORY_INF);
		return;
	}

	if (*res.imeisv) {
		LOGPFSM(fi, "got IMEISV: %s\n", res.imeisv);
		vlr_subscr_set_imeisv(vsub, res.imeisv);
	}
	vlr_loc_upd_post_ciph(fi);
}

static void lu_fsm_wait_imsi(struct osmo_fsm_inst *fi, uint32_t event,
			     void *data)
{
	struct lu_fsm_priv *lfp = lu_fsm_fi_priv(fi);
	struct vlr_subscr *vsub = lfp->vsub;
	char *mi_string = data;

	switch (event) {
	case VLR_ULA_E_ID_IMSI:
		vlr_subscr_set_imsi(vsub, mi_string);
		vlr_loc_upd_node1(fi);
		break;
	default:
		LOGPFSML(fi, LOGL_ERROR, "event without effect: %s\n",
			 osmo_fsm_event_name(fi->fsm, event));
		break;
	}
}

/* At the end of Update_HLR_VLR */
static void lu_fsm_wait_hlr_ul_res(struct osmo_fsm_inst *fi, uint32_t event,
				   void *data)
{
	struct lu_fsm_priv *lfp = lu_fsm_fi_priv(fi);

	switch (event) {
	case VLR_ULA_E_HLR_LU_RES:
		/* pass-through this event to Update_HLR_VLR */
		if (data == NULL)
			osmo_fsm_inst_dispatch(lfp->upd_hlr_vlr_fsm, UPD_HLR_VLR_E_UPD_LOC_ACK, NULL);
		else
			osmo_fsm_inst_dispatch(lfp->upd_hlr_vlr_fsm, UPD_HLR_VLR_E_UPD_LOC_NACK, data);
		break;
	case VLR_ULA_E_UPD_HLR_COMPL:
		if (data == NULL) {
			/* successful case */
			osmo_fsm_inst_state_chg(fi, VLR_ULA_S_WAIT_LU_COMPL,
						LU_TIMEOUT_LONG, 0);
			vlr_loc_upd_start_lu_compl_fsm(fi);
			/* continue in MSC ?!? */
		} else {
			/* unsuccessful case */
			enum gsm48_reject_value cause =
				*(enum gsm48_reject_value *)data;
			/* Ignoring standalone mode for now. */
			if (0 /* procedure_error && vlr->cfg.standalone_mode */) {
				osmo_fsm_inst_state_chg(fi,
						VLR_ULA_S_WAIT_LU_COMPL_STANDALONE,
						LU_TIMEOUT_LONG, 0);
				vlr_loc_upd_start_lu_compl_fsm(fi);
			} else {
				lu_fsm_failure(fi, cause);
			}
		}
		break;
	default:
		LOGPFSML(fi, LOGL_ERROR, "event without effect: %s\n",
			 osmo_fsm_event_name(fi->fsm, event));
		break;
	}
}

/* Wait for end of Location_Update_Completion_VLR */
static void lu_fsm_wait_lu_compl(struct osmo_fsm_inst *fi, uint32_t event,
				 void *data)
{
	struct lu_fsm_priv *lfp = lu_fsm_fi_priv(fi);
	uint8_t cause;

	switch (event) {
	case VLR_ULA_E_NEW_TMSI_ACK:
		osmo_fsm_inst_dispatch(lfp->lu_compl_vlr_fsm,
				       LU_COMPL_VLR_E_NEW_TMSI_ACK, NULL);
		break;
	case VLR_ULA_E_ID_IMEI:
		osmo_fsm_inst_dispatch(lfp->lu_compl_vlr_fsm,
				       LU_COMPL_VLR_E_IMEI_CHECK_ACK, NULL);
		break;
	case VLR_ULA_E_LU_COMPL_SUCCESS:
		lu_fsm_discard_lu_compl_fsm(fi);

		/* Update Register */
		/* TODO: Set_Notification_Type 23.078 */
		/* TODO: Notify_gsmSCF 23.078 */
		/* TODO: Authenticated Radio Contact Established -> ARC */

		if (lfp->type == VLR_LU_TYPE_IMSI_ATTACH)
			lfp->vlr->ops.tx_mm_info(lfp->msc_conn_ref);

		lu_fsm_success(fi);
		break;
	case VLR_ULA_E_LU_COMPL_FAILURE:
		cause = GSM48_REJECT_NETWORK_FAILURE;
		if (data)
			cause = *(uint8_t*)data;
		lu_fsm_discard_lu_compl_fsm(fi);
		lu_fsm_failure(fi, cause);
		break;
	default:
		LOGPFSML(fi, LOGL_ERROR, "event without effect: %s\n",
			 osmo_fsm_event_name(fi->fsm, event));
		break;
	}
}

/* Wait for end of Location_Update_Completion_VLR (standalone case) */
static void lu_fsm_wait_lu_compl_standalone(struct osmo_fsm_inst *fi,
					uint32_t event, void *data)
{
	struct lu_fsm_priv *lfp = lu_fsm_fi_priv(fi);
	struct vlr_subscr *vsub = lfp->vsub;
	uint8_t cause;

	switch (event) {
	case VLR_ULA_E_NEW_TMSI_ACK:
		osmo_fsm_inst_dispatch(lfp->lu_compl_vlr_fsm,
				       LU_COMPL_VLR_E_NEW_TMSI_ACK, NULL);
		break;
	case VLR_ULA_E_LU_COMPL_SUCCESS:
		lu_fsm_discard_lu_compl_fsm(fi);
		vsub->sub_dataconf_by_hlr_ind = false;
		lu_fsm_success(fi);
		break;
	case VLR_ULA_E_LU_COMPL_FAILURE:
		vsub->sub_dataconf_by_hlr_ind = false;
		cause = GSM48_REJECT_NETWORK_FAILURE;
		if (data)
			cause = *(uint8_t*)data;
		lu_fsm_discard_lu_compl_fsm(fi);
		lu_fsm_failure(fi, cause);
		break;
	default:
		LOGPFSML(fi, LOGL_ERROR, "event without effect: %s\n",
			 osmo_fsm_event_name(fi->fsm, event));
		break;
	}
}

static const struct osmo_fsm_state vlr_lu_fsm_states[] = {
	[VLR_ULA_S_IDLE] = {
		.in_event_mask = S(VLR_ULA_E_UPDATE_LA),
		.out_state_mask = S(VLR_ULA_S_WAIT_IMEISV) |
				  S(VLR_ULA_S_WAIT_PVLR) |
				  S(VLR_ULA_S_WAIT_IMSI) |
				  S(VLR_ULA_S_WAIT_AUTH) |
				  S(VLR_ULA_S_WAIT_HLR_UPD) |
				  S(VLR_ULA_S_DONE),
		.name = OSMO_STRINGIFY(VLR_ULA_S_IDLE),
		.action = lu_fsm_idle,
	},
	[VLR_ULA_S_WAIT_IMEISV] = {
		.in_event_mask = S(VLR_ULA_E_ID_IMEISV),
		.out_state_mask = S(VLR_ULA_S_WAIT_PVLR) |
				  S(VLR_ULA_S_WAIT_IMSI) |
				  S(VLR_ULA_S_WAIT_AUTH) |
				  S(VLR_ULA_S_WAIT_HLR_UPD) |
				  S(VLR_ULA_S_DONE),
		.name = OSMO_STRINGIFY(VLR_ULA_S_WAIT_IMEISV),
		.action = lu_fsm_wait_imeisv,
	},
	[VLR_ULA_S_WAIT_PVLR] = {
		.in_event_mask = S(VLR_ULA_E_SEND_ID_ACK) |
				 S(VLR_ULA_E_SEND_ID_NACK),
		.out_state_mask = S(VLR_ULA_S_WAIT_IMSI) |
				  S(VLR_ULA_S_WAIT_AUTH) |
				  S(VLR_ULA_S_DONE),
		.name = OSMO_STRINGIFY(VLR_ULA_S_WAIT_PVLR),
		.action = lu_fsm_wait_pvlr,
	},
	[VLR_ULA_S_WAIT_AUTH] = {
		.in_event_mask = S(VLR_ULA_E_AUTH_RES),
		.out_state_mask = S(VLR_ULA_S_WAIT_CIPH) |
				  S(VLR_ULA_S_WAIT_LU_COMPL) |
				  S(VLR_ULA_S_WAIT_HLR_UPD) |
				  S(VLR_ULA_S_DONE),
		.name = OSMO_STRINGIFY(VLR_ULA_S_WAIT_AUTH),
		.action = lu_fsm_wait_auth,
	},
	[VLR_ULA_S_WAIT_CIPH] = {
		.name = OSMO_STRINGIFY(VLR_ULA_S_WAIT_CIPH),
		.in_event_mask = S(VLR_ULA_E_CIPH_RES),
		.out_state_mask = S(VLR_ULA_S_WAIT_LU_COMPL) |
				  S(VLR_ULA_S_WAIT_HLR_UPD) |
				  S(VLR_ULA_S_DONE),
		.action = lu_fsm_wait_ciph,
	},
	[VLR_ULA_S_WAIT_IMSI] = {
		.in_event_mask = S(VLR_ULA_E_ID_IMSI),
		.out_state_mask = S(VLR_ULA_S_WAIT_AUTH) |
				  S(VLR_ULA_S_WAIT_HLR_UPD) |
				  S(VLR_ULA_S_DONE),
		.name = OSMO_STRINGIFY(VLR_ULA_S_WAIT_IMSI),
		.action = lu_fsm_wait_imsi,
	},
	[VLR_ULA_S_WAIT_HLR_UPD] = {
		.in_event_mask = S(VLR_ULA_E_HLR_LU_RES) |
				 S(VLR_ULA_E_UPD_HLR_COMPL),
		.out_state_mask = S(VLR_ULA_S_WAIT_LU_COMPL) |
				  S(VLR_ULA_S_WAIT_LU_COMPL_STANDALONE) |
				  S(VLR_ULA_S_DONE),
		.name = OSMO_STRINGIFY(VLR_ULA_S_WAIT_HLR_UPD),
		.action = lu_fsm_wait_hlr_ul_res,
	},
	[VLR_ULA_S_WAIT_LU_COMPL] = {
		.in_event_mask = S(VLR_ULA_E_LU_COMPL_SUCCESS) |
				 S(VLR_ULA_E_LU_COMPL_FAILURE) |
				 S(VLR_ULA_E_NEW_TMSI_ACK) |
				 S(VLR_ULA_E_ID_IMEI) |
				 S(VLR_ULA_E_ID_IMEISV),
		.out_state_mask = S(VLR_ULA_S_DONE),
		.name = OSMO_STRINGIFY(VLR_ULA_S_WAIT_LU_COMPL),
		.action = lu_fsm_wait_lu_compl,
	},
	[VLR_ULA_S_WAIT_LU_COMPL_STANDALONE] = {
		.in_event_mask = S(VLR_ULA_E_LU_COMPL_SUCCESS) |
				 S(VLR_ULA_E_LU_COMPL_FAILURE) |
				 S(VLR_ULA_E_NEW_TMSI_ACK),
		.out_state_mask = S(VLR_ULA_S_DONE),
		.name = OSMO_STRINGIFY(VLR_ULA_S_WAIT_LU_COMPL_STANDALONE),
		.action = lu_fsm_wait_lu_compl_standalone,
	},
	[VLR_ULA_S_DONE] = {
		.name = OSMO_STRINGIFY(VLR_ULA_S_DONE),
		.onenter = lu_fsm_dispatch_result,
	},
};

static void fsm_lu_cleanup(struct osmo_fsm_inst *fi, enum osmo_fsm_term_cause cause)
{
	struct lu_fsm_priv *lfp = lu_fsm_fi_priv(fi);
	struct vlr_subscr *vsub = lfp->vsub;

	LOGPFSM(fi, "fsm_lu_cleanup called with cause %s\n",
		osmo_fsm_term_cause_name(cause));
	if (vsub && vsub->lu_fsm == fi)
		vsub->lu_fsm = NULL;
}

static struct osmo_fsm vlr_lu_fsm = {
	.name = "vlr_lu_fsm",
	.states = vlr_lu_fsm_states,
	.num_states = ARRAY_SIZE(vlr_lu_fsm_states),
	.allstate_event_mask = 0,
	.allstate_action = NULL,
	.log_subsys = DVLR,
	.event_names = fsm_lu_event_names,
	.cleanup = fsm_lu_cleanup,
};

static inline struct lu_fsm_priv *lu_fsm_fi_priv(struct osmo_fsm_inst *fi)
{
	OSMO_ASSERT(fi->fsm == &vlr_lu_fsm);
	return (struct lu_fsm_priv*)fi->priv;
}

struct osmo_fsm_inst *
vlr_loc_update(struct osmo_fsm_inst *parent,
	       uint32_t parent_event_success,
	       uint32_t parent_event_failure,
	       void *parent_event_data,
	       struct vlr_instance *vlr, void *msc_conn_ref,
	       enum vlr_lu_type type, uint32_t tmsi, const char *imsi,
	       const struct osmo_location_area_id *old_lai,
	       const struct osmo_location_area_id *new_lai,
	       bool authentication_required,
	       bool ciphering_required,
	       bool is_r99, bool is_utran,
	       bool assign_tmsi)
{
	struct osmo_fsm_inst *fi;
	struct lu_fsm_priv *lfp;

	fi = osmo_fsm_inst_alloc_child(&vlr_lu_fsm, parent, parent_event_failure);
	if (!fi)
		return NULL;

	lfp = talloc_zero(fi, struct lu_fsm_priv);
	lfp->vlr = vlr;
	lfp->msc_conn_ref = msc_conn_ref;
	lfp->tmsi = tmsi;
	lfp->type = type;
	lfp->old_lai = *old_lai;
	lfp->new_lai = *new_lai;
	lfp->lu_by_tmsi = true;
	lfp->parent_event_success = parent_event_success;
	lfp->parent_event_failure = parent_event_failure;
	lfp->parent_event_data = parent_event_data;
	lfp->authentication_required = authentication_required;
	lfp->ciphering_required = ciphering_required;
	lfp->is_r99 = is_r99;
	lfp->is_utran = is_utran;
	lfp->assign_tmsi = assign_tmsi;
	if (imsi) {
		strncpy(lfp->imsi, imsi, sizeof(lfp->imsi)-1);
		lfp->imsi[sizeof(lfp->imsi)-1] = '\0';
		lfp->lu_by_tmsi = false;
	}
	fi->priv = lfp;

	LOGPFSM(fi, "rev=%s net=%s%s%s\n",
		is_r99 ? "R99" : "GSM",
		is_utran ? "UTRAN" : "GERAN",
		(authentication_required || ciphering_required)?
		" Auth" : " (no Auth)",
		(authentication_required || ciphering_required)?
			(ciphering_required? "+Ciph" : " (no Ciph)")
			: "");

	if (is_utran && !authentication_required)
		LOGPFSML(fi, LOGL_ERROR,
			 "Authentication off on UTRAN network. Good luck.\n");

	osmo_fsm_inst_dispatch(fi, VLR_ULA_E_UPDATE_LA, NULL);

	return fi;
}

void vlr_loc_update_cancel(struct osmo_fsm_inst *fi,
			   enum osmo_fsm_term_cause fsm_cause,
			   uint8_t gsm48_cause)
{
	struct lu_fsm_priv *lfp;

	OSMO_ASSERT(fi);
	OSMO_ASSERT(fi->fsm == &vlr_lu_fsm);

	lfp = fi->priv;
	lfp->rej_cause = gsm48_cause;

	if (fi->state != VLR_ULA_S_DONE)
		lu_fsm_failure(fi, gsm48_cause);
}

void vlr_lu_fsm_init(void)
{
	osmo_fsm_register(&vlr_lu_fsm);
	osmo_fsm_register(&upd_hlr_vlr_fsm);
	osmo_fsm_register(&sub_pres_vlr_fsm);
	osmo_fsm_register(&lu_compl_vlr_fsm);
}
