module BTS_Tests_LAPDm {

import from GSM_Types all;
import from Osmocom_Types all;
import from LAPDm_RAW_PT all;
import from LAPDm_Types all;
import from RSL_Types all;
import from BTS_Tests all;
import from GSM_RR_Types all;
import from Misc_Helpers all;

/* test that use exclusively only LAPDm over L1CTL */
type component lapdm_test_CT {
	port LAPDm_PT LAPDM;
	var lapdm_CT lapdm_component;
};

/* contrary to BTS_Tests.ttcn, we use LAPDm_PT here, a convenience wrapper
 * around L1CTL to perform encode/decode of abstract LAPDm frames */

/*********************************************************************************
 * Test using only L1CTL/LAPDm
 *********************************************************************************/

function f_lapdm_init() runs on lapdm_test_CT {
	/* create the LAPDm component */
	lapdm_component := lapdm_CT.create;
	/* connect our own LAPDM port to the LAPDM Service Provider of the LAPDm component */
	connect(self:LAPDM, lapdm_component:LAPDM_SP);
	/* connect the LAPDm compoent's lower-side port to the system L1CTL port (which is internally
	 * connected to the Unix Domain Socket test port */
	map(lapdm_component:L1CTL, system:L1CTL);

	/* start the LAPDm parallel component calling it's local function LAPDmStart */
	lapdm_component.start(LAPDmStart());
}

function f_lapdm_exit() runs on lapdm_test_CT {
	lapdm_component.stop;
	lapdm_component.done;
	unmap(lapdm_component:L1CTL, system:L1CTL);
}

/* master function switching to a dedicated radio channel */
function f_switch_dcch() runs on ConnHdlr {
	var GsmBandArfcn arfcn := valueof(ts_GsmBandArfcn(mp_trx0_arfcn));
	var BCCH_tune_req tune_req := { arfcn := arfcn, combined_ccch := true };
	var DCCH_switch_req sw_req;

	/* Craft channel description (with or without frequency hopping parameters) */
	if (g_pars.fhp.enabled) {
		sw_req.chan_desc := valueof(ts_ChanDescH1(g_pars.chan_nr, g_pars.fhp.maio_hsn));
		sw_req.ma := g_pars.fhp.ma;
	} else {
		sw_req.chan_desc := valueof(ts_ChanDescH0(g_pars.chan_nr, mp_trx0_arfcn));
		sw_req.ma := omit;
	}

	LAPDM.send(tune_req);
	LAPDM.send(sw_req);
	LAPDM.receive(DCCH_switch_res:?);
}

/* helper function releasing dedicated radio channel physically (no Um signaling!) */
function f_release_dcch() runs on lapdm_test_CT {
	var DCCH_release_req rel_req := {};
	LAPDM.send(rel_req);
}

template LAPDm_ph_data t_PH_DATA(template GsmSapi sapi, template boolean sacch, template LapdmFrame frame) := {
	sacch := sacch,
	sapi := sapi,
	lapdm := frame
}

function f_test_sabm_results_in_ua(uint8_t sapi, boolean use_sacch, octetstring payload) runs on ConnHdlr return boolean {
	var LAPDm_ph_data phd;
	var boolean result := false;
	timer T := 5.0;

	LAPDM.send(t_PH_DATA(sapi, use_sacch, ts_LAPDm_SABM(sapi, c_r:=cr_MO_CMD, p:=false, l3:=payload)));
	T.start
	alt {
		[] LAPDM.receive(t_PH_DATA(?, use_sacch, tr_LAPDm_UA(sapi, cr_MT_RSP, f:=false, l3:=payload))) { result := true; }
		[] RSL.receive {repeat;}
		[] LAPDM.receive { repeat; }
		[] T.timeout { }
	}
	LAPDM.send(t_PH_DATA(sapi, use_sacch, ts_LAPDm_RR(sapi, c_r:=cr_MT_CMD, p:=false, nr:=0)));
	return result;
}

function f_TC_sabm_ua_dcch_sapi0(charstring id) runs on ConnHdlr {
	fp_common_init();
	RSL.clear;
	LAPDM.clear;
	var default d := activate(as_ignore_background());
	if (not f_test_sabm_results_in_ua(0, false, 'FEFE'O)) {
		setverdict(fail);
	}
	setverdict(pass);
	deactivate(d);
	fp_common_fini();
}

function f_TC_sabm_ua_dcch_sapi0_nopayload(charstring id) runs on ConnHdlr {
	fp_common_init();
	RSL.clear;
	LAPDM.clear;
	var default d := activate(as_ignore_background());
	if (f_test_sabm_results_in_ua(0, false, ''O)) {
		setverdict(fail, "Initial SABM/UA must contain L3 payload but BTS accepts without");
	}
	setverdict(pass);
	deactivate(d);
	fp_common_fini();
}

function f_TC_sabm_ua_dcch_sapi3(charstring id) runs on ConnHdlr {
	fp_common_init();
	RSL.clear;
	LAPDM.clear;
	var default d := activate(as_ignore_background());
	if (f_test_sabm_results_in_ua(3, false, 'FEFE'O)) {
		setverdict(fail, "Initial SABM/UA must be on SAPI0, but BTS accepts SAPI=3");
	}
	setverdict(pass);
	deactivate(d);
	fp_common_fini();
}

function f_TC_sabm_ua_dcch_sapi4(charstring id) runs on ConnHdlr {
	fp_common_init();
	RSL.clear;
	LAPDM.clear;
	var default d := activate(as_ignore_background());
	if (f_test_sabm_results_in_ua(4, false, 'FEFE'O)) {
		setverdict(fail, "Initial SABM/UA must be on SAPI0, but BTS accepts SAPI=4");
	}
	setverdict(pass);
	deactivate(d);
	fp_common_fini();
}

testcase TC_sabm_ua_dcch_sapi0() runs on test_CT {
	var ConnHdlrPars pars := valueof(t_Pars(t_RslChanNr_Bm(1), ts_RSL_ChanMode_SIGN));
	f_testmatrix_each_chan(pars, refers(f_TC_sabm_ua_dcch_sapi0));
}

testcase TC_sabm_ua_dcch_sapi0_nopayload() runs on test_CT {
	var ConnHdlrPars pars := valueof(t_Pars(t_RslChanNr_Bm(1), ts_RSL_ChanMode_SIGN));
	f_testmatrix_each_chan(pars, refers(f_TC_sabm_ua_dcch_sapi0_nopayload));
}

testcase TC_sabm_ua_dcch_sapi3() runs on test_CT {
	var ConnHdlrPars pars := valueof(t_Pars(t_RslChanNr_Bm(1), ts_RSL_ChanMode_SIGN));
	f_testmatrix_each_chan(pars, refers(f_TC_sabm_ua_dcch_sapi3));
}

testcase TC_sabm_ua_dcch_sapi4() runs on test_CT {
	var ConnHdlrPars pars := valueof(t_Pars(t_RslChanNr_Bm(1), ts_RSL_ChanMode_SIGN));
	f_testmatrix_each_chan(pars, refers(f_TC_sabm_ua_dcch_sapi4));
}

function f_TC_sabm_contention(charstring id) runs on ConnHdlr {
	var LAPDm_ph_data phd;
	const octetstring payload := '0102030405'O;
	const GsmSapi sapi := 0;
	const boolean use_sacch := false;
	timer T := 5.0;

	fp_common_init();
	RSL.clear;
	LAPDM.clear;

	/* first frame is our real SABM */
	LAPDM.send(t_PH_DATA(sapi, use_sacch, ts_LAPDm_SABM(sapi, c_r:=cr_MO_CMD, p:=false, l3:=payload)));
	/* second frame is a SABM with different payload, which BTS has to ignore according to 8.4.1.4 */
	LAPDM.send(t_PH_DATA(sapi, use_sacch, ts_LAPDm_SABM(sapi, c_r:=cr_MO_CMD, p:=false, l3:='ABCDEF'O)));
	T.start
	alt {
		[] LAPDM.receive(t_PH_DATA(?, use_sacch, tr_LAPDm_UA(sapi, cr_MT_RSP, f:=false, l3:=payload))) { setverdict(pass); repeat; }
		[] LAPDM.receive(t_PH_DATA(?, use_sacch, tr_LAPDm_UA(sapi, cr_MT_RSP, f:=false, l3:=?))) {
			setverdict(fail, "Second SABM was responded to during contention resolution");
			}
		[] RSL.receive {repeat;}
		[] LAPDM.receive { repeat };
		[] T.timeout { }
	}

	fp_common_fini();
}

testcase TC_sabm_contention() runs on test_CT {
	var ConnHdlrPars pars := valueof(t_Pars(t_RslChanNr_Bm(1), ts_RSL_ChanMode_SIGN));
	f_testmatrix_each_chan(pars, refers(f_TC_sabm_contention));
}

/* we test that a re-transmitted SABM with identical payload will result in the retransmission of a
  * UA. This is required during the contention resolution procedure as specified in 8.4.1.4 */
function f_TC_sabm_retransmit(charstring id) runs on ConnHdlr {
	const octetstring payload := '00FEFEDEADBEEF'O;
	fp_common_init();
	RSL.clear;
	LAPDM.clear;
	var default d := activate(as_ignore_background());
	if (not f_test_sabm_results_in_ua(0, false, payload)) {
		setverdict(fail);
	}
	if (not f_test_sabm_results_in_ua(0, false, payload)) {
		setverdict(fail);
	}
	setverdict(pass);
	deactivate(d);
	fp_common_fini();
}

testcase TC_sabm_retransmit() runs on test_CT {
	var ConnHdlrPars pars := valueof(t_Pars(t_RslChanNr_Bm(1), ts_RSL_ChanMode_SIGN));
	f_testmatrix_each_chan(pars, refers(f_TC_sabm_retransmit));
}

/*********************************************************************************
 * Test using both L1CTL/LAPDm and RSL
 *********************************************************************************/

private function fp_common_init() runs on ConnHdlr
{
	/* undo what f_start_handler is doing and pull LAPDm_CT into the loop */
	unmap(self:L1CTL, system:L1CTL);
	f_lapdm_init();

	/* Obtain frequency hopping parameters for a given timeslot */
	if (mp_freq_hop_enabled and mp_transceiver_num > 1) {
		f_resolve_fh_params(g_pars.fhp, g_pars.chan_nr.tn);
	}

	/* activate the channel on the BTS side */
	f_rsl_chan_act(g_pars.chan_mode, false, {});
	/* activate the channel on the MS side */
	f_switch_dcch();
}

private function fp_common_fini() runs on ConnHdlr
{
	f_release_dcch();
	f_rsl_chan_deact();
	f_lapdm_exit();
}

/* Mobile-Originated LAPDm establishment on given Link ID */
private function f_establish_mo(RslLinkId link_id) runs on ConnHdlr
{
	var integer sapi := link_id.sapi;
	var boolean is_sacch := false;
	if (link_id.c == SACCH) {
		is_sacch := true;
	}

	var octetstring l3_mo := f_rnd_octstring(5);

	/* MO Establish Request via LADPm: SAPI = 0, C = 0, P = 1, M = 0, 0 ≤ L ≤ N201.. */
	if (is_sacch) {
		/* no payload permitted, as this is not contention resolution */
		l3_mo := ''O;
		LAPDM.send(t_PH_DATA(0, is_sacch, ts_LAPDm_SABM(sapi, c_r:=cr_MO_CMD, p:=true, l3:=l3_mo)));
		RSL.receive(tr_RSL_EST_IND_NOL3(g_chan_nr, link_id));
	} else {
		LAPDM.send(t_PH_DATA(0, is_sacch, ts_LAPDm_SABM(sapi, c_r:=cr_MO_CMD, p:=true, l3:=l3_mo)));
		RSL.receive(tr_RSL_EST_IND(g_chan_nr, link_id, l3_mo));
	}
	/* UA: SAPI = 0, R = 0, F = 1, M = 0, L = L of SABM. */
	LAPDM.receive(t_PH_DATA(0, is_sacch, tr_LAPDm_UA(sapi, cr_MT_RSP, f:=true, l3:=l3_mo)));
}

/* Verify that the BTS is re-transmitting SABM messages after T200 timeout, inspired
   by 3GPP TS 51.010-1 25.2.1.1.2.1 + 25.2.1.2.4 */
private function f_TC_sabm_retransmit_bts(charstring id) runs on ConnHdlr {
	const integer sapi := 3; /* BTS may not establish SAPI=0 outbound */
	fp_common_init();

	LAPDM.clear;
	RSL.send(ts_RSL_EST_REQ(g_chan_nr, ts_RslLinkID_DCCH(sapi)));

	timer T := 8.0;
	var integer sabm_received := 0;
	T.start;
	alt {
	[] LAPDM.receive(t_PH_DATA(0, false, tr_LAPDm_SABM(sapi, ?, ?, ''O))) {
		sabm_received := sabm_received + 1;
		repeat;
		}
	[] LAPDM.receive { repeat; }
	[] T.timeout { }
	}
	if (sabm_received == 0) {
		setverdict(fail, "No SABM observed at all!");
	} else if (sabm_received != 6) {
		setverdict(fail, "Incorrect number of SABM re-transmissions of observed: ",
			   sabm_received);
	} else {
		setverdict(pass, "Received ", sabm_received, " SABM");
	}

	fp_common_fini();
}
testcase TC_sabm_retransmit_bts() runs on test_CT {
	var ConnHdlrPars pars := valueof(t_Pars(t_RslChanNr_Bm(1), ts_RSL_ChanMode_SIGN));
	f_testmatrix_each_chan(pars, refers(f_TC_sabm_retransmit_bts));
}


type record LapdmNamedFrame {
	charstring name,
	LapdmFrame lapdm
};

/* Test that the BTS will ignore receipt of frames other than a UA when
 * received in response to the SABM frame, inspired from 3GPP TS 51.010-1
 * Section 25.2.1.1.2.3 */
private function f_TC_sabm_invalid_resp2(charstring id, LapdmNamedFrame err_frame) runs on ConnHdlr {
	var integer sapi := err_frame.lapdm.ab.addr.sapi;
	fp_common_init();

	/* Establish Request via RSL; Expect SABM on LAPDm side */
	LAPDM.clear;
	RSL.send(ts_RSL_EST_REQ(g_chan_nr, ts_RslLinkID_DCCH(sapi)));
	alt {
	[] LAPDM.receive(t_PH_DATA(0, false, tr_LAPDm_SABM(sapi, ?, ?, ''O)));
	[] LAPDM.receive { repeat; }
	}

	/* send erroneous response to SABM */
	LAPDM.send(t_PH_DATA(0, false, err_frame.lapdm));

	/* expect a SABM retransmission of the BTS */
	timer T := 3.0;
	T.start;
	alt {
	[] LAPDM.receive(t_PH_DATA(0, false, tr_LAPDm_SABM(sapi, ?, ?, ''O))) {
		setverdict(pass);
		}
	[] LAPDM.receive(t_PH_DATA(0, false, tr_LAPDm_UI(0, ?, ''O))) { repeat; }
	[] LAPDM.receive(t_PH_DATA(0, false, ?)) {
		setverdict(fail, "Received unexpected LAPDm frame instead of SABM after sending ",
			   err_frame.name);
		}
	[] LAPDM.receive { repeat; }
	[] T.timeout {
		setverdict(fail, "Timeout waiting for SABM retransmission after sending ",
			   err_frame.name);
		}
	}

	fp_common_fini();
}
private function f_TC_sabm_invalid_resp(charstring id) runs on ConnHdlr {
	const integer sapi := 3; /* BTS may not establish SAPI=0 outbound */
	var LapdmNamedFrame err_frame[3] := {
		{ "I", valueof(ts_LAPDm_I(sapi, c_r := cr_MO_CMD, p := true, nr := 0, ns := 0,
					  l3 := '01020304'O)) },
		{ "RR", valueof(ts_LAPDm_RR(sapi, c_r := cr_MO_CMD, p := true, nr := 0)) },
		{ "REJ" , valueof(ts_LAPDm_REJ(sapi, c_r := cr_MO_CMD, p := true, nr := 0)) }
	};
	var integer i;

	for (i := 0; i < lengthof(err_frame); i := i+1) {
		f_TC_sabm_invalid_resp2(id, err_frame[i])
	}
}
testcase TC_sabm_invalid_resp() runs on test_CT {
	var ConnHdlrPars pars := valueof(t_Pars(t_RslChanNr_Bm(1), ts_RSL_ChanMode_SIGN));
	f_testmatrix_each_chan(pars, refers(f_TC_sabm_invalid_resp));
}

/* Test that the BTS will not re-transmit SABM frames after receiving a DM response,
 * inspired from 3GPP TS 51.010-1 Section 25.2.1.1.3 */
private function f_TC_sabm_dm(charstring id) runs on ConnHdlr {
	const integer sapi := 3; /* BTS may not establish SAPI=0 outbound */
	fp_common_init();

	/* Establish Request via RSL; Expect SABM on LAPDm side */
	LAPDM.clear;
	RSL.send(ts_RSL_EST_REQ(g_chan_nr, ts_RslLinkID_DCCH(sapi)));
	alt {
	[] LAPDM.receive(t_PH_DATA(0, false, tr_LAPDm_SABM(sapi, ?, ?, ''O)));
	[] LAPDM.receive { repeat; }
	}

	/* send DM response to SABM */
	RSL.clear;
	LAPDM.send(t_PH_DATA(0, false, ts_LAPDm_DM(sapi, c_r:=cr_MO_RSP, f:=true)));
	alt {
	[] RSL.receive(tr_RSL_REL_IND(g_chan_nr, tr_RslLinkID_DCCH(sapi)));
	[] RSL.receive { repeat; }
	}

	/* expect no SABM retransmission of the BTS */
	timer T := 3.0;
	T.start;
	alt {
	[] LAPDM.receive(t_PH_DATA(0, false, tr_LAPDm_SABM(sapi, ?, ?, ''O))) {
		setverdict(fail, "Received unexpected SABM retransmission");
		}
	[] LAPDM.receive(t_PH_DATA(0, false, tr_LAPDm_UI(0, ?, ''O))) { repeat; }
	[] LAPDM.receive(t_PH_DATA(0, false, ?)) {
		setverdict(fail, "Received unexpected LAPDm frame");
		}
	[] LAPDM.receive { repeat; }
	[] T.timeout {
		setverdict(pass);
		}
	}

	fp_common_fini();
}
testcase TC_sabm_dm() runs on test_CT {
	var ConnHdlrPars pars := valueof(t_Pars(t_RslChanNr_Bm(1), ts_RSL_ChanMode_SIGN));
	f_testmatrix_each_chan(pars, refers(f_TC_sabm_dm));
}

/* Test the full LAPDm establishment while simulating the loss of the initial SABM or UA
 * frame, requiring the BTS to re-transmit one SABM and then following up all the way to
 * dedicated mode; inspired by 3GPP TS 51.010-1 25.2.1.2.2  */
private function f_TC_establish_ign_first_sabm(charstring id) runs on ConnHdlr {
	const integer sapi := 3; /* BTS may not establish SAPI=0 outbound */
	var integer num_sabm := 0;
	var RslLinkId link_id := valueof(ts_RslLinkID_DCCH(sapi));
	timer T := 3.0;

	fp_common_init();

	/* Establish Request via RSL */
	LAPDM.clear;
	RSL.send(ts_RSL_EST_REQ(g_chan_nr, link_id));
	/* Expect two SABM (retransmit) */
	T.start;
	alt {
	[] LAPDM.receive(t_PH_DATA(0, false, tr_LAPDm_SABM(sapi, ?, ?, ''O))) {
		num_sabm := num_sabm + 1;
		if (num_sabm < 2) {
			repeat;
		}
		}
	[] LAPDM.receive { repeat; }
	}

	/* send UA response to SABM */
	RSL.clear;
	LAPDM.send(t_PH_DATA(0, false, ts_LAPDm_UA(sapi, c_r:=cr_MO_RSP, f:=true, l3:=''O)));
	alt {
	[] RSL.receive(tr_RSL_EST_CONF(g_chan_nr, link_id));
	[] RSL.receive { repeat; }
	}

	/* Send I frame from BTS to MS */
	var octetstring l3 := f_rnd_octstring(10);
	RSL.send(ts_RSL_DATA_REQ(g_chan_nr, link_id, l3));
	alt {
	[] LAPDM.receive(t_PH_DATA(0, false, tr_LAPDm_I(sapi, c_r:=cr_MT_CMD, p:=false,
							nr:=0, ns:=0, l3:=l3)));
	[] LAPDM.receive(t_PH_DATA(0, false, tr_LAPDm_UI(0, ?, ''O))) { repeat; }
	[] LAPDM.receive(t_PH_DATA(0, true, ?)) { repeat; }
	[] LAPDM.receive { setverdict(fail, "Unexpected LAPDm received"); }
	}
	/* Send RR frame in response */
	LAPDM.send(t_PH_DATA(0, false, ts_LAPDm_RR(sapi, c_r:=cr_MO_RSP, p:=false, nr:=1)));

	/* expect idle UI Frame from BTS */
	alt {
	[] LAPDM.receive(t_PH_DATA(0, false, tr_LAPDm_UI(0, ?, ''O))) {
		setverdict(pass);
		}
	[] LAPDM.receive(t_PH_DATA(0, true, ?)) { repeat; }
	[] LAPDM.receive { setverdict(fail, "Unexpected LAPDm received"); }
	}

	fp_common_fini();
}
testcase TC_establish_ign_first_sabm() runs on test_CT {
	var ConnHdlrPars pars := valueof(t_Pars(t_RslChanNr_Bm(1), ts_RSL_ChanMode_SIGN));
	f_testmatrix_each_chan(pars, refers(f_TC_establish_ign_first_sabm));
}

/* ignore all SACCH frames */
private altstep as_lapdm_acch() runs on ConnHdlr {
	[] LAPDM.receive(t_PH_DATA(0, true, ?)) { repeat; }
}
/* ignore all DCCH frames */
private altstep as_lapdm_dcch() runs on ConnHdlr {
	[] LAPDM.receive(t_PH_DATA(0, false, ?)) { repeat; }
}
/* ignore all LAPDm idle frames (UI) */
private altstep as_lapdm_idle() runs on ConnHdlr {
	[] LAPDM.receive(t_PH_DATA(0, ?, tr_LAPDm_UI(?, ?, ''O))) { repeat; }
}
/* ignore all measurement reports */
private altstep as_rsl_meas_rep() runs on ConnHdlr {
	[] RSL.receive(tr_RSL_MEAS_RES(g_chan_nr)) { repeat; }
}
/* fail if we receive an RSL ERROR IND */
private altstep as_rsl_fail_err() runs on ConnHdlr {
	var RSL_Message rx_rsl;
	[] RSL.receive(tr_RSL_ERROR_IND(g_chan_nr, ?, ?)) {
		setverdict(fail, "Received RSL ERROR IND ", rx_rsl);
	}
}
/* all of the above */
private altstep as_ignore_background(boolean want_dcch := true, boolean ignore_rsl_errors := false) runs on ConnHdlr {
	[want_dcch] as_lapdm_acch();
	[not want_dcch] as_lapdm_dcch();
	[] as_lapdm_idle();
	[] as_rsl_meas_rep();
	[not ignore_rsl_errors] as_rsl_fail_err();
	[ignore_rsl_errors] RSL.receive(tr_RSL_ERROR_IND(g_chan_nr, ?, ?)) { repeat;}
}

/* Test the operation of Layer 2 sequence numbering.
 * dedicated mode; inspired by 3GPP TS 51.010-1 25.2.2.1  */
private function f_TC_iframe_seq_and_ack(charstring id) runs on ConnHdlr {
	const integer sapi := 0;
	var RslLinkId link_id := valueof(ts_RslLinkID_DCCH(sapi));
	var octetstring l3 := f_rnd_octstring(18);
	var default d;
	timer T := 3.0;

	fp_common_init();

	/* some common altstep for meas res and other background noise */
	d := activate(as_ignore_background());
	RSL.clear;
	LAPDM.clear;

	f_establish_mo(link_id);

	var integer last_ns_rx := 0;

	for (var integer i := 0; i < 10; i := i+1) {
		var octetstring l3_mo := f_rnd_octstring(12);
		var octetstring l3_mt := f_rnd_octstring(12);
		var LAPDm_ph_data pd;

		log("Starting iteration ", i);
		/* MT I frame */
		RSL.send(ts_RSL_DATA_REQ(g_chan_nr, link_id, l3_mt));
		alt {
		/* SAPI = 0, R = 1, F = 0, M = 0, L = 0. */
		[] LAPDM.receive(t_PH_DATA(0, false, tr_LAPDm_RR(sapi, c_r:=cr_MT_RSP, p:=false,
								 nr:=i mod 8))) {
			log("Ignoring RR in iteration ", i);
			repeat;
			}
		/* SAPI = 0, C = 1, P = 0, M = 0, 0 ≤ L ≤ N201. */
		[] LAPDM.receive(t_PH_DATA(0, false, tr_LAPDm_I(sapi, c_r:=cr_MT_CMD, p:=false,
								nr:=i mod 8, ns:=i mod 8,
								l3:=l3_mt))) -> value pd {
			last_ns_rx := pd.lapdm.ab.ctrl.i.n_s;
			}
		}
		/* respond with MO I-frame: SAPI = 0, C = 0, P = 0, M = 0, 0 <= L <= N201. */
		LAPDM.send(t_PH_DATA(0, false, ts_LAPDm_I(sapi, c_r:=cr_MO_CMD, p:=false,
							  nr:=(last_ns_rx+1)mod 8,
							  ns:=i mod 8, l3 := l3_mo)));
		RSL.receive(tr_RSL_DATA_IND(g_chan_nr, link_id, l3_mo));
	}
	log("Completed iteration");

	deactivate(d);
	fp_common_fini();
}
testcase TC_iframe_seq_and_ack() runs on test_CT {
	var ConnHdlrPars pars := valueof(t_Pars(t_RslChanNr_Bm(1), ts_RSL_ChanMode_SIGN));
	f_testmatrix_each_chan(pars, refers(f_TC_iframe_seq_and_ack));
}

/* To test that the BTS is able to respond to I frames whilst in the timer recovery state.
 * Inspired by 3GPP TS 51.010-1 25.2.2.2  */

/*
  1) The BTS is brought into the multiple frame established state
  2) The MS sends an L3 Request asking for IMEI to the MS.
  3) The BTS shall respond with a RR frame though this may be incorporated with
     the L3 Response I frame.  The MS does not respond to the I frame.
  4) The BTS shall wait for expiry of timer T200 and then repeat the I frame but
     with the P bit set to 1.
  5) The MS then sends a valid L3 Request I frame asking for IMEI which
     does not acknowledge receipt of the I frame from the BTS.
On the FACCH the BTS may send an RR frame acknowledging the I frame.
  6) The BTS shall repeat the I frame, this frame will acknowledge receipt of
     the second I frame from the MS.
  7) The MS then acknowledges receipt of the MS I frame by sending a RR frame.
  8) The BTS shall send the next I frame. The MS acknowledges this I frame.
*/
private function f_TC_iframe_timer_recovery(charstring id) runs on ConnHdlr {
	const integer sapi := 0;
	var RslLinkId link_id := valueof(ts_RslLinkID_DCCH(sapi));
	var default d;
	timer T := 3.0;

	fp_common_init();

	/* some common altstep for meas res and other background noise */
	d := activate(as_ignore_background());
	RSL.clear;
	LAPDM.clear;

	var octetstring l3_mo := f_rnd_octstring(12);
	var octetstring l3_mt := f_rnd_octstring(12);

	/*  1) The BTS is brought into the multiple frame established state */

	/* MO Establish Request via LADPm: SAPI = 0, C = 0, P = 1, M = 0, 0 ≤ L ≤ N201.. */
	LAPDM.send(t_PH_DATA(0, false, ts_LAPDm_SABM(sapi, c_r:=cr_MO_CMD, p:=true, l3:=l3_mo)));
	RSL.receive(tr_RSL_EST_IND(g_chan_nr, link_id, l3_mo));
	/* UA: SAPI = 0, R = 0, F = 1, M = 0, L = L of SABM. */
	LAPDM.receive(t_PH_DATA(0, false, tr_LAPDm_UA(sapi, cr_MT_RSP, f:=true, l3:=l3_mo)));

	/* 2) The MS sends an L3 Request to the BTS */
	l3_mo := f_rnd_octstring(18);
	/* SAPI = 0, C = 1, P = 0, M = 0, 0 ≤ L ≤ N201, N(S) = 0, N(R) = 0.  * */
	LAPDM.send(t_PH_DATA(0, false, ts_LAPDm_I(sapi, c_r:=cr_MO_CMD, p:=false,
						  nr:=0, ns:=0, l3:=l3_mo)));
	RSL.receive(tr_RSL_DATA_IND(g_chan_nr, link_id, l3_mo));
	/* 3) The BTS shall respond with a RR frame though this may be incorporated with
	   the L3 Response I frame.  The MS does not respond to the I frame. */
	RSL.send(ts_RSL_DATA_REQ(g_chan_nr, link_id, l3_mt));
	alt {
	/* SAPI = 0, R = 1, F = 0, M = 0, L = 0, N(R) = 1. */
	[] LAPDM.receive(t_PH_DATA(0, false, tr_LAPDm_RR(sapi, c_r:=cr_MT_RSP, p:=false, nr:=1))) {
		repeat;
		}
	/* SAPI = 0, C = 0, P = 0, M = 0, 0 ≤ L ≤ N201, N(R) = 1, N(S) = 0 */
	[] LAPDM.receive(t_PH_DATA(0, false, tr_LAPDm_I(sapi, c_r:=cr_MT_CMD, p:=false,
							nr:=1, ns:=0, l3:=l3_mt)));
	}

	/* 4) The BTS shall wait for expiry of timer T200 and then repeat the I frame but
	      with the P bit set to 1. */
	/* SAPI = 0, C = 0, P = 1, M = 0, 0 ≤ L ≤ N201, N(R) = 1, N(S) = 0. * */
	LAPDM.receive(t_PH_DATA(0, false, tr_LAPDm_I(sapi, c_r:=cr_MT_CMD, p:=true,
						     nr:=1, ns:=0, l3:=l3_mt)));

	/* 5) The MS then sends a valid L3 Request I frame asking for IMEI which
	      does not acknowledge receipt of the I frame from the BTS. */
	/* SAPI = 0, C = 1, P = 0, M = 0, 0 ≤ L ≤ N201, N(S) = 1, N(R) = 0.  * */
	LAPDM.send(t_PH_DATA(0, false, ts_LAPDm_I(sapi, c_r:=cr_MO_CMD, p:=false,
						  nr:=0, ns:=1, l3 := l3_mo)));
	RSL.receive(tr_RSL_DATA_IND(g_chan_nr, link_id, l3_mo));
	alt {
	/* On the FACCH the BTS may send an RR frame acknowledging the I frame. */
	/* SAPI = 0, R = 1, F = 0, M = 0, L = 0, N(R) = 2. */
	[] LAPDM.receive(t_PH_DATA(0, false, tr_LAPDm_RR(sapi, c_r:=cr_MT_RSP, p:=false, nr:=2))) {
		repeat;
		}
	/* 6) The BTS shall repeat the I frame, this frame will acknowledge
	      receipt of the second I frame from the MS. */
	/* SAPI = 0, C = 0, P = 1, M = 0, 0 ≤ L ≤ N201, N(R) = 2, N(S) = 0. * */
	[] LAPDM.receive(t_PH_DATA(0, false, tr_LAPDm_I(sapi, c_r:=cr_MT_CMD, p:=true,
						     nr:=2, ns:=0, l3:=l3_mt)));
	}

	/* 7) The MS then acknowledges receipt of the BTS I frame by sending a RR * frame. */
	/* SAPI = 0, R = 0, F = 1, 0, M = 0, L = 0, N(R) = 1 */
	LAPDM.send(t_PH_DATA(0, false, ts_LAPDm_RR(sapi, c_r:=cr_MO_RSP, p:=true, nr:=1)));

	/* 8) The BTS shall send the next I frame. The MS acknowledges this I frame. */
	l3_mt := f_rnd_octstring(16);
	RSL.send(ts_RSL_DATA_REQ(g_chan_nr, link_id, l3_mt));
	/* SAPI = 0, C = 0, P = 0, M = 0, 0 ≤ L ≤ N201, N(R) = 2, N(S) = 1 */
	LAPDM.receive(t_PH_DATA(0, false, tr_LAPDm_I(sapi, c_r:=cr_MT_CMD, p:=false,
						     nr:=2, ns:=1, l3:=l3_mt)));
	LAPDM.send(t_PH_DATA(0, false, ts_LAPDm_RR(sapi, c_r:=cr_MO_RSP, p:=true, nr:=2)));

	deactivate(d);
	fp_common_fini();
}
testcase TC_iframe_timer_recovery() runs on test_CT {
	var ConnHdlrPars pars := valueof(t_Pars(t_RslChanNr_Bm(1), ts_RSL_ChanMode_SIGN));
	f_testmatrix_each_chan(pars, refers(f_TC_iframe_timer_recovery));
}

/* 25.2.6.1  ns sequence error
sends wrong N(S), expects REJ, sends wrong N(S) with P=1, expects REJ with F=1 */
private function f_TC_ns_seq_error(charstring id) runs on ConnHdlr {
	const integer sapi := 0;
	var RslLinkId link_id := valueof(ts_RslLinkID_DCCH(sapi));
	var default d;
	timer T := 3.0;

	fp_common_init();

	/* some common altstep for meas res and other background noise */
	d := activate(as_ignore_background(ignore_rsl_errors := true));
	RSL.clear;
	LAPDM.clear;

	var octetstring l3_mo := f_rnd_octstring(12);
	var octetstring l3_mt := f_rnd_octstring(12);

	/*  1) The BTS is brought into the multiple frame established state */

	/* MO Establish Request via LADPm: SAPI = 0, C = 0, P = 1, M = 0, 0 ≤ L ≤ N201.. */
	LAPDM.send(t_PH_DATA(0, false, ts_LAPDm_SABM(sapi, c_r:=cr_MO_CMD, p:=true, l3:=l3_mo)));
	RSL.receive(tr_RSL_EST_IND(g_chan_nr, link_id, l3_mo));
	/* UA: SAPI = 0, R = 0, F = 1, M = 0, L = L of SABM. */
	LAPDM.receive(t_PH_DATA(0, false, tr_LAPDm_UA(sapi, cr_MT_RSP, f:=true, l3:=l3_mo)));

	/* 2) The MS sends an L3 Request to the BTS */
	l3_mo := f_rnd_octstring(18);
	/* SAPI = 0, C = 1, P = 0, M = 0, 0 ≤ L ≤ N201, N(S) = 0, N(R) = 0.  * */
	LAPDM.send(t_PH_DATA(0, false, ts_LAPDm_I(sapi, c_r:=cr_MO_CMD, p:=false,
						  nr:=0, ns:=0, l3:=l3_mo)));
	RSL.receive(tr_RSL_DATA_IND(g_chan_nr, link_id, l3_mo));
	/* 3) The BTS shall respond with a RR frame though this may be incorporated with
	   the L3 Response I frame. */
	RSL.send(ts_RSL_DATA_REQ(g_chan_nr, link_id, l3_mt));
	alt {
	/* SAPI = 0, R = 1, F = 0, M = 0, L = 0, N(R) = 1. */
	[] LAPDM.receive(t_PH_DATA(0, false, tr_LAPDm_RR(sapi, c_r:=cr_MT_RSP, p:=false, nr:=1))) {
		repeat;
		}
	/* SAPI = 0, C = 0, P = 0, M = 0, 0 ≤ L ≤ N201, N(R) = 1, N(S) = 0 */
	[] LAPDM.receive(t_PH_DATA(0, false, tr_LAPDm_I(sapi, c_r:=cr_MT_CMD, p:=false,
							nr:=1, ns:=0, l3:=l3_mt)));
	}

	/* 4) The MS shall then send an I frame containing Identity Request with incorrect N(S)
	but correctly acknowledging the MS's I frame; P bit set to zero.  */
	LAPDM.send(t_PH_DATA(0, false, ts_LAPDm_I(sapi, c_r:=cr_MO_CMD, p:=false,
						  nr:=1, ns:=0, l3:=l3_mo)));

	/* no rsl data ind  due to wrong ns */

	/* The BTS shall send a REJ frame. */
	timer T1 := 2.0;
	T1.start;
	alt{
	[] LAPDM.receive(t_PH_DATA(0, false, tr_LAPDm_REJ(sapi, c_r:=cr_MT_RSP, p:=false, nr:=1)));
	[] T1.timeout{ setverdict(fail, "Missing first REJ")}
	}

	f_sleep(2.0); // T200

	/* The MS shall, after T200, send another I frame with incorrect N(S), P bit set to 1 this time. */
	LAPDM.send(t_PH_DATA(0, false, ts_LAPDm_I(sapi, c_r:=cr_MO_CMD, p:=true,
						  nr:=1, ns:=0, l3:=l3_mo)));

	/* The BTS shall respond with a REJ, F bit set to 1. */
	T1.start;
	alt{
	[] LAPDM.receive(t_PH_DATA(0, false, tr_LAPDm_REJ(sapi, c_r:=cr_MT_RSP, p:=true, nr:=1)));
	[] T1.timeout{ setverdict(fail, "Missing second REJ")}
	}

	deactivate(d);
	fp_common_fini();
	setverdict(pass);
}

testcase TC_ns_seq_error() runs on test_CT {
	var ConnHdlrPars pars := valueof(t_Pars(t_RslChanNr_Bm(1), ts_RSL_ChanMode_SIGN));
	f_testmatrix_each_chan(pars, refers(f_TC_ns_seq_error));
}

/* 25.2.6.2 nr sequence error */
private function f_TC_nr_seq_error(charstring id) runs on ConnHdlr {
	const integer sapi := 0;
	var RslLinkId link_id := valueof(ts_RslLinkID_DCCH(sapi));
	var default d;
	var integer n201 := 20;
	if (link_id.c == SACCH) {
		n201 := 18;
	}

	fp_common_init();

	/* some common altstep for meas res and other background noise */
	d := activate(as_ignore_background(ignore_rsl_errors := true));
	RSL.clear;
	LAPDM.clear;

	var octetstring l3_mo := f_rnd_octstring(12);
	var octetstring l3_mt := f_rnd_octstring(12);

	/*  1) The BTS is brought into the multiple frame established state */

	/* MO Establish Request via LADPm: SAPI = 0, C = 0, P = 1, M = 0, 0 ≤ L ≤ N201.. */
	LAPDM.send(t_PH_DATA(0, false, ts_LAPDm_SABM(sapi, c_r:=cr_MO_CMD, p:=true, l3:=l3_mo)));
	RSL.receive(tr_RSL_EST_IND(g_chan_nr, link_id, l3_mo));
	/* UA: SAPI = 0, R = 0, F = 1, M = 0, L = L of SABM. */
	LAPDM.receive(t_PH_DATA(0, false, tr_LAPDm_UA(sapi, cr_MT_RSP, f:=true, l3:=l3_mo)));

	/* 2) The MS shall send an I frame containing an information field of length N201 and an
	 incorrect receive sequence number. */
	l3_mo := f_rnd_octstring(n201);
	/* SAPI = 0, C = 1, P = 0, M = 0,  L = N201, N(S) = 0, N(R) = 1.  * */
	LAPDM.send(t_PH_DATA(0, false, ts_LAPDm_I(sapi, c_r:=cr_MO_CMD, p:=false,
						  nr:=1, ns:=0, l3:=l3_mo)));

	/* The BTS may: a)   send a DISC frame within N200×T200; */
	/* DISC SAPI = 0, C = 0, P = 1, M = 0, L = 0. */
	timer T1 := 2.0;
	T1.start;
	alt{
	[] LAPDM.receive(t_PH_DATA(0, false, tr_LAPDm_DISC(sapi, c_r:=cr_MT_CMD, p:=true)));
	[] T1.timeout{ setverdict(fail, "Missing DISC from BTS")}
	}

	/* a) the MS shall respond with a UA frame.
	SAPI = 0, R = 0, F = 1, M = 0, L = 0. */
	LAPDM.send(t_PH_DATA(0, false, ts_LAPDm_UA(sapi, c_r:=cr_MO_CMD, f:=true, l3:=l3_mo)));

	deactivate(d);
	fp_common_fini();
	setverdict(pass);
}

testcase TC_nr_seq_error() runs on test_CT {
	var ConnHdlrPars pars := valueof(t_Pars(t_RslChanNr_Bm(1), ts_RSL_ChanMode_SIGN));
	f_testmatrix_each_chan(pars, refers(f_TC_nr_seq_error));
}

private function f_TC_rec_invalid_frame_txrx(integer sapi, LapdmFrame x, integer line_nr) runs on ConnHdlr {
	LAPDM.send(t_PH_DATA(0, false, x));
	f_sleep(2.0); // T200
	LAPDM.send(t_PH_DATA(0, false, ts_LAPDm_RR(sapi, c_r:=cr_MO_CMD, p:=true, nr:=0)));
	timer T1 := 2.0;
	T1.start;
	alt {
	[] LAPDM.receive(t_PH_DATA(0, false, tr_LAPDm_RR(sapi, c_r:=cr_MT_RSP, p:=true , nr := 0))) { T1.stop; }
	[] T1.timeout{ Misc_Helpers.f_shutdown(__BFILE__, line_nr, fail, "Missing LAPDm_RR RSP"); }
	}
}

/* 25.2.7     Test on receipt of invalid frames
sends a bunch of different invalid frames, expects the BTS to ignore all of them */
private function f_TC_rec_invalid_frame(charstring id) runs on ConnHdlr {
	const integer sapi := 0;
	var RslLinkId link_id := valueof(ts_RslLinkID_DCCH(sapi));
	var default d;
	timer T := 3.0;

	fp_common_init();

	/* some common altstep for meas res and other background noise */
	d := activate(as_ignore_background(ignore_rsl_errors := true));
	RSL.clear;
	LAPDM.clear;

	var octetstring l3_mo := f_rnd_octstring(12);
	var octetstring l3_mt := f_rnd_octstring(12);

	/*  1) The BTS is brought into the multiple frame established state */

	/* MO Establish Request via LADPm: SAPI = 0, C = 0, P = 1, M = 0, 0 ≤ L ≤ N201.. */
	LAPDM.send(t_PH_DATA(0, false, ts_LAPDm_SABM(sapi, c_r:=cr_MO_CMD, p:=true, l3:=l3_mo)));
	T.start
	alt {
	[] RSL.receive(tr_RSL_EST_IND(g_chan_nr, link_id, l3_mo)) {}
	[] T.timeout{ Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, "Missing RSL EST IND"); }
	}
	alt {
	/* UA: SAPI = 0, R = 0, F = 1, M = 0, L = L of SABM. */
	[] LAPDM.receive(t_PH_DATA(0, false, tr_LAPDm_UA(sapi, cr_MT_RSP, f:=true, l3:=l3_mo))) { T.stop; }
	[] T.timeout{ Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, "Missing LAPDm UA RSP"); }
	}

	/* 1: One RR frame: SAPI = 0, R = 0, F = 0, M = 0, L > 0, N(R) = 1.
	RR frame with the Length indicator greater than zero and a faulty N(R); */
	var LapdmFrame x:= valueof(ts_LAPDm_RR(sapi, c_r:=cr_MO_CMD, p:=false, nr:=1));
	x.ab.payload := f_rnd_octstring(5);
	f_TC_rec_invalid_frame_txrx(0, x, __LINE__);
	/* 3: One REJ frame: SAPI = 0, R = 0, F = 0, M = 0, L = 0, N(R) = 1, EA = 0.
	EJ frame with the EA bit set to zero and a faulty N(R); */
	x:= valueof(ts_LAPDm_REJ(sapi, c_r:=cr_MO_CMD, p:=false, nr:=1));
	x.ab.addr.ea := false;
	f_TC_rec_invalid_frame_txrx(0, x, __LINE__);
	/* 4: One SABM frame: SAPI = 0, C = 1, P = 1, M = 0, L = 0, EL = 0.
	SABM frame with the EL bit set to zero; */
	l3_mo := ''O;
	x:= valueof(ts_LAPDm_SABM(sapi, c_r:=cr_MO_CMD, p:=true, l3:=l3_mo));
	x.ab.el := 0;
	f_TC_rec_invalid_frame_txrx(0, x, __LINE__);
	/* 5: One DM frame: SAPI = 0, R = 0, F = 1, M = 0, L > 0.
	DM frame with the Length indicator greater than zero;*/
	x:= valueof(ts_LAPDm_DM(sapi, c_r:=cr_MO_CMD, f:=true));
	x.ab.payload := f_rnd_octstring(5);
	f_TC_rec_invalid_frame_txrx(0, x, __LINE__);
	/* 6: One DISC frame: SAPI = 0, C = 1, P = 1, M = 1, L = 0.
	DISC frame with the M bit set to 1; */
	x:= valueof(ts_LAPDm_DISC(sapi, c_r:=cr_MO_CMD, p:=true));
	x.ab.m := true;
	f_TC_rec_invalid_frame_txrx(0, x, __LINE__);
	/* 7: One UA frame: SAPI = 0, R = 0, F = 0, M = 0, L = 0, EA = 0.
	UA frame with the EA bit set to zero*/
	x:= valueof(ts_LAPDm_UA(sapi, c_r:=cr_MO_CMD, f:=false, l3:=''O));
	x.ab.addr.ea := false;
	f_TC_rec_invalid_frame_txrx(0, x, __LINE__);
	/* 8: One I frame: SAPI = 0, C = 1, P = 0, M = 0, L > N201, N(R) = 0, N(S) = 6.
	I frame with the Length indicator greater than N201;*/
	x:= valueof(ts_LAPDm_I(sapi, c_r:=cr_MO_CMD, p:=true, nr := 0, ns := 6, l3 := f_rnd_octstring(25)))
	f_TC_rec_invalid_frame_txrx(0, x, __LINE__);
	/* 9: One I frame: SAPI = 0, C = 1, P = 0, M = 1, L < N201, N(R) = 0, N(S) = 7.
	I frame with the M bit set to 1 and the Length indicator less than N201;*/
	x:= valueof(ts_LAPDm_I(sapi, c_r:=cr_MO_CMD, p:=true, nr := 0, ns := 7, l3 := f_rnd_octstring(5)))
	x.ab.m := true;
	f_TC_rec_invalid_frame_txrx(0, x, __LINE__);
	/* 10: One RR frame: SAPI = 0, C = 1, P = 1, M = 0, L = 0, N(R) = 0. */
	x:= valueof(ts_LAPDm_RR(sapi, c_r:=cr_MO_CMD, p:=true, nr:=0));
	f_TC_rec_invalid_frame_txrx(0, x, __LINE__);

	/* command frames with correct Address and Length indicator field and a non-implemented control field */
	/* 12: One command frame with Control Field = xxx1 1101. */
	x:= valueof(ts_LAPDm_RR(sapi, c_r:=cr_MO_CMD, p:=false, nr:=1));
	x.ab.ctrl.other := bit2int('00011101'B);
	f_TC_rec_invalid_frame_txrx(0, x, __LINE__);
	/* 13: One command frame with Control field = xxx1 1011. */
	x:= valueof(ts_LAPDm_RR(sapi, c_r:=cr_MO_CMD, p:=false, nr:=1));
	x.ab.ctrl.other := bit2int('00011011'B);
	f_TC_rec_invalid_frame_txrx(0, x, __LINE__);
	/* 14: One command frame with Control field = xxx1 0111. */
	x:= valueof(ts_LAPDm_RR(sapi, c_r:=cr_MO_CMD, p:=false, nr:=1));
	x.ab.ctrl.other := bit2int('00010001'B);
	f_TC_rec_invalid_frame_txrx(0, x, __LINE__);
	/* 15: One command frame with Control field = 01x1 1111. */
	x:= valueof(ts_LAPDm_RR(sapi, c_r:=cr_MO_CMD, p:=false, nr:=1));
	x.ab.ctrl.other := bit2int('01011111'B);
	f_TC_rec_invalid_frame_txrx(0, x, __LINE__);
	/* 16: One command frame with Control field = 1xx1 1111. */
	x:= valueof(ts_LAPDm_RR(sapi, c_r:=cr_MO_CMD, p:=false, nr:=1));
	x.ab.ctrl.other := bit2int('10011111'B);
	f_TC_rec_invalid_frame_txrx(0, x, __LINE__);
	/* 17: One command frame with Control field = 0011 0011. */
	x:= valueof(ts_LAPDm_RR(sapi, c_r:=cr_MO_CMD, p:=false, nr:=1));
	x.ab.ctrl.other := bit2int('00110011'B);
	f_TC_rec_invalid_frame_txrx(0, x, __LINE__);
	/* 18: One command frame with Control field = 1xx1 0011. */
	x:= valueof(ts_LAPDm_RR(sapi, c_r:=cr_MO_CMD, p:=false, nr:=1));
	x.ab.ctrl.other := bit2int('10010011'B);
	f_TC_rec_invalid_frame_txrx(0, x, __LINE__);

	deactivate(d);
	fp_common_fini();
	setverdict(pass);
}

testcase TC_rec_invalid_frame() runs on test_CT {
	var ConnHdlrPars pars := valueof(t_Pars(t_RslChanNr_Bm(1), ts_RSL_ChanMode_SIGN));
	pars.t_guard := 60.0;
	f_testmatrix_each_chan(pars, refers(f_TC_rec_invalid_frame));
}

type record LapdmDlConfig {
	integer n201,
	integer t200
};

type record LapdmDlState {
	integer v_s,
	integer v_a,
	integer v_r
};

template (value) LapdmDlState t_init_LapdmDlState := {
	v_s := 0,
	v_a := 0,
	v_r := 0
}

private function inc_mod8(inout integer v)
{
	v := (v + 1) mod 8;
}

private function f_lapdm_transceive_mo(inout LapdmDlState dls, RslLinkId link_id, octetstring l3)
runs on ConnHdlr {
	var LAPDm_ph_data pd;
	var integer offset := 0;
	var integer n201 := 20;
	var boolean is_sacch := false;
	if (link_id.c == SACCH) {
		n201 := 18;
		is_sacch := true;
	}

	while (offset < lengthof(l3)) {
		var integer remain_len := lengthof(l3) - offset;
		var integer seg_len := remain_len;
		if (remain_len > n201) {
			seg_len := n201;
		}
		var octetstring segment := substr(l3, offset, seg_len);
		var boolean more;
		if (offset + lengthof(segment) < lengthof(l3)) {
			more := true;
		} else {
			more := false;
		}
		/* send the next segment */
		LAPDM.send(t_PH_DATA(0, is_sacch,
				     ts_LAPDm_I(link_id.sapi, c_r:=cr_MO_CMD, p:=false,
						nr:=dls.v_a, ns:=dls.v_s, l3:=segment, m:=more)));
		inc_mod8(dls.v_s);
		offset := offset + lengthof(segment);

		/* wait for it to be acknowledged */
		alt {
		[] LAPDM.receive(t_PH_DATA(0, is_sacch, tr_LAPDm_RR(link_id.sapi, c_r:=cr_MT_RSP,
								    p:=false, nr:=(dls.v_s) mod 8)));
		[] as_ignore_background(not is_sacch);
		[] LAPDM.receive(t_PH_DATA(0, is_sacch, ?)) -> value pd {
			Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, log2str("received unexpected LAPDm ", pd));
			}
		[] LAPDM.receive(t_PH_DATA(0, ?, ?)) { repeat; }
		[offset < lengthof(l3)] RSL.receive(tr_RSL_DATA_IND(g_chan_nr, link_id, ?)) {
			Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, "received RSL DATA IND before message complete");
			}
		}
	}

	timer T := 1.0;
	T.start;
	alt {
	[] RSL.receive(tr_RSL_DATA_IND(g_chan_nr, link_id, l3)) {
		setverdict(pass);
		}
	[] RSL.receive(tr_RSL_DATA_IND(g_chan_nr, link_id, ?)) {
		Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, "Received RSL DATA IND with wrong payload");
		}
	[] T.timeout {
		Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, "Timeout waiting for RSL DATA IND of de-segmented message");
		}
	}
}

/* Section 5.8.5 of TS 04.06 */
const integer c_TS0406_MAX_L3_OCTETS := 251;

/* test segmentation and de-segmentation (concatenation) of a large message in uplink
 * on specified SAPI/channel */
private function f_TC_segm_concat(charstring id, RslLinkId link_id) runs on ConnHdlr {
	var integer sapi := link_id.sapi;
	var boolean is_sacch := false;
	if (link_id.c == SACCH) {
		is_sacch := true;
	}
	var default d;
	timer T := 3.0;

	fp_common_init();

	/* some common altstep for meas res and other background noise */
	d := activate(as_ignore_background(not is_sacch));
	RSL.clear;
	LAPDM.clear;

	f_establish_mo(link_id);

	var octetstring l3_mo := f_rnd_octstring(c_TS0406_MAX_L3_OCTETS);

	deactivate(d);

	var LapdmDlState dls := valueof(t_init_LapdmDlState);
	f_lapdm_transceive_mo(dls, link_id, l3_mo);

	fp_common_fini();
}
private function f_TC_segm_concat_dcch(charstring id) runs on ConnHdlr {
	f_TC_segm_concat(id, valueof(ts_RslLinkID_DCCH(0)));
}
private function f_TC_segm_concat_sacch(charstring id) runs on ConnHdlr {
	f_TC_segm_concat(id, link_id :=valueof(ts_RslLinkID_SACCH(0)));
}
/* test mobile-originated segmentation/de-segmentation on DCCH */
testcase TC_segm_concat_dcch() runs on test_CT {
	var ConnHdlrPars pars := valueof(t_Pars(t_RslChanNr_Bm(1), ts_RSL_ChanMode_SIGN));
	f_testmatrix_each_chan(pars, refers(f_TC_segm_concat_dcch));
}
/* test mobile-originated segmentation/de-segmentation on SACCH */
testcase TC_segm_concat_sacch() runs on test_CT {
	var ConnHdlrPars pars := valueof(t_Pars(t_RslChanNr_Bm(1), ts_RSL_ChanMode_SIGN));
	f_testmatrix_each_chan(pars, refers(f_TC_segm_concat_sacch));
}

/* TS 04.06 Section 5.8.2.1 */
private function f_n200_by_chan_nr(RslChannelNr chan_nr, RslLinkId link_id) return integer {
	/* SACCH irrespective of physical channel type */
	if (match(link_id, tr_RslLinkID_SACCH(?))) {
		return 5;
	}
	/* DCCH below */
	select (chan_nr) {
	case (t_RslChanNr_SDCCH4(?, ?)) { return 23; }
	case (t_RslChanNr_SDCCH8(?, ?)) { return 23; }
	case (t_RslChanNr_Bm(?)) { return 34; }
	case (t_RslChanNr_Lm(?, ?)) { return 29; }
	}
	setverdict(fail, "Unknown chan_nr ", chan_nr, " or link_id ", link_id);
	return -1;
}

/* Test if there are exactly N200+1 transmissions of I frames; inspired by 25.2.4.1 */
private function f_TC_t200_n200(charstring id) runs on ConnHdlr {
	var RslLinkId link_id := valueof(ts_RslLinkID_DCCH(0));
	var integer sapi := link_id.sapi;
	var boolean is_sacch := false;
	if (link_id.c == SACCH) {
		is_sacch := true;
	}
	var integer n200 := f_n200_by_chan_nr(g_chan_nr, link_id);
	var integer num_retrans := 0;
	timer T := 3.0;
	var default d;

	fp_common_init();

	/* some common altstep for meas res and other background noise */
	d := activate(as_ignore_background(true));
	RSL.clear;
	LAPDM.clear;

	f_establish_mo(link_id);

	var octetstring l3_mt := f_rnd_octstring(20);
	RSL.send(ts_RSL_DATA_REQ(g_chan_nr, link_id, l3_mt));
	/* first transmission, P = 0 */
	LAPDM.receive(t_PH_DATA(0, is_sacch, tr_LAPDm_I(sapi, c_r:=cr_MT_CMD, p:=false,
							nr:=0, ns:=0, l3:=l3_mt)));
	deactivate(d);

	alt {
	/* re-transmission, P = 1 */
	[] LAPDM.receive(t_PH_DATA(0, is_sacch,
				tr_LAPDm_I(sapi, c_r:=cr_MT_CMD, p:=true, nr:=0, ns:=0, l3:=l3_mt))) {
		num_retrans := num_retrans + 1;
		if (num_retrans < n200) {
			repeat;
		} else if (num_retrans == n200) {
			T.start; /* wait for some more time if there are more retransmissions */
			repeat;
		} else {
			/* break */
		}
		}
	[] LAPDM.receive(t_PH_DATA(0, false, tr_LAPDm_I(sapi, ?, ?, ?, ?, ?))) {
		setverdict(fail, "Received unexpected I frame");
		}
	[not is_sacch] as_lapdm_acch();
	[is_sacch] as_lapdm_dcch();
	[] as_lapdm_idle();
	[] as_rsl_meas_rep();
	[num_retrans == n200] RSL.receive(tr_RSL_ERROR_IND(g_chan_nr, link_id, '01'O)) {
		/* break */
		}
	[] T.timeout {
		setverdict(fail, "Missing RSL RLL ERROR INDICATION");
		}
	}

	if (num_retrans == n200) {
		setverdict(pass, "Received ", num_retrans, " on channel ", g_chan_nr, " link ", link_id);
	} else if (num_retrans < n200) {
		setverdict(fail, "Too few retransmissions (", num_retrans, "); N200=", n200,
			   " on channel ", g_chan_nr, " link ", link_id);
	}

	fp_common_fini();
}
testcase TC_t200_n200() runs on test_CT {
	var ConnHdlrPars pars := valueof(t_Pars(t_RslChanNr_Bm(1), ts_RSL_ChanMode_SIGN));
	f_testmatrix_each_chan(pars, refers(f_TC_t200_n200));
}

/* Ensure BTS repeats RR frame after retransmitting I frame to emulate RR loss;
   Inspired by TS 51.010-1 25.2.4.3 */
private function f_TC_rr_response_frame_loss(charstring id) runs on ConnHdlr {
	var RslLinkId link_id := valueof(ts_RslLinkID_DCCH(0));
	var integer sapi := link_id.sapi;
	var boolean is_sacch := false;
	if (link_id.c == SACCH) {
		is_sacch := true;
	}
	timer T := 3.0;
	var default d;

	fp_common_init();

	/* some common altstep for meas res and other background noise */
	d := activate(as_ignore_background(true));
	RSL.clear;
	LAPDM.clear;

	f_establish_mo(link_id);

	var octetstring l3_mo := f_rnd_octstring(10);
	/* Send an I frame to the BTS: SAPI = 0, C = 1, P = 0, M = 0, L = 3, N(S) = 0, N(R) = 0 */
	LAPDM.send(t_PH_DATA(0, is_sacch, ts_LAPDm_I(sapi, c_r:=cr_MO_CMD, p:=false, nr:=0, ns:=0,
						     l3:=l3_mo)));
	RSL.receive(tr_RSL_DATA_IND(g_chan_nr, link_id, l3_mo));
	/* SAPI = 0, R = 1, F = 0, M = 0, L = 0, N(R) = 1. */
	LAPDM.receive(t_PH_DATA(0, is_sacch, tr_LAPDm_RR(sapi, c_r:=cr_MT_RSP, p:=false, nr:=1)));

	/* Re-send I frame: SAPI = 0, C = 1, P = 1, M = 0, L = 3, N(S) = 0, N(R) = 0. */
	LAPDM.send(t_PH_DATA(0, is_sacch, ts_LAPDm_I(sapi, c_r:=cr_MO_CMD, p:=true, nr:=0, ns:=0,
						     l3:=l3_mo)));

	T.start;
	alt {
	/* RR: SAPI = 0, R = 1, F = 1, M = 0, L = 0, N(R) = 1. */
	[] LAPDM.receive(t_PH_DATA(0, is_sacch, tr_LAPDm_RR(sapi, c_r:=cr_MT_RSP, p:=true, nr:=1))) {
		setverdict(pass);
		}
	/* REJ: SAPI = 0, R = 1, F = 1, M = 0, L = 0, N(R) = 1. */
	[] LAPDM.receive(t_PH_DATA(0, is_sacch, tr_LAPDm_REJ(sapi, c_r:=cr_MT_RSP, p:=true, nr:=1))) {
		setverdict(pass);
		}
	[] T.timeout {
		setverdict(fail, "Timeout waiting for RR or REJ");
		}
	}

	deactivate(d);

	fp_common_fini();
}
testcase TC_rr_response_frame_loss() runs on test_CT {
	var ConnHdlrPars pars := valueof(t_Pars(t_RslChanNr_Bm(1), ts_RSL_ChanMode_SIGN));
	f_testmatrix_each_chan(pars, refers(f_TC_rr_response_frame_loss));
}

/* Ensure BTS ignores I frames with wrong C/R bit; Inspired by TS 51.010-1 25.2.5.1 */
private function f_TC_incorrect_cr(charstring id) runs on ConnHdlr {
	var RslLinkId link_id := valueof(ts_RslLinkID_DCCH(0));
	var integer sapi := link_id.sapi;
	var boolean is_sacch := false;
	if (link_id.c == SACCH) {
		is_sacch := true;
	}
	timer T := 3.0;
	var default d;

	fp_common_init();

	/* some common altstep for meas res and other background noise */
	d := activate(as_ignore_background(true));
	RSL.clear;
	LAPDM.clear;

	f_establish_mo(link_id);

	var octetstring l3_mo := f_rnd_octstring(10);
	/* Send an I frame to the BTS: SAPI = 0, C = 0, P = 1, M = 0, L = 3, N(S) = 0, N(R) = 0 */
	LAPDM.send(t_PH_DATA(0, is_sacch, ts_LAPDm_I(sapi, c_r:=cr_MO_RSP, p:=true, nr:=0, ns:=0,
						     l3:=l3_mo)));
	T.start;
	alt {
	[] RSL.receive(tr_RSL_DATA_IND(g_chan_nr, link_id, l3_mo)) {
		setverdict(fail, "BTS didn't ignore I frame with wrong C/R bit");
		}
	[] RSL.receive(tr_RSL_ERROR_IND(g_chan_nr, link_id, '0C'O)) {
		repeat;
		}
	/* ensure BTS still sends idle frames */
	[] as_lapdm_idle() {
		setverdict(pass, "still sending idle frames");
		}
	[] T.timeout {}
	}

	/* Send RR command P=1 */
	LAPDM.send(t_PH_DATA(0, is_sacch, ts_LAPDm_RR(sapi, c_r:=cr_MO_CMD, p:=true, nr:=0)));

	/* The BTS shall respond with a RR response, F bit set to 1. */
	LAPDM.receive(t_PH_DATA(0, is_sacch, tr_LAPDm_RR(sapi, c_r:=cr_MT_RSP, p:=true, nr:=0)));

	deactivate(d);

	fp_common_fini();
}
testcase TC_incorrect_cr() runs on test_CT {
	var ConnHdlrPars pars := valueof(t_Pars(t_RslChanNr_Bm(1), ts_RSL_ChanMode_SIGN));
	f_testmatrix_each_chan(pars, refers(f_TC_incorrect_cr));
}

/* test that the BTS will take no action when it receives an SABM frame with the C bit set wrong (R)
   Inspired by TS 51.010-1 25.2.5.2 */
private function f_TC_sabm_incorrect_c(charstring id) runs on ConnHdlr {
	var RslLinkId link_id := valueof(ts_RslLinkID_DCCH(0));
	var integer sapi := link_id.sapi;
	var boolean is_sacch := false;
	if (link_id.c == SACCH) {
		is_sacch := true;
	}
	timer T := 3.0;
	var default d;

	fp_common_init();

	/* some common altstep for meas res and other background noise */
	d := activate(as_ignore_background(true));
	RSL.clear;
	LAPDM.clear;

	f_establish_mo(link_id);

	/* Send I-frame SAPI = 0, C = 1, P = 0, M = 0, L = 3, N(S) = 0, N(R) = 0 */
	var octetstring l3_mo := '010203'O;
	LAPDM.send(t_PH_DATA(0, is_sacch, ts_LAPDm_I(sapi, c_r:=cr_MO_CMD, p:=false, nr:=0, ns:=0,
						     l3:=l3_mo)));
	/* Expect RR SAPI = 0, R = 1, F = 0, M = 0, L = 0, N(R) = 1 */
	LAPDM.receive(t_PH_DATA(0, is_sacch, tr_LAPDm_RR(sapi, c_r:=cr_MT_RSP, p:=false, nr:=1)));
	RSL.receive(tr_RSL_DATA_IND(g_chan_nr, link_id, l3_mo));
	/* Send SABM SAPI = 0, C = 0, P = 1, M = 0, L = 0 */
	LAPDM.send(t_PH_DATA(0, is_sacch, ts_LAPDm_SABM(sapi, c_r:=cr_MO_RSP, p:=true, l3:=''O)));
	/* Expect RSL ERR IND */
	RSL.receive(tr_RSL_ERROR_IND(g_chan_nr, link_id, '0C'O));
	/* Expect fill frame C = 0, P = 0, M = 0, L = 0 */
	LAPDM.receive(t_PH_DATA(0, is_sacch, tr_LAPDm_UI(0, ?, ''O)));
	/* Send RR command (P=1) SAPI = 0, C = 1, P = 1, M = 0, L = 0, N(R) = 0 */
	LAPDM.send(t_PH_DATA(0, is_sacch, ts_LAPDm_RR(sapi, c_r:=cr_MO_CMD, p:=true, nr:=0)));
	/* Expect RR response (F=1) SAPI = 0, R = 1, F = 1, M = 0, L = 0, N(R) = 1 */
	LAPDM.receive(t_PH_DATA(0, is_sacch, tr_LAPDm_RR(sapi, c_r:=cr_MT_RSP, p:=true, nr:=1)));

	deactivate(d);

	fp_common_fini();
}
testcase TC_sabm_incorrect_c() runs on test_CT {
	var ConnHdlrPars pars := valueof(t_Pars(t_RslChanNr_Bm(1), ts_RSL_ChanMode_SIGN));
	f_testmatrix_each_chan(pars, refers(f_TC_sabm_incorrect_c));
}

/* Test procedure for normal reestablishment, as per:
 * OS#4819
 * 3GPP TS 44.006 8.4.1.2 "Normal establishment procedure"
 * 3GPP TS 44.006 8.4.2.1 "General requirements"
 * 3GPP TS 44.006 8.6.3 "Procedures for re-establishment"
 * */
private function f_TC_normal_reestablishment(charstring id) runs on ConnHdlr {
	var RslLinkId link_id := valueof(ts_RslLinkID_DCCH(0))
	var octetstring l3_mo := f_rnd_octstring(c_TS0406_MAX_L3_OCTETS);
	var default d;
	timer T := 3.0;
	var boolean use_sacch := false;
	var boolean received_estind := false;
	var boolean received_ua := false;

	fp_common_init();

	/* some common altstep for meas res and other background noise */
	d := activate(as_ignore_background(true));
	RSL.clear;
	LAPDM.clear;

	f_establish_mo(link_id);

	deactivate(d);

	var LapdmDlState dls := valueof(t_init_LapdmDlState);
	f_lapdm_transceive_mo(dls, link_id, l3_mo);

	LAPDM.send(t_PH_DATA(link_id.sapi, use_sacch, ts_LAPDm_SABM(link_id.sapi, c_r:=cr_MO_CMD, p:=true, l3:=''O)));
	T.start
	alt {
	[] LAPDM.receive(t_PH_DATA(?, use_sacch, tr_LAPDm_UA(link_id.sapi, cr_MT_RSP, f:=true, l3:=''O))) {
		received_ua := true;
		if (not received_estind) {
			repeat;
		}
		}
	[] RSL.receive(tr_RSL_EST_IND_NOL3(g_chan_nr, link_id)) {
		received_estind := true;
		if (not received_ua) {
			repeat;
		}
	}
	[] RSL.receive { repeat; }
	[] LAPDM.receive { repeat; }
	[] T.timeout { setverdict(fail, "Timeout waiting for UA"); }
	}

	/* Test we can still send data afterwards */
	l3_mo := f_rnd_octstring(c_TS0406_MAX_L3_OCTETS);
	dls := valueof(t_init_LapdmDlState);
	f_lapdm_transceive_mo(dls, link_id, l3_mo);


	fp_common_fini();
}
testcase TC_normal_reestablishment() runs on test_CT {
	var ConnHdlrPars pars := valueof(t_Pars(t_RslChanNr_Bm(1), ts_RSL_ChanMode_SIGN));
	f_testmatrix_each_chan(pars, refers(f_TC_normal_reestablishment));
}

/* Test procedure for normal reestablishment in state LAPD_STATE_TIMER_RECOV (after T200, waiting for Ack), as per:
 * OS#4819
 * 3GPP TS 44.006 8.4.1.2 "Normal establishment procedure"
 * 3GPP TS 44.006 8.4.2.1 "General requirements"
 * 3GPP TS 44.006 8.6.3 "Procedures for re-establishment"
 * */
private function f_TC_normal_reestablishment_state_unacked(charstring id) runs on ConnHdlr {
	var RslLinkId link_id := valueof(ts_RslLinkID_DCCH(0))
	var octetstring l3_mo := f_rnd_octstring(c_TS0406_MAX_L3_OCTETS);
	var octetstring l3_mt := f_rnd_octstring(20);
	var LapdmDlState dls;
	var default d;
	timer T := 3.0;
	var boolean use_sacch := false;
	var boolean received_estind := false;
	var boolean received_ua := false;

	fp_common_init();

	/* some common altstep for meas res and other background noise */
	d := activate(as_ignore_background(true));
	RSL.clear;
	LAPDM.clear;

	f_establish_mo(link_id);
	RSL.send(ts_RSL_DATA_REQ(g_chan_nr, link_id, l3_mt));
	/* first transmission, P = 0 */
	LAPDM.receive(t_PH_DATA(0, use_sacch, tr_LAPDm_I(link_id.sapi, c_r:=cr_MT_CMD, p:=false,
							 nr:=0, ns:=0, l3:=l3_mt)));
	/* re-transmission, P = 1 */
	LAPDM.receive(t_PH_DATA(0, use_sacch, tr_LAPDm_I(link_id.sapi, c_r:=cr_MT_CMD, p:=true,
							 nr:=0, ns:=0, l3:=l3_mt)));
	deactivate(d);

	/* We received one retrans, so peer is in LAPD_STATE_TIMER_RECOV state. Now send SABM: */
	LAPDM.send(t_PH_DATA(link_id.sapi, use_sacch, ts_LAPDm_SABM(link_id.sapi, c_r:=cr_MO_CMD, p:=true, l3:=''O)));
	T.start
	alt {
	[] LAPDM.receive(t_PH_DATA(?, use_sacch, tr_LAPDm_UA(link_id.sapi, cr_MT_RSP, f:=true, l3:=''O))) {
		received_ua := true;
		if (not received_estind) {
			repeat;
		}
		}
	[] RSL.receive(tr_RSL_EST_IND_NOL3(g_chan_nr, link_id)) {
		received_estind := true;
		if (not received_ua) {
			repeat;
		}
	}
	[] RSL.receive { repeat; }
	[] LAPDM.receive { repeat; }
	[] T.timeout { setverdict(fail, "Timeout waiting for UA"); }
	}

	/* Test we can still send data afterwards */
	l3_mo := f_rnd_octstring(c_TS0406_MAX_L3_OCTETS);
	dls := valueof(t_init_LapdmDlState);
	f_lapdm_transceive_mo(dls, link_id, l3_mo);

	fp_common_fini();
}
testcase TC_normal_reestablishment_state_unacked() runs on test_CT {
	var ConnHdlrPars pars := valueof(t_Pars(t_RslChanNr_Bm(1), ts_RSL_ChanMode_SIGN));
	f_testmatrix_each_chan(pars, refers(f_TC_normal_reestablishment_state_unacked));
}

control {
	execute(TC_sabm_ua_dcch_sapi0());
	execute(TC_sabm_ua_dcch_sapi0_nopayload());
	execute(TC_sabm_ua_dcch_sapi3());
	execute(TC_sabm_ua_dcch_sapi4());
	execute(TC_sabm_contention());
	execute(TC_sabm_retransmit());
	execute(TC_sabm_retransmit_bts());
	execute(TC_sabm_invalid_resp());
	execute(TC_sabm_dm());
	execute(TC_establish_ign_first_sabm());
	execute(TC_iframe_seq_and_ack());
	execute(TC_iframe_timer_recovery());
	execute(TC_ns_seq_error());
	execute(TC_nr_seq_error());
	execute(TC_rec_invalid_frame());
	execute(TC_segm_concat_dcch());
	execute(TC_segm_concat_sacch());
	execute(TC_t200_n200());
	execute(TC_rr_response_frame_loss());
	execute(TC_incorrect_cr());
	execute(TC_sabm_incorrect_c());
	execute(TC_normal_reestablishment());
	execute(TC_normal_reestablishment_state_unacked());
}

}
