module RemsimClient_Tests {

/* Integration Tests for osmo-remsim-client
 * (C) 2019-2020 by Harald Welte <laforge@gnumonks.org>
 * All rights reserved.
 *
 * Released under the terms of GNU General Public License, Version 2 or
 * (at your option) any later version.
 *
 * SPDX-License-Identifier: GPL-2.0-or-later
 *
 * This test suite tests osmo-remsim-client by attaching to the external interfaces.
 */

import from Native_Functions all;
import from Osmocom_Types all;
import from IPA_Emulation all;
import from Misc_Helpers all;

/* the PIPEasp port allows us to interact with osmo-remsim-client-shell via stdin/stdout */
import from PIPEasp_PortType all;
import from PIPEasp_Types all;

import from RSPRO all;
import from RSPRO_Types all;
import from RSPRO_Server all;
import from REMSIM_Tests all;

modulepar {
	boolean mp_have_local_client := false; /* backwards compatible default */
	charstring mp_client_shell_cmd := "osmo-remsim-client-shell";
};

type component client_test_CT extends rspro_server_CT {
	port PIPEasp_PT PIPE;
	var ComponentIdentity g_srv_comp_id, g_bankd_comp_id;
	timer g_T_guard := 60.0;
};

private altstep as_Tguard() runs on client_test_CT {
	[] g_T_guard.timeout {
		setverdict(fail, "Timeout of T_guard");
		Misc_Helpers.f_shutdown(__BFILE__, __LINE__);
		}
}

private function f_init() runs on client_test_CT {
	g_srv_comp_id := valueof(ts_CompId(remsimServer, "ttcn-server"));
	g_bankd_comp_id := valueof(ts_CompId(remsimBankd, "ttcn-bankd"));

	/* Start the guard timer */
	g_T_guard.start;
	activate(as_Tguard());

	f_rspro_srv_init(0, mp_server_ip, mp_server_port, g_srv_comp_id);
	f_rspro_srv_init(1, mp_bankd_ip, mp_bankd_port, g_bankd_comp_id, exp_connect := false);
}


/* ConnectClientReq from client to remsim-server */
testcase TC_srv_connectClient() runs on client_test_CT {
	f_init();
	/* expect inbound connectClientReq */
	as_connectClientReq();
	setverdict(pass);
	f_sleep(1.0);
}

/* ConnectClientReq from client to remsim-server */
testcase TC_srv_connectClient_reject() runs on client_test_CT {
	f_init();
	/* expect inbound connectClientReq */
	as_connectClientReq(res := illegalClientId);
	/* expect disconnect by client */
	RSPRO_SRV[0].receive(tr_ASP_IPA_EV(ASP_IPA_EVENT_DOWN));
	setverdict(pass);
	f_sleep(1.0);
}

/* ConnectClientReq from client to remsim-server */
testcase TC_srv_connectClient_configClientBank() runs on client_test_CT {
	var BankSlot bslot := { 1, 0 };
	f_init();
	/* expect inbound connectClientReq */
	as_connectClientReq();
	/* configure client to connect to [simulated] bankd */
	f_rspro_config_client_bank(bslot, ts_IpPort(ts_IPv4(mp_bankd_ip), mp_bankd_port));
	/* expect inbound connect on simulated bankd */
	f_rspro_srv_exp_connect(1);
	/* expect inbound connectClientReq on simulated bankd */
	as_connectClientReq(i := 1);
	setverdict(pass);
	f_sleep(1.0);
}

/* Test if client re-connects to server after connection is lost */
testcase TC_srv_reconnect() runs on client_test_CT {
	var BankSlot bslot := { 1, 0 };
	f_init();
	/* expect inbound connectClientReq */
	as_connectClientReq();

	/* disconnect the client from server and expect re-establish + re-connect */
	f_rspro_srv_fini(0);
	f_rspro_srv_init(0, mp_server_ip, mp_server_port, g_srv_comp_id, exp_connect := true);
	/* expect inbound connectClientReq */
	as_connectClientReq(i := 0);

	setverdict(pass);
	f_sleep(1.0);
}

/* Test if client re-connects to bank after connection is lost */
testcase TC_bank_reconnect() runs on client_test_CT {
	var BankSlot bslot := { 1, 0 };
	f_init();
	/* expect inbound connectClientReq */
	as_connectClientReq();
	/* configure client to connect to [simulated] bankd */
	f_rspro_config_client_bank(bslot, ts_IpPort(ts_IPv4(mp_bankd_ip), mp_bankd_port));
	/* expect inbound connect on simulated bankd */
	f_rspro_srv_exp_connect(1);
	/* expect inbound connectClientReq on simulated bankd */
	as_connectClientReq(i := 1);

	/* disconnect the client from bankd and expect re-establish + re-connect */
	f_rspro_srv_fini(1);
	f_rspro_srv_init(1, mp_bankd_ip, mp_bankd_port, g_bankd_comp_id, exp_connect := true);
	/* expect inbound connectClientReq on simulated bankd */
	as_connectClientReq(i := 1);

	setverdict(pass);
	f_sleep(1.0);
}

/* Test if client disconnects from bankd after slotmap delete on server */
testcase TC_bank_disconnect() runs on client_test_CT {
	var BankSlot bslot := { 1, 0 };
	f_init();
	/* expect inbound connectClientReq */
	as_connectClientReq();
	/* configure client to connect to [simulated] bankd */
	f_rspro_config_client_bank(bslot, ts_IpPort(ts_IPv4(mp_bankd_ip), mp_bankd_port));
	/* expect inbound connect on simulated bankd */
	f_rspro_srv_exp_connect(1);
	/* expect inbound connectClientReq on simulated bankd */
	as_connectClientReq(i := 1);

	f_sleep(1.0);

	/* configure client to disconnect from [simulated] bankd */
	f_rspro_config_client_bank(bslot, ts_IpPort(ts_IPv4("0.0.0.0"), 0));

	/* expect disconnect of client on simulated bankd side */
	RSPRO_SRV[1].receive(tr_ASP_IPA_EV(ASP_IPA_EVENT_DOWN));
	setverdict(pass);
}

/* Test if client connects to bankd after disconnects from bankd after slotmap delete on server */
testcase TC_bank_disconnect_reconnect() runs on client_test_CT {
	var BankSlot bslot := { 1, 0 };
	f_init();
	/* expect inbound connectClientReq */
	as_connectClientReq();
	/* configure client to connect to [simulated] bankd */
	f_rspro_config_client_bank(bslot, ts_IpPort(ts_IPv4(mp_bankd_ip), mp_bankd_port));
	/* expect inbound connect on simulated bankd */
	f_rspro_srv_exp_connect(1);
	/* expect inbound connectClientReq on simulated bankd */
	as_connectClientReq(i := 1);

	f_sleep(1.0);

	/* configure client to disconnect from [simulated] bankd */
	f_rspro_config_client_bank(bslot, ts_IpPort(ts_IPv4("0.0.0.0"), 0));

	/* expect disconnect of client on simulated bankd side */
	RSPRO_SRV[1].receive(tr_ASP_IPA_EV(ASP_IPA_EVENT_DOWN));

	/* re-start the IPA emulation (which terminated itself on the TCP disconnect */
	f_rspro_srv_init(1, mp_bankd_ip, mp_bankd_port, g_bankd_comp_id, exp_connect := false);

	/* configure client to connect to [simulated] bankd */
	f_rspro_config_client_bank(bslot, ts_IpPort(ts_IPv4(mp_bankd_ip), mp_bankd_port));

	/* expect inbound connect on simulated bankd */
	f_rspro_srv_exp_connect(1);

	/* expect inbound connect on simulated bankd */
	as_connectClientReq(i := 1);

	setverdict(pass);
}

/***********************************************************************
 * Tests interacting with local remsim-bankd-client via PIPE port
 ***********************************************************************/

template (value) ASP_PExecuteBackground ts_ExecBg(charstring cmd) := {
	command := cmd
}

template (present) ASP_PStdout tr_Stdout(template (present) charstring line) := {
	stdout := line
}

template (present) ASP_PStderr tr_Stderr(template (present) charstring line) := {
	stderr := line
}

template (value) ASP_PStdin ts_Stdin(template (value) charstring line) := {
	stdin :=line
}

/* osmo-remsim-client logs to stderr, so we need to ignore that log output */
private altstep as_ignore_stderr() runs on client_test_CT {
[] PIPE.receive(tr_Stderr(?)) { repeat; }
}

/* start a local osmo-remsim-client as sub-process and attach it to PIPE port */
private function f_init_client_pipe(ClientSlot cs) runs on client_test_CT {
	var charstring cmdline := mp_client_shell_cmd & " -i 127.0.0.1";
	map(self:PIPE, system:PIPE);
	PIPE.send(ts_ExecBg(cmdline & " -c " & int2str(cs.clientId)
				    & " -n " & int2str(cs.slotNr)));
	activate(as_ignore_stderr());
}

/* pretty-print an octet string as series of ASCII encoded hex bytes with spaces */
function f_osmo_hexdump(octetstring input) return charstring {
	var charstring ret := "";
	for (var integer i := 0; i < lengthof(input); i := i+1) {
		ret := ret & f_str_tolower(oct2str(input[i])) & " ";
	}
	return ret;
}

/* simulated bankd instructs client to "set ATR"; expect it to show up on stdout */
function f_set_atr(template (value) ClientSlot cs, octetstring atr,
		   template ResultCode exp_res := ok, integer i := 0)
runs on client_test_CT {
	RSPRO_SRV[i].send(ts_RSPRO_SetAtrReq(cs, atr));
	interleave {
	[] RSPRO_SRV[i].receive(tr_RSPRO_SetAtrRes(exp_res));
	[] PIPE.receive(tr_Stdout("SET_ATR: " & f_osmo_hexdump(atr)));
	}
}

/* send a C-APDU from simulated application to client stdin; expect it on simulated bankd */
function f_client2bank(template (present) ClientSlot cs, template (present) BankSlot bs,
			octetstring c_apdu, integer i:=0) runs on client_test_CT
{
	/* send C-APDU via STDIN of osmo-remsim-client-shell */
	PIPE.send(ts_Stdin(oct2str(c_apdu)));
	/* expect the same C-APDU to arrive via RSPRO tpduModemToCard */
	f_rspro_srv_exp(tr_RSPRO_TpduModemToCard(cs, bs, ?, c_apdu), i);
}

/* send a R-APDU from simulated bankd to client; expect it on simualated app (client stdout) */
function f_bank2client(template (present) BankSlot bs, template (present) ClientSlot cs,
			octetstring r_apdu, boolean exp_fail := false, integer i:=0)
runs on client_test_CT {
	var TpduFlags flags := {
		tpduHeaderPresent:=true,
		finalPart:=true,
		procByteContinueTx:=false,
		procByteContinueRx:=false
	}
	timer T := 10.0;

	RSPRO_SRV[i].send(ts_RSPRO_TpduCardToModem(bs, cs, flags, r_apdu));
	T.start;
	alt {
	[] PIPE.receive(tr_Stdout("R-APDU: " & f_osmo_hexdump(r_apdu))) {
		if (exp_fail) {
			setverdict(fail, "Expected R-APDU to fail but still received it");
			self.stop;
		} else {
			setverdict(pass);
		}
		}
	[] PIPE.receive(tr_Stdout(?)) {
		setverdict(fail, "Unexpected R-APDU on stdout of remsim-client-shell");
		self.stop;
		}
	[] T.timeout {
		if (exp_fail) {
			setverdict(pass);
		} else {
			setverdict(fail, "Timeout waiting for R-APDU on remsim-client-shell");
			self.stop;
		}
		}
	}
}

/* Transceive a C+R APDU from client (via pipe) to simulated bankd and back */
function f_xceive_apdus(ClientSlot cslot, BankSlot bslot,
			integer count := 100, integer i := 0) runs on client_test_CT
{
	for (var integer j := 0; j < count; j := j+1) {
		var octetstring c_apdu := f_rnd_octstring_rnd_len(270);
		var octetstring r_apdu := f_rnd_octstring_rnd_len(270);
		f_client2bank(cslot, bslot, c_apdu, i:=i);
		f_bank2client(bslot, cslot, r_apdu, i:=i);
	}
}

/* transceive APDUs using forked osmo-remsim-client-shell + stdio */
testcase TC_pipe_xceive_apdus() runs on client_test_CT {
	var BankSlot bslot := { 1, 0 };
	var ClientSlot cslot := { 321, 123 };
	f_init_client_pipe(cslot);
	f_init();

	/* expect inbound connectClientReq */
	as_connectClientReq();
	/* configure client to connect to [simulated] bankd */
	f_rspro_config_client_bank(bslot, ts_IpPort(ts_IPv4(mp_bankd_ip), mp_bankd_port));
	/* expect inbound connect on simulated bankd */
	f_rspro_srv_exp_connect(1);
	/* expect inbound connectClientReq on simulated bankd */
	as_connectClientReq(i := 1);

	f_set_atr(cslot, '3B9F96801FC78031A073BE21136743200718000001A5'O, i:=1);

	f_xceive_apdus(cslot, bslot, count := 100, i:=1);
}

/* Send R-APDU from correct bankId/slotNr but to wrong ClientId */
testcase TC_pipe_apdu_wrong_cslot() runs on client_test_CT {
	var BankSlot bslot := { 1, 0 };
	var ClientSlot cslot := { 321, 123 };
	f_init_client_pipe(cslot);
	f_init();

	/* expect inbound connectClientReq */
	as_connectClientReq();
	/* configure client to connect to [simulated] bankd */
	f_rspro_config_client_bank(bslot, ts_IpPort(ts_IPv4(mp_bankd_ip), mp_bankd_port));
	/* expect inbound connect on simulated bankd */
	f_rspro_srv_exp_connect(1);
	/* expect inbound connectClientReq on simulated bankd */
	as_connectClientReq(i := 1);

	f_set_atr(cslot, '3B9F96801FC78031A073BE21136743200718000001A5'O, i:=1);

	var octetstring c_apdu := f_rnd_octstring_rnd_len(270);
	var octetstring r_apdu := f_rnd_octstring_rnd_len(270);
	/* Send C-APDU from correct ClientId/Slot to simulated bankd */
	f_client2bank(cslot, bslot, c_apdu, i:=1);
	/* respond with R-APDU from correct bankId/Slot but stating wrong ClientId */
	cslot.clientId := 1023;
	f_bank2client(bslot, cslot, r_apdu, exp_fail:=true, i:=1);
}

/* Send R-APDU from wrong bankId/slotNr but to correct ClientId/Slot */
testcase TC_pipe_apdu_wrong_bslot() runs on client_test_CT {
	var BankSlot bslot := { 1, 0 };
	var ClientSlot cslot := { 321, 123 };
	f_init_client_pipe(cslot);
	f_init();

	/* expect inbound connectClientReq */
	as_connectClientReq();
	/* configure client to connect to [simulated] bankd */
	f_rspro_config_client_bank(bslot, ts_IpPort(ts_IPv4(mp_bankd_ip), mp_bankd_port));
	/* expect inbound connect on simulated bankd */
	f_rspro_srv_exp_connect(1);
	/* expect inbound connectClientReq on simulated bankd */
	as_connectClientReq(i := 1);

	f_set_atr(cslot, '3B9F96801FC78031A073BE21136743200718000001A5'O, i:=1);

	var octetstring c_apdu := f_rnd_octstring_rnd_len(270);
	var octetstring r_apdu := f_rnd_octstring_rnd_len(270);
	/* Send C-APDU from correct ClientId/Slot to simulated bankd */
	f_client2bank(cslot, bslot, c_apdu, i:=1);
	/* respond with R-APDU from wrong bankId but stating correct ClientId */
	bslot.bankId := 1023;
	f_bank2client(bslot, cslot, r_apdu, exp_fail:=true, i:=1);
}


/* TODO:
   * send a configClientBankIpReq and change the bank of an active client
   * send a configClientBankSlotReq and chagne the bank slot of an active client
   * test keepalive mechanism: do we get IPA PING?
   * test keepalive mechanism: do we see disconnect+reconnect if we don't respond to IPA PING?
   * test messages in invalid state, e.g. APDUs before we're connected to a bank
   * test messages on server connection which are only permitted on bankd connection
 */

control {
	execute( TC_srv_connectClient() );
	execute( TC_srv_connectClient_reject() );
	execute( TC_srv_connectClient_configClientBank() );
	execute( TC_srv_reconnect() );
	execute( TC_bank_reconnect() );
	execute( TC_bank_disconnect() );
	execute( TC_bank_disconnect_reconnect() );

	if (mp_have_local_client) {
		execute( TC_pipe_xceive_apdus() );
		execute( TC_pipe_apdu_wrong_cslot() );
		execute( TC_pipe_apdu_wrong_bslot() );
	}
}


}
