module BTS_Tests {

/* Integration Tests for OsmoBTS
 * (C) 2018-2019 by Harald Welte <laforge@gnumonks.org>
 * contributions by Vadim Yanitskiy and sysmocom - s.f.m.c. GmbH
 * 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 OsmoBTS by attaching to the external interfaces
 * such as Abis RSL, PCU, VTY as well as by attaching to a MS L1 implementation
 * using the L1CTL protocol/interface.
 *
 * You can run the tests with
 *  a) osmo-bts-trx + trxcon + fake_trx (without any hardware)
 *  b) any osmo-bts-* + OsmocomBB layer1 + osmocon (with real BTS hardware)
 *  c) osmo-bts-virtual + virt_phy (without any hardware)
 *
 * Some of the tests will only run on a subset of those three configurations
 * due to limitations in the respective L1.
 */

import from Misc_Helpers all;
import from General_Types all;
import from GSM_Types all;
import from GSM_RR_Types all;
import from Osmocom_Types all;
import from GSM_Types all;
import from GSM_SystemInformation all;
import from L1CTL_PortType all;
import from L1CTL_Types all;
import from LAPDm_Types all;
import from LAPDm_RAW_PT all;
import from Osmocom_CTRL_Adapter all;
import from Osmocom_CTRL_Functions all;

import from RSL_Types all;
import from IPA_Types all;
import from IPA_Emulation all;
import from IPA_Testing all;
import from RSL_Emulation all;

import from IPL4asp_Types all;
import from TRXC_Types all;
import from TRXC_CodecPort all;
import from TRXC_CodecPort_CtrlFunct all;

import from PCUIF_Types all;
import from PCUIF_CodecPort all;
import from UD_Types all;

import from MobileL3_CommonIE_Types all;
import from MobileL3_RRM_Types all;
import from MobileL3_Types all;
import from L3_Templates all;
import from L3_Common all;
import from MobileL3_GMM_SM_Types all;

import from Osmocom_VTY_Functions all;
import from TELNETasp_PortType all;
import from BTS_Tests_LAPDm all;

friend module BTS_Tests_SMSCB;
friend module BTS_Tests_virtphy;
friend module BTS_Tests_LAPDm;
friend module BTS_Tests_perf;

/* The tests assume a BTS with the following timeslot configuration:
 * TS0 : Combined CCCH + SDCCH/4
 * TS1 : TCH/F
 * TS2 : TCH/F
 * TS3 : TCH/F_PDCH (IPA Style)
 * TS4 : TCH/F_TCH/H_PDCH (Osmocom Style)
 * TS5 : TCH/H
 * TS6 : SDCCH/8
 * TS7 : PDCH
 */

modulepar {
	charstring mp_rsl_ip := "127.0.0.2";
	integer mp_rsl_port := 3003;
	integer mp_trx0_arfcn := 871;
	charstring mp_bts_trxc_ip := "127.0.0.1";
	integer mp_bts_trxc_port := 5701;
	charstring mp_pcu_socket := PCU_SOCK_DEFAULT;
	charstring mp_ctrl_ip := "127.0.0.1";
	integer mp_ctrl_port := 4238;
	charstring mp_bsc_ctrl_ip := "127.0.0.1";
	integer mp_bsc_ctrl_port := 4249;
	integer mp_tolerance_rxqual := 1;
	integer mp_tolerance_rxlev := 3;
	integer mp_tolerance_timing_offset_256syms := 0;
	integer mp_rxlev_exp := 57;
	integer mp_ul_rxlev_exp := 10;
	integer mp_ms_power_level_exp := 7;
	integer mp_ms_actual_ta_exp := 0;
	integer mp_timing_offset_256syms_exp := 512;
	/* Time to wait for RSL conn from BTS during startup of test */
	float mp_ipa_up_timeout := 15.0;
	float mp_ipa_up_delay := 0.0;
	/* false for now, as only virtphy supports it, not calypso-l1 nor trxcon */
	boolean mp_l1_supports_gprs := false;
}

type record of RslChannelNr ChannelNrs;

type component test_CT extends CTRL_Adapter_CT {
	/* IPA Emulation component underneath RSL */
	var IPA_Emulation_CT vc_IPA;
	/* RSL Emulation component (for ConnHdlr tests) */
	var RSL_Emulation_CT vc_RSL;
	/* Direct RSL_CCHAN_PT */
	port RSL_CCHAN_PT RSL_CCHAN;

	/* L1CTL port (for classic tests) */
	port L1CTL_PT L1CTL;

	/* Optional TRXC connection to FakeTRX (BTS side) */
	port TRXC_CODEC_PT BTS_TRXC;
	var integer g_bts_trxc_conn_id;

	/* VTY connections to both BTS and BSC */
	port TELNETasp_PT BTSVTY;
	port TELNETasp_PT BSCVTY;

	/* PCU Interface of BTS */
	port PCUIF_CODEC_PT PCU;
	var integer g_pcu_conn_id;
	/* Last PCU INFO IND we received */
	var PCUIF_Message g_pcu_last_info;

	/* SI configuration */
	var SystemInformationConfig si_cfg := {
		bcch_extended := false,
		si1_present := false,
		si2bis_present := false,
		si2ter_present := false,
		si2quater_present := false,
		si7_present := false,
		si8_present := false,
		si9_present := false,
		si13_present := false,
		si13alt_present := false,
		si15_present := false,
		si16_present := false,
		si17_present := false,
		si2n_present := false,
		si21_present := false,
		si22_present := false
	};

	/* all logical channels available on the BTS */
	var ChannelNrs g_AllChannels;
	var ChannelNrs g_AllChanTypes;
}

/* an individual call / channel */
type component ConnHdlr extends RSL_DchanHdlr, lapdm_test_CT {
	port L1CTL_PT L1CTL;

	/* Optional TRXC connection to FakeTRX (BTS side) */
	port TRXC_CODEC_PT BTS_TRXC;
	var integer g_bts_trxc_conn_id;

	timer g_Tguard;
	timer g_Tmeas_exp := 2.0; /* >= 103 SACCH multiframe ~ 500ms */

	var ConnHdlrPars g_pars;
	var uint8_t g_next_meas_res_nr := 0;
	var boolean g_first_meas_res := true;

	/* PCU Interface of BTS */
	port PCUIF_CODEC_PT PCU;
}

function f_init_rsl(charstring id) runs on test_CT {
	vc_IPA := IPA_Emulation_CT.create(id & "-RSL-IPA");
	vc_RSL := RSL_Emulation_CT.create(id & "-RSL");

	map(vc_IPA:IPA_PORT, system:IPA_CODEC_PT);
	connect(vc_IPA:IPA_RSL_PORT, vc_RSL:IPA_PT);
	connect(self:RSL_CCHAN, vc_RSL:CCHAN_PT);

	vc_IPA.start(IPA_Emulation.main_server(mp_rsl_ip, mp_rsl_port));
	vc_RSL.start(RSL_Emulation.main(false));
}

type record ConnHdlrPars {
	RslChannelNr chan_nr,
	RSL_IE_ChannelMode chan_mode,
	float t_guard,
	ConnL1Pars l1_pars,
	TestSpecUnion spec optional,
	RSL_IE_EncryptionInfo encr optional,
	BtsBand bts0_band optional
}

/* Test-specific parameters */
type union TestSpecUnion {
	RllTestCase rll
}

template (value) RachControlParameters ts_RachCtrl_default := {
	max_retrans := RACH_MAX_RETRANS_7,
	tx_integer := '1001'B, /* 12 slots */
	cell_barr_access := false,
	re_not_allowed := true,
	acc := '0000010000000000'B
};

template (value) CellSelectionParameters ts_CellSelPar_default := {
	cell_resel_hyst_2dB := 2,
	ms_txpwr_max_cch := mp_ms_power_level_exp,
	acs := '0'B,
	neci := true,
	rxlev_access_min := 0
}

template (value) LocationAreaIdentification ts_LAI_default := {
	mcc_mnc := '262F42'H,
	lac := 42
}

/* Default SYSTEM INFORMATION 3 */
template (value) SystemInformation ts_SI3_default := {
	header := ts_RrHeader(SYSTEM_INFORMATION_TYPE_3, 18),
	payload := {
		si3 := {
			cell_id := 23,
			lai := ts_LAI_default,
			ctrl_chan_desc := {
				msc_r99 := true,
				att := true,
				bs_ag_blks_res := 1,
				ccch_conf := CCHAN_DESC_1CCCH_COMBINED,
				si22ind := false,
				cbq3 := CBQ3_IU_MODE_NOT_SUPPORTED,
				spare := '00'B,
				bs_pa_mfrms := 0, /* 2 multiframes */
				t3212 := 1 /* 6 minutes */
			},
			cell_options := {
				dn_ind := false,
				pwrc := false,
				dtx := MS_MAY_USE_UL_DTX,
				radio_link_tout_div4 := (32/4)-1
			},
			cell_sel_par := ts_CellSelPar_default,
			rach_control := ts_RachCtrl_default,
			rest_octets := '2C2B2B2B'O /* GPRS present */
		}
	}
}

template (value) SystemInformation ts_SI2_default := {
	header := ts_RrHeader(SYSTEM_INFORMATION_TYPE_2, 22),
	payload := {
		si2 := {
			bcch_freq_list := '00000000000000000000000000000000'O,
			ncc_permitted := '11111111'B,
			rach_control := ts_RachCtrl_default
		}
	}
}

template (value) SystemInformation ts_SI4_default := {
	header := ts_RrHeader(SYSTEM_INFORMATION_TYPE_4, 12), /* no CBCH / restoct */
	payload := {
		si4 := {
			lai := ts_LAI_default,
			cell_sel_par := ts_CellSelPar_default,
			rach_control := ts_RachCtrl_default,
			cbch_chan_desc := omit,
			cbch_mobile_alloc := omit,
			rest_octets := ''O
		}
	}
}

function f_rsl_bcch_fill_raw(RSL_IE_SysinfoType rsl_si_type, octetstring si_enc)
runs on test_CT {
	log("Setting ", rsl_si_type, ": ", si_enc);
	RSL_CCHAN.send(ts_RSL_UD(ts_RSL_BCCH_INFO(rsl_si_type, si_enc)));
}

function f_rsl_bcch_fill(RSL_IE_SysinfoType rsl_si_type, template (value) SystemInformation si_dec)
runs on test_CT {
	var octetstring si_enc := enc_SystemInformation(valueof(si_dec));
	log("Setting ", rsl_si_type, ": ", si_dec);
	f_rsl_bcch_fill_raw(rsl_si_type, si_enc);
}

friend function f_init_vty(charstring id) runs on test_CT {
	map(self:BTSVTY, system:BTSVTY);
	f_vty_set_prompts(BTSVTY);
	f_vty_transceive(BTSVTY, "enable");
}

friend function f_init_vty_bsc() runs on test_CT {
	map(self:BSCVTY, system:BSCVTY);
	f_vty_set_prompts(BSCVTY, "OsmoBSC");
	f_vty_transceive(BSCVTY, "enable");
}

/* PCU socket may at any time receive a new INFO.ind */
private altstep as_pcu_info_ind(PCUIF_CODEC_PT pt, integer pcu_conn_id,
				out PCUIF_Message pcu_last_info) {
	var PCUIF_send_data sd;
	[] pt.receive(t_SD_PCUIF(pcu_conn_id, tr_PCUIF_INFO_IND(0, ?))) -> value sd {
		pcu_last_info := sd.data;
		}
	[] pt.receive(t_SD_PCUIF(pcu_conn_id, tr_PCUIF_INFO_IND(?, ?, ?))) -> value sd {
		Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, "Invalid PCU Version/BTS Number received");
		}
}

private function f_init_pcu(PCUIF_CODEC_PT pt, charstring id,
			    out integer pcu_conn_id, out PCUIF_Message pcu_last_info) {
	timer T := 2.0;
	var PCUIF_send_data sd;
	if (mp_pcu_socket == "") {
		pcu_conn_id := -1;
		return;
	}
	pcu_conn_id := f_pcuif_connect(pt, mp_pcu_socket);

	T.start;
	alt {
	[] as_pcu_info_ind(pt, pcu_conn_id, pcu_last_info);
	[] T.timeout {
		Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, "Timeout waiting for PCU INFO_IND");
		}
	}
}

private function f_init_trxc(TRXC_CODEC_PT pt, charstring id,
			     out integer trxc_conn_id) {
	var Result res;

	res := TRXC_CodecPort_CtrlFunct.f_IPL4_connect(pt, mp_bts_trxc_ip, mp_bts_trxc_port,
						       "", -1, -1, { udp := {} }, {});
	if (not ispresent(res.connId)) {
		Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail,
					"Could not connect to the control (TRXC) interface " &
					"of FakeTRX, check your configuration");
	}
	trxc_conn_id := res.connId;
}

/* global init function */
function f_init() runs on test_CT {
	var charstring id := testcasename();
	timer T := mp_ipa_up_timeout;
	g_AllChannels := {
		/* TS 1..4: TCH/F */
		valueof(ts_RslChanNr_Bm(1)), valueof(ts_RslChanNr_Bm(2)),
		valueof(ts_RslChanNr_Bm(3)), valueof(ts_RslChanNr_Bm(4)),
		/* TS 5: TCH/H */
		valueof(ts_RslChanNr_Lm(5,0)), valueof(ts_RslChanNr_Lm(5,1)),
		/* TS 0: SDCCH/4 */
		valueof(ts_RslChanNr_SDCCH4(0,0)), valueof(ts_RslChanNr_SDCCH4(0,1)),
		valueof(ts_RslChanNr_SDCCH4(0,2)), valueof(ts_RslChanNr_SDCCH4(0,3)),
		/* TS 6: SDCCH/8 */
		valueof(ts_RslChanNr_SDCCH8(6,0)), valueof(ts_RslChanNr_SDCCH8(6,1)),
		valueof(ts_RslChanNr_SDCCH8(6,2)), valueof(ts_RslChanNr_SDCCH8(6,3)),
		valueof(ts_RslChanNr_SDCCH8(6,4)), valueof(ts_RslChanNr_SDCCH8(6,5)),
		valueof(ts_RslChanNr_SDCCH8(6,6)), valueof(ts_RslChanNr_SDCCH8(6,7))
	};

	/* FIXME: FACCH/H is unreliable with calypso firmware, see OS#3653 */
	if (mp_bts_trxc_port != -1) {
		g_AllChanTypes := {
			/* TS 1..4: TCH/F */
			valueof(ts_RslChanNr_Bm(1)),
			/* TS 5: TCH/H */
			valueof(ts_RslChanNr_Lm(5,1)),
			/* TS 0: SDCCH/4 */
			valueof(ts_RslChanNr_SDCCH4(0,2)),
			/* TS 6: SDCCH/8 */
			valueof(ts_RslChanNr_SDCCH8(6,4))
		};
	} else {
		g_AllChanTypes := {
			/* TS 1..4: TCH/F */
			valueof(ts_RslChanNr_Bm(1)),
			/* TS 0: SDCCH/4 */
			valueof(ts_RslChanNr_SDCCH4(0,2)),
			/* TS 6: SDCCH/8 */
			valueof(ts_RslChanNr_SDCCH8(6,4))
		};
	}
	f_init_rsl(id);
	T.start;
	alt {
	[] RSL_CCHAN.receive(ASP_IPA_Event:{up_down := ASP_IPA_EVENT_UP});
	[] T.timeout {
		Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, "Timeout waiting for ASP_IPA_EVENT_UP");
		}
	}
	f_sleep(0.5);	/* workaround for OS#3000 */
	f_init_vty(id);
	f_ipa_ctrl_start(mp_ctrl_ip, mp_ctrl_port);

	/* Send SI3 to the BTS, it is needed for various computations */
	f_rsl_bcch_fill(RSL_SYSTEM_INFO_3, ts_SI3_default);
	/* SI2 + SI4 are required for SI testing as they are mandatory defaults */
	f_rsl_bcch_fill(RSL_SYSTEM_INFO_2, ts_SI2_default);
	f_rsl_bcch_fill(RSL_SYSTEM_INFO_4, ts_SI4_default);

	map(self:PCU, system:PCU);
	f_init_pcu(PCU, id, g_pcu_conn_id, g_pcu_last_info);

	if (mp_bts_trxc_port != -1) {
		var TrxcMessage ret;

		/* Init TRXC interface to FakeTRX */
		map(self:BTS_TRXC, system:BTS_TRXC);
		f_init_trxc(BTS_TRXC, id, g_bts_trxc_conn_id);

		/* Start with a default moderate timing offset equalling TA=2, and RSSI=-60 */
		ret := f_TRXC_transceive(BTS_TRXC, g_bts_trxc_conn_id, valueof(ts_TRXC_FAKE_TIMING(2*256)));
		ret := f_TRXC_transceive(BTS_TRXC, g_bts_trxc_conn_id, valueof(ts_TRXC_FAKE_RSSI(-60)));
		/* OsmoBTS may have different AB / NB threshold (see MIN_QUAL_NORM, MIN_QUAL_RACH) */
		ret := f_TRXC_transceive(BTS_TRXC, g_bts_trxc_conn_id, valueof(ts_TRXC_FAKE_CI(60)));
	}

	/* Wait some extra time to make sure the BTS emits a stable carrier.
	 * (this is only relevant when running the tests with a physical BTS.) */
	f_sleep(mp_ipa_up_delay);
}

/* Attach L1CTL to master test_CT (classic tests, non-handler mode) */
function f_init_l1ctl() runs on test_CT {
	map(self:L1CTL, system:L1CTL);
	f_connect_reset(L1CTL);
}

type function void_fn(charstring id) runs on ConnHdlr;

/* create a new test component */
function f_start_handler(void_fn fn, ConnHdlrPars pars,
			 boolean pcu_comp := false,
			 boolean trxc_comp := false)
runs on test_CT return ConnHdlr {
	var charstring id := testcasename();
	var ConnHdlr vc_conn;

	vc_conn := ConnHdlr.create(id);
	/* connect to RSL Emulation main component */
	connect(vc_conn:RSL, vc_RSL:CLIENT_PT);
	connect(vc_conn:RSL_PROC, vc_RSL:RSL_PROC);

	/* The ConnHdlr component may want to talk to some ports directly,
	 * so we disconnect it from the test_CT and connect it to the component.
	 * This obviously only works for one component, i.e. no concurrency. */
	if (pcu_comp) {
		unmap(self:PCU, system:PCU);
		map(vc_conn:PCU, system:PCU);
	}
	if (trxc_comp) {
		unmap(self:BTS_TRXC, system:BTS_TRXC);
		map(vc_conn:BTS_TRXC, system:BTS_TRXC);
	}

	vc_conn.start(f_handler_init(fn, id, pars));
	return vc_conn;
}

template ASP_RSL_Unitdata ts_RSL_UD(template RSL_Message rsl, IpaStreamId sid := IPAC_PROTO_RSL_TRX0) := {
	streamId := sid,
	rsl := rsl
}

template ASP_RSL_Unitdata tr_RSL_UD(template RSL_Message rsl,
				    template IpaStreamId sid := IPAC_PROTO_RSL_TRX0) := {
	streamId := sid,
	rsl := rsl
}

private altstep as_Tguard() runs on ConnHdlr {
	[] g_Tguard.timeout {
		Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, "Tguard timeout");
	}
}

friend function f_l1_tune(L1CTL_PT L1CTL, L1ctlCcchMode ccch_mode := CCCH_MODE_COMBINED) {
	f_L1CTL_FBSB(L1CTL, { false, mp_trx0_arfcn }, ccch_mode, mp_rxlev_exp);
}

private function f_trxc_fake_rssi(TRXC_RSSI rssi) runs on ConnHdlr {
	var TrxcMessage ret;
	ret := f_TRXC_transceive(BTS_TRXC, g_bts_trxc_conn_id, valueof(ts_TRXC_FAKE_RSSI(rssi)));
}

private function f_trxc_fake_toffs256(int16_t toffs256) runs on ConnHdlr {
	var TrxcMessage ret;
	ret := f_TRXC_transceive(BTS_TRXC, g_bts_trxc_conn_id, valueof(ts_TRXC_FAKE_TIMING(toffs256)));
}

/* first function started in ConnHdlr component */
private function f_handler_init(void_fn fn, charstring id, ConnHdlrPars pars)
runs on ConnHdlr {
	g_pars := pars;
	g_chan_nr := pars.chan_nr;

	map(self:L1CTL, system:L1CTL);
	f_connect_reset(L1CTL);

	if (mp_bts_trxc_port != -1 and BTS_TRXC.checkstate("Mapped")) {
		f_init_trxc(BTS_TRXC, id, g_bts_trxc_conn_id);
	}

	g_Tguard.start(pars.t_guard);
	activate(as_Tguard());

	f_rslem_register(0, pars.chan_nr);

	/* call the user-supplied test case function */
	fn.apply(id);
}

function f_rsl_transceive_ret(template RSL_Message tx, template RSL_Message exp_rx, charstring id,
				boolean ignore_other := false)
runs on ConnHdlr return RSL_Message {
	var RSL_Message rx;
	timer T := 3.0;
	RSL.send(tx);
	T.start;
	alt {
	[] RSL.receive(exp_rx) -> value rx {
		T.stop;
		setverdict(pass);
		}
	[] T.timeout {
		Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, "Timeout expecting " & id);
		}
	[not ignore_other] as_l1_sacch();
	[not ignore_other] as_meas_res();
	[not ignore_other] as_l1_dcch();
	[not ignore_other] RSL.receive {
		Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, "Unexpected RSL message received");
		}
	[ignore_other] RSL.receive { repeat; }
	}
	return rx;
}

function f_rsl_transceive(template RSL_Message tx, template RSL_Message exp_rx, charstring id,
			  boolean ignore_other := false)
runs on ConnHdlr {
	var RSL_Message rx := f_rsl_transceive_ret(tx, exp_rx, id, ignore_other);
}

function f_rsl_chan_act(RSL_IE_ChannelMode mode, boolean encr_enable := false, RSL_IE_List more_ies := {},
			RSL_IE_ActivationType act_type := t_RSL_IE_ActType_IA) runs on ConnHdlr {
	var RSL_Message ch_act := valueof(ts_RSL_CHAN_ACT(g_chan_nr, mode, act_type));
	if (encr_enable) {
		/* append encryption related IEs, if requested */
		var RSL_IE_EncryptionInfo encr_info;
		encr_info := valueof(ts_RSL_IE_EncrInfo(g_pars.encr.alg_id, g_pars.encr.key));
		ch_act.ies := ch_act.ies & { valueof(t_RSL_IE(RSL_IE_ENCR_INFO, RSL_IE_Body:{encr_info :=
encr_info})) };
	}
	ch_act.ies := ch_act.ies & more_ies;
	f_rsl_transceive(ch_act, tr_RSL_CHAN_ACT_ACK(g_chan_nr), "RSL CHAN ACT");
}

function f_rsl_chan_deact() runs on ConnHdlr {
	f_rsl_transceive(ts_RSL_RF_CHAN_REL(g_chan_nr), tr_RSL_RF_CHAN_REL_ACK(g_chan_nr),
			"RF CHAN REL", true);
}

friend template ConnHdlrPars t_Pars(template RslChannelNr chan_nr,
					template RSL_IE_ChannelMode chan_mode,
					float t_guard := 20.0) := {
	chan_nr := valueof(chan_nr),
	chan_mode := valueof(chan_mode),
	t_guard := t_guard,
	l1_pars := {
		dtx_enabled := false,
		toa256_enabled := false,
		meas_ul := {
			full := {
				rxlev := mp_ul_rxlev_exp,
				rxqual := 0
			},
			sub := {
				rxlev := mp_ul_rxlev_exp,
				rxqual := 0
			}
		},
		timing_offset_256syms := mp_timing_offset_256syms_exp,
		bs_power_level := 0,
		ms_power_level := mp_ms_power_level_exp,
		ms_actual_ta := mp_ms_actual_ta_exp
	},
	spec := omit,
	encr := omit,
	bts0_band := omit
}

/***********************************************************************
 * Channel Activation / Deactivation
 ***********************************************************************/

/* Stress test: Do 500 channel activations/deactivations in rapid succession */
function f_TC_chan_act_stress(charstring id) runs on ConnHdlr {
	for (var integer i := 0; i < 500; i := i+1) {
		f_rsl_chan_act(g_pars.chan_mode);
		f_rsl_chan_deact();
	}
	setverdict(pass);
}
testcase TC_chan_act_stress() runs on test_CT {
	var ConnHdlr vc_conn;
	var ConnHdlrPars pars := valueof(t_Pars(t_RslChanNr_Bm(1), ts_RSL_ChanMode_SIGN));
	f_init();
	vc_conn := f_start_handler(refers(f_TC_chan_act_stress), pars);
	vc_conn.done;
	Misc_Helpers.f_shutdown(__BFILE__, __LINE__);
}

/* Test if re-activation of an already active channel fails as expected */
function f_TC_chan_act_react(charstring id) runs on ConnHdlr {
	f_rsl_chan_act(g_pars.chan_mode);
	/* attempt to activate the same lchan again -> expect reject */
	RSL.send(ts_RSL_CHAN_ACT(g_chan_nr, g_pars.chan_mode));
	alt {
	[] RSL.receive(tr_RSL_CHAN_ACT_ACK(g_chan_nr)) {
		Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, "Unexpected CHAN ACT ACK on double activation");
		}
	[] RSL.receive(tr_RSL_CHAN_ACT_NACK(g_chan_nr)) {
		setverdict(pass);
		}
	}
	f_rsl_chan_deact();
}
testcase TC_chan_act_react() runs on test_CT {
	var ConnHdlr vc_conn;
	var ConnHdlrPars pars := valueof(t_Pars(t_RslChanNr_Bm(1), ts_RSL_ChanMode_SIGN));
	f_init();
	vc_conn := f_start_handler(refers(f_TC_chan_act_react), pars);
	vc_conn.done;
	Misc_Helpers.f_shutdown(__BFILE__, __LINE__);
}

/* Attempt to de-activate a channel that's not active */
function f_TC_chan_deact_not_active(charstring id) runs on ConnHdlr {
	timer T := 3.0;
	RSL.send(ts_RSL_RF_CHAN_REL(g_chan_nr));
	T.start;
	alt {
	[] RSL.receive(tr_RSL_RF_CHAN_REL_ACK(g_chan_nr)) {
		setverdict(pass);
		}
	[] T.timeout {
		Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, "Timeout expecting RF_CHAN_REL_ACK");
		}
	}
}
testcase TC_chan_deact_not_active() runs on test_CT {
	var ConnHdlrPars pars := valueof(t_Pars(t_RslChanNr_Bm(1), ts_RSL_ChanMode_SIGN));
	f_init();
	var ConnHdlr vc_conn := f_start_handler(refers(f_TC_chan_deact_not_active), pars);
	vc_conn.done;
	Misc_Helpers.f_shutdown(__BFILE__, __LINE__);
}

/* attempt to activate channel with wrong RSL Channel Nr IE; expect NACK */
function f_TC_chan_act_wrong_nr(charstring id) runs on ConnHdlr {
	RSL.send(ts_RSL_CHAN_ACT(g_chan_nr, g_pars.chan_mode));
	alt {
	[] RSL.receive(tr_RSL_CHAN_ACT_ACK(g_chan_nr)) {
		Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, "Unexpected CHAN ACT ACK");
		}
	[] RSL.receive(tr_RSL_CHAN_ACT_NACK(g_chan_nr)) {
		setverdict(pass);
		}
	}
}
private type record WrongChanNrCase {
	RslChannelNr	chan_nr,
	charstring	description
}
private type record of WrongChanNrCase WrongChanNrCases;
private template WrongChanNrCase t_WCN(template RslChannelNr chan_nr, charstring desc) := {
	chan_nr := chan_nr,
	description := desc
}

testcase TC_chan_act_wrong_nr() runs on test_CT {
	var ConnHdlr vc_conn;
	var ConnHdlrPars pars;

	f_init();

	var WrongChanNrCases wrong := {
		valueof(t_WCN(t_RslChanNr_RACH(0), "RACH is not a dedicated channel")),
		valueof(t_WCN(t_RslChanNr_RACH(1), "RACH doesn't exist on timeslot")),
		valueof(t_WCN(t_RslChanNr_BCCH(0), "BCCH is not a dedicated channel")),
		valueof(t_WCN(t_RslChanNr_PCH_AGCH(0), "PCH/AGCH is not a dedicated channel")),
		valueof(t_WCN(t_RslChanNr_Bm(0), "TS0 cannot be TCH/F")),
		valueof(t_WCN(t_RslChanNr_Lm(0, 0), "TS0 cannot be TCH/H")),
		valueof(t_WCN(t_RslChanNr_Lm(0, 1), "TS0 cannot be TCH/H")),
		valueof(t_WCN(t_RslChanNr_PDCH(0), "TS0 cannot be PDCH")),
		valueof(t_WCN(t_RslChanNr_SDCCH8(0, 0), "TS0 cannot be SDCCH/8")),
		valueof(t_WCN(t_RslChanNr_SDCCH8(0, 7), "TS0 cannot be SDCCH/8")),
		valueof(t_WCN(t_RslChanNr_SDCCH4(7, 0), "TS7 cannot be SDCCH/4")),
		valueof(t_WCN(t_RslChanNr_SDCCH4(7, 3), "TS7 cannot be SDCCH/4")),
		valueof(t_WCN(t_RslChanNr_Lm(1, 0), "TS1 cannot be TCH/H"))
	};

	for (var integer i := 0; i < sizeof(wrong); i := i+1) {
		pars := valueof(t_Pars(wrong[i].chan_nr, ts_RSL_ChanMode_SIGN));
		vc_conn := f_start_handler(refers(f_TC_chan_act_wrong_nr), pars);
		vc_conn.done;
	}
	Misc_Helpers.f_shutdown(__BFILE__, __LINE__);
}

/* execute the same callback function on a variety of logical channels */
friend function f_testmatrix_each_chan(ConnHdlrPars pars, void_fn fn) runs on test_CT {
	var ConnHdlr vc_conn;
	f_init();

	/* test on each of the channels we have */
	for (var integer i := 0; i < sizeof(g_AllChanTypes); i := i+1) {
		pars.chan_nr := valueof(g_AllChanTypes[i]);

		log(testcasename(), ": XXX Starting on ", g_AllChanTypes[i]);
		vc_conn := f_start_handler(fn, pars);
		vc_conn.done;
	}

	Misc_Helpers.f_shutdown(__BFILE__, __LINE__);
}

/***********************************************************************
 * SACCH handling
 ***********************************************************************/

private function f_exp_sacch(boolean exp) runs on ConnHdlr {
	timer T_sacch := 3.0;
	T_sacch.start;
	alt {
	[not exp] L1CTL.receive(tr_L1CTL_DATA_IND(g_chan_nr, tr_RslLinkID_SACCH(0))) {
		Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, "Received SACCH when not expecting it");
		}
	[not exp] T_sacch.timeout {
		setverdict(pass);
		}
	[exp] L1CTL.receive(tr_L1CTL_DATA_IND(g_chan_nr, tr_RslLinkID_SACCH(0))) {
		setverdict(pass);
		}
	[exp] T_sacch.timeout {
		Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, log2str("Timeout waiting for SACCH on ", g_chan_nr));
		}
	[] L1CTL.receive { repeat; }
	[] RSL.receive { repeat; }
	}
}

/* Test if DEACTIVATE SACCH actualy deactivates its transmission (TS 48.058 4.6) */
private function f_TC_deact_sacch(charstring id) runs on ConnHdlr {
	f_l1_tune(L1CTL);
	RSL.clear;

	/* activate the logical channel */
	f_est_dchan();
	L1CTL.clear;

	/* check that SACCH actually are received as expected */
	f_exp_sacch(true);

	/* deactivate SACCH on the logical channel */
	RSL.send(ts_RSL_DEACT_SACCH(g_chan_nr));
	f_sleep(1.0);
	L1CTL.clear;

	/* check that no SACCH are received anymore */
	f_exp_sacch(false);

	/* release the channel */
	f_rsl_chan_deact();
	f_L1CTL_DM_REL_REQ(L1CTL, g_chan_nr);
}
testcase TC_deact_sacch() runs on test_CT {
	var ConnHdlr vc_conn;
	var ConnHdlrPars pars;
	f_init();
	for (var integer i := 0; i < sizeof(g_AllChannels); i := i+1) {
	//for (var integer i := 0; i < 1; i := i+1) {
		pars := valueof(t_Pars(g_AllChannels[i], ts_RSL_ChanMode_SIGN));
		log(testcasename(), ": Starting for ", g_AllChannels[i]);
		vc_conn := f_start_handler(refers(f_TC_deact_sacch), pars);
		vc_conn.done;
	}
	/* TODO: do the above in parallel, rather than sequentially? */
	Misc_Helpers.f_shutdown(__BFILE__, __LINE__);
}

/* verify that given SACCH payload is present */
private function f_sacch_present(template octetstring l3_exp) runs on ConnHdlr {
	var L1ctlDlMessage dl;
	/* check that the specified SI5 value is actually sent */
	timer T_sacch := 3.0;
	L1CTL.clear;
	T_sacch.start;
	alt {
	[] L1CTL.receive(tr_L1CTL_DATA_IND(g_chan_nr, tr_RslLinkID_SACCH(0))) -> value dl {
		var octetstring l3 := substr(dl.payload.data_ind.payload, 4, 19);
		if (match(l3, l3_exp)) {
			setverdict(pass);
		} else {
			repeat;
		}
		}
	[] L1CTL.receive { repeat; }
	[] T_sacch.timeout {
		Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, log2str("Timeout waiting for SACCH ", l3_exp));
		}
	}
}

/* verify that given SACCH payload is not present */
private function f_sacch_missing(template octetstring l3_exp) runs on ConnHdlr {
	var L1ctlDlMessage dl;
	/* check that the specified SI5 value is actually sent */
	timer T_sacch := 3.0;
	L1CTL.clear;
	T_sacch.start;
	alt {
	[] L1CTL.receive(tr_L1CTL_DATA_IND(g_chan_nr, tr_RslLinkID_SACCH(0))) -> value dl {
		var octetstring l3 := substr(dl.payload.data_ind.payload, 4, 19);
		if (match(l3, l3_exp)) {
			Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, log2str("Received unexpected SACCH ", dl));
		} else {
			repeat;
		}
		}
	[] L1CTL.receive { repeat; }
	[] T_sacch.timeout {
		setverdict(pass);
		}
	}
}

/* Test for default SACCH FILL transmitted in DL SACCH (all channel types) */
private function f_TC_sacch_filling(charstring id) runs on ConnHdlr {
	/* Set a known default SACCH filling for SI5 */
	var octetstring si5 := f_rnd_octstring(19);
	RSL.send(ts_RSL_SACCH_FILL(RSL_SYSTEM_INFO_5, si5));

	f_l1_tune(L1CTL);
	RSL.clear;

	/* activate the logical channel */
	f_est_dchan();

	/* check that the specified SI5 value is actually sent */
	f_sacch_present(si5);

	/* release the channel */
	RSL.clear;
	f_rsl_chan_deact();
	f_L1CTL_DM_REL_REQ(L1CTL, g_chan_nr);
}
testcase TC_sacch_filling() runs on test_CT {
	var ConnHdlr vc_conn;
	var ConnHdlrPars pars;
	f_init();
	for (var integer i := 0; i < sizeof(g_AllChannels); i := i+1) {
		pars := valueof(t_Pars(g_AllChannels[i], ts_RSL_ChanMode_SIGN));
		log(testcasename(), ": Starting for ", g_AllChannels[i]);
		vc_conn := f_start_handler(refers(f_TC_sacch_filling), pars);
		vc_conn.done;
	}
	/* TODO: do the above in parallel, rather than sequentially? */
	Misc_Helpers.f_shutdown(__BFILE__, __LINE__);
}

/* Test for lchan-specific SACCH INFO MODIFY (TS 48.058 4.12) */
private function f_TC_sacch_info_mod(charstring id) runs on ConnHdlr {
	/* Set a known default SACCH filling for SI5 */
	var octetstring si5 := f_rnd_octstring(19);
	var octetstring si5_diff := f_rnd_octstring(19);
	RSL.send(ts_RSL_SACCH_FILL(RSL_SYSTEM_INFO_5, si5));

	f_l1_tune(L1CTL);
	RSL.clear;

	log("Activating channel, expecting standard SI5");
	/* activate the logical channel */
	f_est_dchan();
	/* check that the specified SI5 value is actually sent */
	f_sacch_present(si5);

	/* set channel-specific different SI5 */
	log("Setting channel specific SACCH INFO, expecting it");
	RSL.send(ts_RSL_SACCH_INF_MOD(g_chan_nr, RSL_SYSTEM_INFO_5, si5_diff))
	/* check that the specified lchan-specific value is now used */
	f_sacch_present(si5_diff);

	/* deactivate the channel and re-activate it, this should result in default SI5  */
	log("De-activating and re-activating channel, expecting standard SI5");
	f_rsl_chan_deact();
	f_rsl_chan_act(valueof(ts_RSL_ChanMode_SIGN));
	/* Verify that the TRX-wide default SACCH filling is present again */
	f_sacch_present(si5);

	/* release the channel */
	RSL.clear;
	f_rsl_chan_deact();
	f_L1CTL_DM_REL_REQ(L1CTL, g_chan_nr);
}
testcase TC_sacch_info_mod() runs on test_CT {
	var ConnHdlr vc_conn;
	var ConnHdlrPars pars;
	f_init();
	for (var integer i := 0; i < sizeof(g_AllChannels); i := i+1) {
		pars := valueof(t_Pars(g_AllChannels[i], ts_RSL_ChanMode_SIGN));
		log(testcasename(), ": Starting for ", g_AllChannels[i]);
		vc_conn := f_start_handler(refers(f_TC_sacch_info_mod), pars);
		vc_conn.done;
	}
	/* TODO: do the above in parallel, rather than sequentially? */
	Misc_Helpers.f_shutdown(__BFILE__, __LINE__);
}

/* Test SACCH scheduling of multiple different SI message types */
private function f_TC_sacch_multi(charstring id) runs on ConnHdlr {
	var octetstring si5 := f_rnd_octstring(19);
	var octetstring si5bis := f_rnd_octstring(19);
	var octetstring si5ter := f_rnd_octstring(19);
	var octetstring si6 := f_rnd_octstring(19);

	RSL.send(ts_RSL_SACCH_FILL(RSL_SYSTEM_INFO_5, si5));
	RSL.send(ts_RSL_SACCH_FILL(RSL_SYSTEM_INFO_5bis, si5bis));
	RSL.send(ts_RSL_SACCH_FILL(RSL_SYSTEM_INFO_5ter, si5ter));
	RSL.send(ts_RSL_SACCH_FILL(RSL_SYSTEM_INFO_6, si6));

	f_l1_tune(L1CTL);
	RSL.clear;

	/* activate the logical channel */
	f_est_dchan();
	L1CTL.clear;

	/* check that SACCH actually are received as expected */
	f_sacch_present(si5);
	f_sacch_present(si5bis);
	f_sacch_present(si5ter);
	f_sacch_present(si6);

	/* release the channel */
	f_rsl_chan_deact();
	f_L1CTL_DM_REL_REQ(L1CTL, g_chan_nr);
}
testcase TC_sacch_multi() runs on test_CT {
	var ConnHdlr vc_conn;
	var ConnHdlrPars pars;
	f_init();
	for (var integer i := 0; i < sizeof(g_AllChannels); i := i+1) {
		pars := valueof(t_Pars(g_AllChannels[i], ts_RSL_ChanMode_SIGN));
		log(testcasename(), ": Starting for ", g_AllChannels[i]);
		vc_conn := f_start_handler(refers(f_TC_sacch_multi), pars);
		vc_conn.done;
	}
	/* TODO: do the above in parallel, rather than sequentially? */
	Misc_Helpers.f_shutdown(__BFILE__, __LINE__);
}

/* Test if SACH information is modified as expected */
private function f_TC_sacch_multi_chg(charstring id) runs on ConnHdlr {
	var octetstring si5 := f_rnd_octstring(19);
	var octetstring si6 := f_rnd_octstring(19);

	/* First, configure both SI5 and SI6 to be transmitted */
	RSL.send(ts_RSL_SACCH_FILL(RSL_SYSTEM_INFO_5, si5));
	RSL.send(ts_RSL_SACCH_FILL(RSL_SYSTEM_INFO_6, si6));

	f_l1_tune(L1CTL);
	RSL.clear;

	/* activate the logical channel */
	f_est_dchan();
	L1CTL.clear;

	/* check that SACCH actually are received as expected */
	f_sacch_present(si5);
	f_sacch_present(si6);

	/* disable SI6 */
	RSL.send(ts_RSL_SACCH_FILL(RSL_SYSTEM_INFO_6, ''O));

	/* check that SI5 is still transmitted */
	f_sacch_present(si5);
	/* check if SI6 is now gone */
	f_sacch_missing(si6);

	/* release the channel */
	f_rsl_chan_deact();
	f_L1CTL_DM_REL_REQ(L1CTL, g_chan_nr);
}
testcase TC_sacch_multi_chg() runs on test_CT {
	var ConnHdlr vc_conn;
	var ConnHdlrPars pars;
	f_init();
	for (var integer i := 0; i < sizeof(g_AllChannels); i := i+1) {
		pars := valueof(t_Pars(g_AllChannels[i], ts_RSL_ChanMode_SIGN));
		log(testcasename(), ": Starting for ", g_AllChannels[i]);
		vc_conn := f_start_handler(refers(f_TC_sacch_multi_chg), pars);
		vc_conn.done;
	}
	/* TODO: do the above in parallel, rather than sequentially? */
	Misc_Helpers.f_shutdown(__BFILE__, __LINE__);
}

/* Test for SACCH information present in RSL CHAN ACT (overrides FILLING) */
private function f_TC_sacch_chan_act(charstring id) runs on ConnHdlr {
	var octetstring si5 := f_rnd_octstring(19);
	var octetstring si6 := f_rnd_octstring(19);
	var octetstring si5_specific := f_rnd_octstring(19);
	var octetstring si6_specific := f_rnd_octstring(19);

	/* First, configure both SI5 and SI6 to be transmitted */
	RSL.send(ts_RSL_SACCH_FILL(RSL_SYSTEM_INFO_5, si5));
	RSL.send(ts_RSL_SACCH_FILL(RSL_SYSTEM_INFO_6, si6));

	f_l1_tune(L1CTL);
	RSL.clear;

	/* activate channel with different SACCH filling */
	var RSL_SacchInfo sacch_info := valueof(ts_RSL_SacchInfo({
				ts_RSL_SacchInfoElem(RSL_SYSTEM_INFO_5, si5_specific),
				ts_RSL_SacchInfoElem(RSL_SYSTEM_INFO_6, si6_specific)
				}));
	var RSL_IE_List addl_ies := { valueof(t_RSL_IE(RSL_IE_SACCH_INFO,
							RSL_IE_Body:{sacch_info := sacch_info})) };
	f_est_dchan(more_ies := addl_ies);

	/* check that SACCH actually are received as expected */
	f_sacch_present(si5_specific);
	f_sacch_present(si6_specific);

	/* release the channel */
	f_rsl_chan_deact();
	f_L1CTL_DM_REL_REQ(L1CTL, g_chan_nr);
}
testcase TC_sacch_chan_act() runs on test_CT {
	var ConnHdlr vc_conn;
	var ConnHdlrPars pars;
	f_init();

	for (var integer i := 0; i < sizeof(g_AllChannels); i := i+1) {
		pars := valueof(t_Pars(g_AllChannels[i], ts_RSL_ChanMode_SIGN));
		log(testcasename(), ": Starting for ", g_AllChannels[i]);
		vc_conn := f_start_handler(refers(f_TC_sacch_chan_act), pars);
		vc_conn.done;
	}
	/* TODO: do the above in parallel, rather than sequentially? */
	Misc_Helpers.f_shutdown(__BFILE__, __LINE__);
}

/* verify that SACCH DL transmission is started only if MS power IE present
 * see section 4.1.3 of 3GPP TS 48.058 */
private function f_TC_sacch_chan_act_ho_async(charstring id) runs on ConnHdlr {
	var octetstring si5 := f_rnd_octstring(19);

	f_l1_tune(L1CTL);
	RSL.clear;

	/* Step 1: Activate ASYNC HO channel without MS power IE */

	/* Activate channel on BTS side */
	f_rsl_chan_act(g_pars.chan_mode, act_type := t_RSL_IE_ActType_HO_ASYNC);
	/* don't perform immediate assignment here, as we're testing non-IA case */
	/* enable dedicated mode */
	f_L1CTL_DM_EST_REQ(L1CTL, {false, mp_trx0_arfcn }, g_pars.chan_nr, 7);

	/* Verify that no DL SACCH is being received */
	f_sacch_missing(?);

	f_rsl_chan_deact();
	f_L1CTL_DM_REL_REQ(L1CTL, g_chan_nr);


	/* Step 2: Activate ASYNC HO channel with MS power IE */

	/* Activate channel on BTS side */
	var RSL_IE_List addl_ies := {
		valueof(t_RSL_IE(RSL_IE_MS_POWER, RSL_IE_Body:{ms_power := ts_RSL_IE_MS_Power(0)}))
		};
	f_rsl_chan_act(g_pars.chan_mode, more_ies := addl_ies, act_type := t_RSL_IE_ActType_HO_ASYNC);
	/* don't perform immediate assignment here, as we're testing non-IA case */
	/* enable dedicated mode */
	f_L1CTL_DM_EST_REQ(L1CTL, {false, mp_trx0_arfcn }, g_pars.chan_nr, 7);

	/* Verify that DL SACCH is being received */
	f_sacch_present(si5);

	f_rsl_chan_deact();
	f_L1CTL_DM_REL_REQ(L1CTL, g_chan_nr);
}
testcase TC_sacch_chan_act_ho_async() runs on test_CT {
	var ConnHdlr vc_conn;
	var ConnHdlrPars pars;
	f_init();

	for (var integer i := 0; i < sizeof(g_AllChannels); i := i+1) {
		pars := valueof(t_Pars(g_AllChannels[i], ts_RSL_ChanMode_SIGN));
		log(testcasename(), ": Starting for ", g_AllChannels[i]);
		vc_conn := f_start_handler(refers(f_TC_sacch_chan_act_ho_async), pars);
		vc_conn.done;
	}
	/* TODO: do the above in parallel, rather than sequentially? */
	Misc_Helpers.f_shutdown(__BFILE__, __LINE__);
}

/* verify that SACCH DL transmission is started only if TA + MS power IEs present,
 * see section 4.1.4 of 3GPP TS 48.058 */
private function f_TC_sacch_chan_act_ho_sync(charstring id) runs on ConnHdlr {
	var octetstring si5 := f_rnd_octstring(19);
	var RSL_IE_List addl_ies;

	f_l1_tune(L1CTL);
	RSL.clear;

	/* Step 1: Activate SYNC HO channel without MS power IE */

	/* Activate channel on BTS side */
	f_rsl_chan_act(g_pars.chan_mode, act_type := t_RSL_IE_ActType_HO_SYNC);
	/* don't perform immediate assignment here, as we're testing non-IA case */
	/* enable dedicated mode */
	f_L1CTL_DM_EST_REQ(L1CTL, {false, mp_trx0_arfcn }, g_pars.chan_nr, 7);

	/* Verify that no DL SACCH is being received */
	f_sacch_missing(?);

	f_rsl_chan_deact();
	f_L1CTL_DM_REL_REQ(L1CTL, g_chan_nr);


	/* Step 2a: Activate SYNC HO channel with only MS power IE */

	/* Activate channel on BTS side */
	addl_ies := {
		valueof(t_RSL_IE(RSL_IE_MS_POWER, RSL_IE_Body:{ms_power := ts_RSL_IE_MS_Power(0)}))
		};
	f_rsl_chan_act(g_pars.chan_mode, more_ies := addl_ies, act_type := t_RSL_IE_ActType_HO_SYNC);
	/* don't perform immediate assignment here, as we're testing non-IA case */
	/* enable dedicated mode */
	f_L1CTL_DM_EST_REQ(L1CTL, {false, mp_trx0_arfcn }, g_pars.chan_nr, 7);

	/* Verify that no DL SACCH is being received */
	f_sacch_missing(?);

	f_rsl_chan_deact();
	f_L1CTL_DM_REL_REQ(L1CTL, g_chan_nr);


	/* Step 2b: Activate SYNC HO channel with TA IE */

	/* Activate channel on BTS side */
	addl_ies := {
		valueof(t_RSL_IE(RSL_IE_TIMING_ADVANCE, RSL_IE_Body:{timing_adv := 0}))
		};
	f_rsl_chan_act(g_pars.chan_mode, more_ies := addl_ies, act_type := t_RSL_IE_ActType_HO_SYNC);
	/* don't perform immediate assignment here, as we're testing non-IA case */
	/* enable dedicated mode */
	f_L1CTL_DM_EST_REQ(L1CTL, {false, mp_trx0_arfcn }, g_pars.chan_nr, 7);

	/* Verify that no DL SACCH is being received */
	f_sacch_missing(?);

	f_rsl_chan_deact();
	f_L1CTL_DM_REL_REQ(L1CTL, g_chan_nr);


	/* Step 3: Activate SYNC HO channel with MS power IE and TA IE */

	/* Activate channel on BTS side */
	addl_ies := {
		valueof(t_RSL_IE(RSL_IE_TIMING_ADVANCE, RSL_IE_Body:{timing_adv := 0})),
		valueof(t_RSL_IE(RSL_IE_MS_POWER, RSL_IE_Body:{ms_power := ts_RSL_IE_MS_Power(0)}))
		};
	f_rsl_chan_act(g_pars.chan_mode, more_ies := addl_ies, act_type := t_RSL_IE_ActType_HO_SYNC);
	/* don't perform immediate assignment here, as we're testing non-IA case */
	/* enable dedicated mode */
	f_L1CTL_DM_EST_REQ(L1CTL, {false, mp_trx0_arfcn }, g_pars.chan_nr, 7);

	/* Verify that DL SACCH is being received */
	f_sacch_present(si5);

	f_rsl_chan_deact();
	f_L1CTL_DM_REL_REQ(L1CTL, g_chan_nr);
}
testcase TC_sacch_chan_act_ho_sync() runs on test_CT {
	var ConnHdlr vc_conn;
	var ConnHdlrPars pars;
	f_init();

	for (var integer i := 0; i < sizeof(g_AllChannels); i := i+1) {
		pars := valueof(t_Pars(g_AllChannels[i], ts_RSL_ChanMode_SIGN));
		log(testcasename(), ": Starting for ", g_AllChannels[i]);
		vc_conn := f_start_handler(refers(f_TC_sacch_chan_act_ho_sync), pars);
		vc_conn.done;
	}
	/* TODO: do the above in parallel, rather than sequentially? */
	Misc_Helpers.f_shutdown(__BFILE__, __LINE__);
}


/***********************************************************************
 * RACH Handling
 ***********************************************************************/

/* like L1SAP_IS_PACKET_RACH */
private function ra_is_ps(OCT1 ra) return boolean {
	if ((ra and4b 'F0'O == '70'O) and (ra and4b '0F'O != '0F'O)) {
		return true;
	}
	return false;
}

/* generate a random RACH for circuit-switched */
private function f_rnd_ra_cs() return OCT1 {
	var OCT1 ra;
	do {
		ra := f_rnd_octstring(1);
	} while (ra_is_ps(ra));
	return ra;
}

/* generate a random RACH for packet-switched */
private function f_rnd_ra_ps() return OCT1 {
	var OCT1 ra;
	do {
		ra := f_rnd_octstring(1);
	} while (not ra_is_ps(ra));
	return ra;
}

/* generate a random 11-bit RA (packet-switched only) */
private function f_rnd_ra11_ps() return BIT11 {
	var integer ra11 := f_rnd_int(bit2int('11111111111'B));
	return int2bit(ra11, 11);
}

/* Send 1000 RACH requests and check their RA+FN on the RSL side */
testcase TC_rach_content() runs on test_CT {
	f_init();
	f_init_l1ctl();
	f_l1_tune(L1CTL);

	var GsmFrameNumber fn_last := 0;
	var boolean test_failed := false;
	for (var integer i := 0; i < 1000; i := i+1) {
		var OCT1 ra := f_rnd_ra_cs();
		var GsmFrameNumber fn := f_L1CTL_RACH(L1CTL, oct2int(ra));
		if (fn == fn_last) {
			Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, "Two RACH in same FN?!?");
		}
		fn_last := fn;

		timer T := 5.0;
		T.start;
		alt {
		[] RSL_CCHAN.receive(tr_RSL_UD(tr_RSL_CHAN_RQD(ra, fn, t_RslChanNr_RACH(0)))) {
			T.stop;
			}
		[] RSL_CCHAN.receive(tr_RSL_UD(tr_RSL_CHAN_RQD(?, ?, ?, ?))) {
			Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, "Unexpected CHAN RQD");
			}
		[] RSL_CCHAN.receive { repeat; }
		[] T.timeout {
			test_failed := true;
			log("[", i, "] Timeout waiting for CHAN RQD FN=", fn, " RA=", ra);
			}
		}
	}
	if (test_failed) {
		Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, log2str("Some out of 1000 RACH requests timed out"));
	}
	setverdict(pass);
	Misc_Helpers.f_shutdown(__BFILE__, __LINE__);
}

/* Send 1000 RACH Requests (flood ~ 89/s) and count if count(Abis) == count(Um) */
testcase TC_rach_count() runs on test_CT {
	f_init();
	f_init_l1ctl();
	f_sleep(1.0);
	f_l1_tune(L1CTL);

	var GsmFrameNumber fn_last := 0;
	for (var integer i := 0; i < 1000; i := i+1) {
		var OCT1 ra := f_rnd_ra_cs();
		var GsmFrameNumber fn := f_L1CTL_RACH(L1CTL, oct2int(ra));
		if (fn == fn_last) {
			Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, "Two RACH in same FN?!?");
		}
		fn_last := fn;
	}
	var integer rsl_chrqd := 0;
	timer T := 3.0;
	T.start;
	alt {
	[] RSL_CCHAN.receive(tr_RSL_UD(tr_RSL_CHAN_RQD(?,?))) {
		rsl_chrqd := rsl_chrqd + 1;
		f_timer_safe_restart(T);
		repeat;
		}
	[] RSL_CCHAN.receive { repeat; }
	[] T.timeout { }
	}
	if (rsl_chrqd == 1000) {
		setverdict(pass);
	} else {
		Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, log2str("Received only ", rsl_chrqd, " out of 1000 RACH"));
	}
	Misc_Helpers.f_shutdown(__BFILE__, __LINE__);
}

private function f_vty_load_ind_thresh(integer period := 10, integer bts_nr := 0) runs on test_CT {
	var charstring bts_str := "bts " & int2str(bts_nr);
	f_vty_config2(BSCVTY, {"network", bts_str}, "ccch load-indication-threshold " & int2str(period));
}

/* empirical value: Number of RACH slots per reporting interval (1s) on combined CCCH */
private template integer tr_rach_slots_per_interval := (90 .. 130);

/* Expect 0 RACH load on an idle BTS that has just started up */
testcase TC_rach_load_idle_thresh0() runs on test_CT {
	var ASP_RSL_Unitdata rx_ud;

	f_init_vty_bsc();
	/* send load indications even at 0% load */
	f_vty_load_ind_thresh(0);
	f_vty_transceive(BSCVTY, "drop bts connection 0 oml");
	f_sleep(2.0);

	f_init();

	timer T := 5.0;
	T.start;
	alt {
	[] RSL_CCHAN.receive(tr_RSL_UD(tr_RSL_RACH_LOAD_IND(tr_rach_slots_per_interval, 0, 0))) {
		setverdict(pass);
		repeat;
		}
	[] RSL_CCHAN.receive(tr_RSL_UD(tr_RSL_RACH_LOAD_IND(?, ?, ?))) -> value rx_ud {
		setverdict(fail, "Unexpected RACH LOAD IND: ", rx_ud);
		repeat;
		}
	[] RSL_CCHAN.receive {
		repeat;
		}
	[] T.timeout { }
	}

	f_vty_load_ind_thresh(10);
	Misc_Helpers.f_shutdown(__BFILE__, __LINE__);
}

/* Expect no RACH load indications on an idle BTS that has just started up (default threshold 10%) */
testcase TC_rach_load_idle_below_thresh() runs on test_CT {
	var ASP_RSL_Unitdata rx_ud;

	f_init_vty_bsc();
	f_init();

	timer T := 5.0;
	T.start;
	alt {
	[] RSL_CCHAN.receive(tr_RSL_UD(tr_RSL_RACH_LOAD_IND(?, ?, ?))) -> value rx_ud {
		setverdict(fail, "Unexpected RACH LOAD IND: ", rx_ud);
		repeat;
		}
	[] RSL_CCHAN.receive {
		repeat;
		}
	[] T.timeout {
		setverdict(pass);
		}
	}

	Misc_Helpers.f_shutdown(__BFILE__, __LINE__);
}

/* Expect 0 RACH load on an idle BTS that has just started up */
testcase TC_rach_load_count() runs on test_CT {
	var ASP_RSL_Unitdata rx_ud;
	var integer load_access_count := 0;

	f_init_vty_bsc();
	/* send load indications even at 0% load */
	f_vty_load_ind_thresh(0);
	f_vty_transceive(BSCVTY, "drop bts connection 0 oml");
	f_sleep(2.0);
	f_init();

	f_init_l1ctl();
	f_sleep(1.0);
	f_l1_tune(L1CTL);

	var GsmFrameNumber fn_last := 0;
	for (var integer i := 0; i < 1000; i := i+1) {
		var OCT1 ra := f_rnd_ra_cs();
		var GsmFrameNumber fn := f_L1CTL_RACH(L1CTL, oct2int(ra));
		if (fn == fn_last) {
			Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, "Two RACH in same FN?!?");
		}
		fn_last := fn;
	}

	timer T := 5.0;
	T.start;
	alt {
	[] RSL_CCHAN.receive(tr_RSL_UD(tr_RSL_RACH_LOAD_IND(tr_rach_slots_per_interval, ?, ?)))
										-> value rx_ud {
		var RSL_IE_Body ie;
		f_rsl_find_ie(rx_ud.rsl, RSL_IE_RACH_LOAD, ie);
		load_access_count := load_access_count + ie.rach_load.access_count;
		if (ie.rach_load.busy_count < ie.rach_load.access_count) {
			setverdict(fail, "Access count cannot be < Busy count");
		}
		repeat;
		}
	[] RSL_CCHAN.receive(tr_RSL_UD(tr_RSL_RACH_LOAD_IND(?, ?, ?))) -> value rx_ud {
		setverdict(fail, "Unexpected RACH LOAD IND: ", rx_ud);
		repeat;
		}
	[] RSL_CCHAN.receive {
		repeat;
		}
	[] T.timeout { }
	}
	if (load_access_count == 1000) {
		setverdict(pass);
	} else {
		setverdict(fail, "Load reports state ", load_access_count, " RACH, but we sent 1000");
	}

	f_vty_load_ind_thresh(10);
	Misc_Helpers.f_shutdown(__BFILE__, __LINE__);
}

private function f_rach_toffs(int16_t toffs256, boolean expect_pass) runs on test_CT {
	var TrxcMessage ret;
	/* tell fake_trx to use a given timing offset for all bursts */
	ret := f_TRXC_transceive(BTS_TRXC, g_bts_trxc_conn_id, valueof(ts_TRXC_FAKE_TIMING(toffs256)));
	f_sleep(0.5);

	/* Transmit RACH request + wait for confirmation */
	var OCT1 ra := f_rnd_ra_cs();
	var GsmFrameNumber fn := f_L1CTL_RACH(L1CTL, oct2int(ra));

	/* Check for expected result */
	timer T := 1.5;
	T.start;
	alt {
	[expect_pass] RSL_CCHAN.receive(tr_RSL_UD(tr_RSL_CHAN_RQD(ra, fn))) {
		setverdict(pass);
		}
	[not expect_pass] RSL_CCHAN.receive(tr_RSL_UD(tr_RSL_CHAN_RQD(ra, fn))) {
		Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, log2str("RACH passed but was expected to be dropped: ", toffs256));
		}
	[] RSL_CCHAN.receive { repeat; }
	[not expect_pass] T.timeout {
		setverdict(pass);
		}
	[expect_pass] T.timeout {
		Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, log2str("Timeout waiting for CHAN RQD: FN=", fn, " RA=", ra));
		}
	}
}

/* Test if dropping of RACH Based on NM_ATT_MAX_TA works */
testcase TC_rach_max_ta() runs on test_CT {
	f_init();
	f_init_l1ctl();
	f_l1_tune(L1CTL);
	f_sleep(1.0);

	/* default max-ta is 63 (full range of GSM timing advance */

	/* We allow early arrival up to 2 symbols */
	f_rach_toffs(-1*256, true);
	f_rach_toffs(-2*256, true);
	f_rach_toffs(-10*256, false);

	/* 0 / 32 / 63 bits is legal / permitted */
	f_rach_toffs(0, true);
	f_rach_toffs(32*256, true);
	f_rach_toffs(63*256, true);

	/* more than 63 bits is not legal / permitted */
	f_rach_toffs(64*256, false);
	f_rach_toffs(127*256, false);
	Misc_Helpers.f_shutdown(__BFILE__, __LINE__);
}

function f_TC_ho_rach(charstring id) runs on ConnHdlr {
	var GsmFrameNumber fn;
	var RSL_Message rm;

	f_l1_tune(L1CTL);
	RSL.clear;

	/* Generate a random Handover Reference */
	var integer ho_ref := oct2int(f_rnd_octstring(1));

	/* Handover Reference IE (see 3GPP TS 48.058, 9.3.9) */
	var RSL_IE ho_ref_ie := valueof(t_RSL_IE(RSL_IE_HANDO_REF,
					RSL_IE_Body:{ handover_ref := ho_ref }));

	/* Activate a channel on the BTS side (no encryption) */
	f_rsl_chan_act(g_pars.chan_mode, more_ies := { ho_ref_ie },
		       act_type := t_RSL_IE_ActType_HO_SYNC);

	/* Switch the MS side (e.g. trxcon) to a dedicated channel without
	 * waiting for Immediate Assignment and sending Access Burst */
	f_L1CTL_DM_EST_REQ(L1CTL, { false, mp_trx0_arfcn }, g_pars.chan_nr, 7);

	/* Send handover Access Burst */
	fn := f_L1CTL_RACH(L1CTL, ho_ref, chan_nr := g_pars.chan_nr);

	/* TODO: test mismatching Handover Reference, and missing IE */

	/* Wait for handover detection */
	timer T := 3.0;
	T.start;
	alt {
	[] RSL.receive(tr_RSL_HANDO_DET(g_pars.chan_nr)) -> value rm {
		log("Handover RACH has been detected: ", rm);
		setverdict(pass);
		}
	[] RSL.receive(tr_RSL_CHAN_RQD(?, ?, ?, ?)) -> value rm {
		Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail,
			log2str("RSL_CHAN_RQD was not expected: ", rm));
		}
	[] RSL.receive { repeat; }
	[] T.timeout {
		Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail,
			log2str("Timeout waiting for handover RACH: FN=", fn, " RA=", ho_ref));
		}
	}

	/* Release the channel */
	f_rsl_chan_deact();
	f_L1CTL_DM_REL_REQ(L1CTL, g_chan_nr);
}

/* Test handover RACH detection */
testcase TC_ho_rach() runs on test_CT {
	var ConnHdlrPars pars;
	var ConnHdlr vc_conn;

	f_init();

	for (var integer i := 0; i < sizeof(g_AllChannels); i := i + 1) {
		pars := valueof(t_Pars(g_AllChannels[i], ts_RSL_ChanMode_SIGN));
		log(testcasename(), ": Starting for ", g_AllChannels[i]);
		vc_conn := f_start_handler(refers(f_TC_ho_rach), pars);
		vc_conn.done;
	}

	/* TODO: do the above in parallel, rather than sequentially? */
	Misc_Helpers.f_shutdown(__BFILE__, __LINE__);
}

/***********************************************************************
 * Measurement Processing / Reporting
 ***********************************************************************/

template LapdmAddressField ts_LapdmAddr(LapdmSapi sapi, boolean c_r) := {
	spare := '0'B,
	lpd := 0,
	sapi := sapi,
	c_r := c_r,
	ea := true
}

template LapdmFrameAB ts_LAPDm_AB(LapdmSapi sapi, boolean c_r, boolean p, octetstring pl) := {
	addr := ts_LapdmAddr(sapi, c_r),
	ctrl := ts_LapdmCtrlUI(p),
	len := 0, /* overwritten */
	m := false,
	el := 1,
	payload := pl
}

/* handle incoming downlink SACCH and respond with uplink SACCH (meas res) */
altstep as_l1_sacch() runs on ConnHdlr {
	var L1ctlDlMessage l1_dl;
	[] L1CTL.receive(tr_L1CTL_DATA_IND(g_chan_nr, tr_RslLinkID_SACCH(?))) -> value l1_dl {
		log("SACCH received: ", l1_dl.payload.data_ind.payload);
		var GsmRrL3Message meas_rep := valueof(ts_MEAS_REP(true, mp_rxlev_exp, mp_rxlev_exp, 0, 0, omit));
		var LapdmFrameAB lb := valueof(ts_LAPDm_AB(0, false, false, enc_GsmRrL3Message(meas_rep)));
		log("LAPDm: ", lb);

		var template (value) SacchL1Header l1h := ts_SacchL1Header(
			g_pars.l1_pars.ms_power_level, false,
			g_pars.l1_pars.ms_actual_ta);

		/* TODO: we can use an extension of TTCN-3 for that, i.e. PADDING('2B'O) */
		var octetstring l2 := f_pad_oct(enc_LapdmFrameAB(lb), 21, '2B'O);

		log("Sending Measurement Report: ", l1h, l2);
		L1CTL.send(ts_L1CTL_DATA_REQ_SACCH(g_chan_nr, ts_RslLinkID_SACCH(0), l1h, l2));
		repeat;
		}
}

altstep as_l1_dcch() runs on ConnHdlr {
	var L1ctlDlMessage l1_dl;
	[] L1CTL.receive(tr_L1CTL_DATA_IND(g_chan_nr, tr_RslLinkID_DCCH(?))) -> value l1_dl {
		log("DCCH received: ", l1_dl.payload.data_ind.payload);
		var octetstring pl := '010301'O;
		L1CTL.send(ts_L1CTL_DATA_REQ(g_chan_nr, ts_RslLinkID_DCCH(0),
			f_pad_oct(pl, 23, '2B'O)));
		repeat;
		}
}

type record MeasElem {
	uint6_t rxlev,
	uint3_t rxqual
}

type record MeasElemFS {
	MeasElem full,
	MeasElem sub
}

type record ConnL1Pars {
	boolean dtx_enabled,
	boolean toa256_enabled,
	MeasElemFS meas_ul,
	int16_t timing_offset_256syms,
	uint5_t bs_power_level,
	uint5_t ms_power_level,
	uint8_t ms_actual_ta
}

/* Convert tiing offset from 1/256th symbol to RSL Timing Offset */
private function toffs256s_to_rsl(int16_t toffs256s) return uint8_t {
	return 63 + (toffs256s/256);
}

private function f_max(integer a, integer b) return integer {
	if (a > b) {
		return a;
	} else {
		return b;
	}
}

private function f_min(integer a, integer b) return integer {
	if (a < b) {
		return a;
	} else {
		return b;
	}
}

/* compute negative tolerance val-tolerance, ensure >= min */
private function f_tolerance_neg(integer val, integer min, integer tolerance) return integer {
	val := val - tolerance;
	return f_max(val, min);
}

/* compute positive tolerance val+tolerance, ensure <= max */
private function f_tolerance_pos(integer val, integer max, integer tolerance) return integer {
	val := val + tolerance;
	return f_min(val, max);
}

/* return a template of (val-tolerance .. val+tolerance) ensuring it is within (min .. max) */
private function f_tolerance(integer val, integer min, integer max, integer tolerance)
return template integer {
	var template integer ret;
	ret := (f_tolerance_neg(val, min, tolerance) .. f_tolerance_pos(val, max, tolerance));
	return ret;
}


/* build a template for matching measurement results against */
private function f_build_meas_res_tmpl() runs on ConnHdlr return template RSL_Message {
	var ConnL1Pars l1p := g_pars.l1_pars;
	var template RSL_IE_UplinkMeas ul_meas := {
		len := 3,
		rfu := '0'B,
		dtx_d := l1p.dtx_enabled,
		rxlev_f_u := f_tolerance(l1p.meas_ul.full.rxlev, 0, 63, mp_tolerance_rxlev),
		reserved1 := '00'B,
		rxlev_s_u := f_tolerance(l1p.meas_ul.sub.rxlev, 0, 63, mp_tolerance_rxlev),
		reserved2 := '00'B,
		rxq_f_u := f_tolerance(l1p.meas_ul.full.rxqual, 0, 7, mp_tolerance_rxqual),
		rxq_s_u := f_tolerance(l1p.meas_ul.sub.rxqual, 0, 7, mp_tolerance_rxqual),
		supp_meas_info := omit
	};
	if (l1p.toa256_enabled) {
		ul_meas.len := (3+8);
		ul_meas.supp_meas_info := {
			toa256_mean := f_tolerance(l1p.timing_offset_256syms, -63*256, 192*256, mp_tolerance_timing_offset_256syms),
			toa256_min := ?,
			toa256_max := ?,
			toa256_std_dev := ?
		}
	}
	var template RSL_IE_BS_Power bs_power := {
		reserved := 0,
		epc := false,
		fpc := false,
		power_level := l1p.bs_power_level
	};
	var template RSL_IE_L1Info l1_info := {
		ms_power_lvl := l1p.ms_power_level,
		fpc := false,
		reserved := 0,
		actual_ta := f_tolerance(l1p.ms_actual_ta, 0, 63, mp_tolerance_timing_offset_256syms/256)
	};
	var uint8_t offs := toffs256s_to_rsl(l1p.timing_offset_256syms);
	var template uint8_t t_toffs := f_tolerance(offs, 0, 255, mp_tolerance_timing_offset_256syms/256);
	return tr_RSL_MEAS_RES_OSMO(g_chan_nr, g_next_meas_res_nr, ul_meas, bs_power, l1_info,
				    ?, t_toffs);
}

/* build a template for matching measurement results that do not contain any
 * MS related measurement (l1_info, l3_info and ms timing offset). */
private function f_build_meas_res_tmpl_empty() runs on ConnHdlr return template RSL_Message {
	var ConnL1Pars l1p := g_pars.l1_pars;
	var template RSL_IE_UplinkMeas ul_meas := {
		len := 3,
		rfu := '0'B,
		dtx_d := l1p.dtx_enabled,
		rxlev_f_u := ?,
		reserved1 := '00'B,
		rxlev_s_u := ?,
		reserved2 := '00'B,
		rxq_f_u := ?,
		rxq_s_u := ?,
		supp_meas_info := omit
	};
	if (l1p.toa256_enabled) {
		ul_meas.len := (3+8);
		ul_meas.supp_meas_info := {
			toa256_mean := f_tolerance(l1p.timing_offset_256syms, -63*256, 192*256, mp_tolerance_timing_offset_256syms),
			toa256_min := ?,
			toa256_max := ?,
			toa256_std_dev := ?
		}
	}
	var template RSL_IE_BS_Power bs_power := {
		reserved := 0,
		epc := false,
		fpc := false,
		power_level := l1p.bs_power_level
	};

	return tr_RSL_MEAS_RES_EMPTY(g_chan_nr, g_next_meas_res_nr, ul_meas, bs_power);
}

/* verify we regularly receive measurement reports with incrementing numbers */
altstep as_meas_res(boolean verify_meas := true) runs on ConnHdlr {
	var RSL_Message rsl;
	var boolean chan_est := false;

	[not verify_meas] RSL.receive(tr_RSL_MEAS_RES(?)) { repeat; }

	/* Receive osmocom specific measurement reports. This is the normal
	 * case. Here we verify that the measurement reports we sent are
	 * comming back as we expect them. */
	[] RSL.receive(f_build_meas_res_tmpl()) -> value rsl {
		/* increment counter of next to-be-expected meas rep */
		g_next_meas_res_nr := (g_next_meas_res_nr + 1) mod 256;
		/* Re-start the timer expecting the next MEAS RES */
		f_timer_safe_restart(g_Tmeas_exp);

		/* The following two cases may only happen in the beginning
		 * of the channel establishment phase. Once we have received
		 * the "our" measurement report the first time, the channel
		 * is established and empty or hardcoded TRXCON reports must
		 * not occur anymore. */
		chan_est := true;

		repeat;
		}

	/* When the BTS has established the channel, the MS might need slightly
	 * more time to establish the channel and actually start sending. The
	 * result is then a measurement report that just lacks the measurement
	 * information of the MS. This is normal and we tolerate this behavior. */
	[chan_est == false] RSL.receive(f_build_meas_res_tmpl_empty()) -> value rsl {
		/* increment counter of next to-be-expected meas rep */
		g_next_meas_res_nr := (g_next_meas_res_nr + 1) mod 256;
		/* Re-start the timer expecting the next MEAS RES */
		f_timer_safe_restart(g_Tmeas_exp);
		repeat;
		}

	/* Due to the TDMA nature of GSM, TRXCON implements a way to emit dummy
	 * measurements if the TTCN3 side does not supply measurement input in
	 * time. In those cases TRXCON will either use a cached measurement
	 * report or a hardcoded one. If TRXCON picks the hardcoded measurement
	 * report the templates above will not match. We tolerate this
	 * behavior, but only once. */
	[chan_est == false] RSL.receive(tr_RSL_MEAS_RES(g_chan_nr, g_next_meas_res_nr)) -> value rsl {
		/* increment counter of next to-be-expected meas rep */
		g_next_meas_res_nr := (g_next_meas_res_nr + 1) mod 256;
		if (g_first_meas_res) {
			g_first_meas_res := false;
			repeat;
		} else {
			Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, log2str("Received unspecific MEAS RES ", rsl));
		}
		}
	[] RSL.receive(tr_RSL_MEAS_RES(?)) -> value rsl {
		Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, log2str("Received unexpected MEAS RES ", rsl));
		}
	[g_Tmeas_exp.running] g_Tmeas_exp.timeout {
		Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, "Didn't receive expected measurement result")
		}
}

private function f_alg_id_to_l1ctl(RSL_AlgId rsl_alg_id) return uint8_t {
	select (rsl_alg_id) {
	case (RSL_ALG_ID_A5_0) { return 0; }
	case (RSL_ALG_ID_A5_1) { return 1; }
	case (RSL_ALG_ID_A5_2) { return 2; }
	case (RSL_ALG_ID_A5_3) { return 3; }
	case (RSL_ALG_ID_A5_4) { return 4; }
	case (RSL_ALG_ID_A5_5) { return 5; }
	case (RSL_ALG_ID_A5_6) { return 6; }
	case (RSL_ALG_ID_A5_7) { return 7; }
	case else {
		Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, "Unknwon Algorithm ID");
		/* Make compiler happy by calling mtc.stop here. It is already
		 * called in f_shutdown */
		mtc.stop;
		}
	}
}

private function f_alg_id_to_l3(RSL_AlgId rsl_alg_id) return BIT3 {
	select (rsl_alg_id) {
	case (RSL_ALG_ID_A5_1) { return '000'B; }
	case (RSL_ALG_ID_A5_2) { return '001'B; }
	case (RSL_ALG_ID_A5_3) { return '010'B; }
	case (RSL_ALG_ID_A5_4) { return '011'B; }
	case (RSL_ALG_ID_A5_5) { return '100'B; }
	case (RSL_ALG_ID_A5_6) { return '101'B; }
	case (RSL_ALG_ID_A5_7) { return '110'B; }
	case else {
		Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, "Unknwon Algorithm ID");
		/* Make compiler happy by calling mtc.stop here. It is already
		 * called in f_shutdown */
		mtc.stop;
		}
	}
}

/* Send RACH request through l1CTL and wait for ChanReq on RSL BST->BSC */
private function f_rach_req_wait_chan_rqd(integer ra) runs on ConnHdlr return GsmFrameNumber {
	var GsmFrameNumber fn;
	timer T := 8.0;

	/* advertise to RSL Emulation that we expect to receive confirmation from RACH */
	RSL.send(ts_RSLDC_ChanRqd_anyFN(int2oct(ra,1)));

	f_L1CTL_PARAM(L1CTL, g_pars.l1_pars.ms_actual_ta, g_pars.l1_pars.ms_power_level);
	/* Send the actual RACH */
	fn := f_L1CTL_RACH(L1CTL, ra);

	T.start;
	alt {
	[] RSL.receive(tr_RSL_CHAN_RQD(int2oct(ra,1), fn)) { setverdict(pass, "Received CHAN-RQD from RACH REQ") }
	[] T.timeout {
		Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, log2str("Timeout waiting for CHAN-RQD from RACH REQ <", ra, ", ", fn, ">"));
		}
	}
	T.stop
	return fn;
}

/* Establish dedicated channel: L1CTL + RSL side */
private function f_est_dchan(boolean encr_enable := false, RSL_IE_List more_ies := {}) runs on ConnHdlr {
	var GsmFrameNumber fn;
	var ImmediateAssignment imm_ass;
	var integer ra := 23;

	/* Send RACH request and wait for ChanReq */
	fn := f_rach_req_wait_chan_rqd(ra);

	/* Activate channel on BTS side */
	f_rsl_chan_act(g_pars.chan_mode, encr_enable, more_ies);

	/* Send IMM.ASS via CCHAN */
	var ChannelDescription ch_desc := {
		chan_nr := g_pars.chan_nr,
		tsc := 7,
		h := false,
		arfcn := mp_trx0_arfcn,
		maio_hsn := omit
	};
	var MobileAllocation ma := {
		len := 0,
		ma := ''B
	};
	var GsmRrMessage rr_msg := valueof(ts_IMM_ASS(ra, fn, 0, ch_desc, ma));
	RSL.send(ts_RSL_IMM_ASSIGN(enc_GsmRrMessage(rr_msg)));

	/* receive IMM.ASS on MS side */
	var ImmediateAssignment ia_um;
	ia_um := f_L1CTL_WAIT_IMM_ASS(L1CTL, ra, fn);
	/* enable dedicated mode */
	f_L1CTL_DM_EST_REQ_IA(L1CTL, ia_um);
	/* enable encryption, if requested */
	if (encr_enable) {
		var uint8_t alg_id := f_alg_id_to_l1ctl(g_pars.encr.alg_id);
		f_L1CTL_CRYPTO_REQ(L1CTL, g_pars.chan_nr, alg_id, g_pars.encr.key);
	}

	g_first_meas_res := true;
}

/* establish DChan, verify existance + contents of measurement reports */
function f_TC_meas_res_periodic(charstring id) runs on ConnHdlr {
	f_l1_tune(L1CTL);
	RSL.clear;

	if (mp_bts_trxc_port != -1) {
		f_trxc_fake_rssi(rxlev2dbm(mp_ul_rxlev_exp));
		f_trxc_fake_toffs256(g_pars.l1_pars.timing_offset_256syms);
	}

	f_est_dchan();

	/* run for a number of seconds, send SACCH + FACCH from MS side and verify
	 * RSL measurement reports on Abis side */
	timer T := 8.0;
	T.start;
	alt {
	[] as_l1_sacch();
	[] as_meas_res();
	[] as_l1_dcch();
	[] L1CTL.receive { repeat; }
	[g_Tmeas_exp.running] T.timeout {
		/* as_meas_res() would have done Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail) in case
		 * of any earlier errors, so if we reach this timeout, we're good */
		setverdict(pass);
		}
	[] T.timeout {
		Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, "No MEAS RES received at all");
		}
	}
	f_rsl_chan_deact();
	f_L1CTL_DM_REL_REQ(L1CTL, g_chan_nr);
}

function f_check_meas_bs_power_level(integer level) runs on ConnHdlr {
	timer T := 8.0;
	T.start;
	var RSL_Message rsl;
	alt {
	[] as_l1_sacch();
	[] L1CTL.receive { repeat; }
	[] RSL.receive(tr_RSL_MEAS_RES(g_chan_nr, ?, ?, ?)) -> value rsl {
		if (rsl.ies[3].body.bs_power.power_level == level) {
			setverdict(pass)
		} else {
			Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, log2str("Received wrong BS power level in MEAS RES ", rsl));
		}
		}
	[] T.timeout {
		Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, "No MEAS RES received at all");
		}
	}
}

/* see if the rsl meas res contains our expeced bs power level
bs power set during assignment */
function f_TC_rsl_bs_pwr_static_ass(charstring id) runs on ConnHdlr {
	f_l1_tune(L1CTL);
	RSL.clear;

	if (mp_bts_trxc_port != -1) {
		f_trxc_fake_rssi(rxlev2dbm(mp_ul_rxlev_exp));
		f_trxc_fake_toffs256(g_pars.l1_pars.timing_offset_256syms);
	}

	var uint5_t pwr_var := 1;
	var template (value) RSL_IE_BS_Power bs_power := ts_RSL_IE_BS_Power(pwr_var);
	var template (value) RSL_IE pwr := t_RSL_IE(RSL_IE_BS_POWER, RSL_IE_Body:{bs_power := bs_power});

	f_est_dchan(more_ies :={valueof(pwr)});

	f_check_meas_bs_power_level(pwr_var);

	f_rsl_chan_deact();
	f_L1CTL_DM_REL_REQ(L1CTL, g_chan_nr);
}

/* see if the rsl meas res contains our expeced bs power level
bs power set after assignment */
function f_TC_rsl_bs_pwr_static_power_control(charstring id) runs on ConnHdlr {
	f_l1_tune(L1CTL);
	RSL.clear;

	if (mp_bts_trxc_port != -1) {
		f_trxc_fake_rssi(rxlev2dbm(mp_ul_rxlev_exp));
		f_trxc_fake_toffs256(g_pars.l1_pars.timing_offset_256syms);
	}

	var uint5_t pwr_var := 1;
	var template (value) RSL_IE_BS_Power bs_power := ts_RSL_IE_BS_Power(pwr_var);

	f_est_dchan();

	RSL.send(ts_RSL_BS_PWR_CTRL(g_chan_nr, bs_power));

	f_check_meas_bs_power_level(pwr_var);

	f_rsl_chan_deact();
	f_L1CTL_DM_REL_REQ(L1CTL, g_chan_nr);
}

testcase TC_rsl_bs_pwr_static_ass() runs on test_CT {
	var ConnHdlr vc_conn;
	var ConnHdlrPars pars;
	f_init();
	for (var integer tn := 1; tn <= 4; tn := tn+1) {
		pars := valueof(t_Pars(t_RslChanNr_Bm(tn), ts_RSL_ChanMode_SIGN));
		vc_conn := f_start_handler(refers(f_TC_rsl_bs_pwr_static_ass), pars,
					   pcu_comp := false, trxc_comp := true);
		vc_conn.done;
	}
	Misc_Helpers.f_shutdown(__BFILE__, __LINE__);
}

testcase TC_rsl_bs_pwr_static_power_control() runs on test_CT {
	var ConnHdlr vc_conn;
	var ConnHdlrPars pars;
	f_init();
	for (var integer tn := 1; tn <= 4; tn := tn+1) {
		pars := valueof(t_Pars(t_RslChanNr_Bm(tn), ts_RSL_ChanMode_SIGN));
		vc_conn := f_start_handler(refers(f_TC_rsl_bs_pwr_static_power_control), pars,
					   pcu_comp := false, trxc_comp := true);
		vc_conn.done;
	}
	Misc_Helpers.f_shutdown(__BFILE__, __LINE__);
}

/* target level -100, first rssi -90, ms power 7, expected increase to 7+6 within 6 seconds,
second rssi -110, ms power 7+6, expected decrease to 7 within 6 seconds,
These power levels are valid for all bands and require no special handling */
function f_TC_rsl_ms_pwr_dyn_ass_updown(charstring id) runs on ConnHdlr {
	var uint5_t pwr_var := 7;
	var L1ctlDlMessage l1_dl;

	f_trxc_fake_rssi(rxlev2dbm(10));
	f_l1_tune(L1CTL);
	RSL.clear;

	var RSL_IE_List addl_ies;
	var template (value)  RSL_IE_MS_Power_Parameters pp := (ts_RSL_IE_MS_Power_Parameters(''O));

	addl_ies := {
		valueof(t_RSL_IE(RSL_IE_MS_POWER, RSL_IE_Body:{ms_power := ts_RSL_IE_MS_Power(pwr_var)})),
		valueof(t_RSL_IE(RSL_IE_MS_POWER_PARAM, RSL_IE_Body:{ms_power_params := pp}))
	};

	/* establish with power parameters */
	f_est_dchan(more_ies := addl_ies);

	/* set a high value to ensure L1 power control level increases */
	f_trxc_fake_rssi(rxlev2dbm(20));

	timer T2 := 6.0;
	T2.start;
	alt {
	[] L1CTL.receive(tr_L1CTL_DATA_IND(g_chan_nr, tr_RslLinkID_SACCH(?))) -> value l1_dl {
		/* Update sent MS power to follow what BTS requests */
		f_L1CTL_PARAM(L1CTL, g_pars.l1_pars.ms_actual_ta, oct2int(l1_dl.payload.data_ind.payload[0]));
		if (oct2int(l1_dl.payload.data_ind.payload[0]) < (pwr_var + 6)) {
			repeat;
		}
		T2.stop;
		}
	[] L1CTL.receive { repeat; }
	[] T2.timeout {
			Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail,
			"Power Level in L1 header has not increased sufficiently");
		}
	}

	/* set a low value to ensure L1 power control level decreases */
	f_trxc_fake_rssi(rxlev2dbm(0));

	timer T4 := 6.0;
	T4.start;
	alt {
	[] L1CTL.receive(tr_L1CTL_DATA_IND(g_chan_nr, tr_RslLinkID_SACCH(?))) -> value l1_dl {
		/* Update sent MS power to follow what BTS requests */
		f_L1CTL_PARAM(L1CTL, g_pars.l1_pars.ms_actual_ta, oct2int(l1_dl.payload.data_ind.payload[0]));
		if (oct2int(l1_dl.payload.data_ind.payload[0]) > pwr_var) {
			repeat;
		}
		T4.stop;
		setverdict(pass, "Power level in L1 decreased/increased as expected");
		}
	[] L1CTL.receive { repeat; }
	[] T4.timeout {
			Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail,
			"Power Level in L1 header has not decreased sufficiently");
		}
	}

	f_rsl_chan_deact();
	f_L1CTL_DM_REL_REQ(L1CTL, g_chan_nr);

}

/* check that we do not exceed the max power */
function f_TC_rsl_ms_pwr_dyn_max(charstring id) runs on ConnHdlr {
	var uint5_t pwr_var := 7;
	var L1ctlDlMessage l1_dl;

	/* set a low value to ensure power increases */
	f_trxc_fake_rssi(rxlev2dbm(10));
	f_l1_tune(L1CTL);
	RSL.clear;

	var RSL_IE_List addl_ies;
	var template (value)  RSL_IE_MS_Power_Parameters pp := (ts_RSL_IE_MS_Power_Parameters(''O));

	addl_ies := {
		valueof(t_RSL_IE(RSL_IE_MS_POWER, RSL_IE_Body:{ms_power := ts_RSL_IE_MS_Power(pwr_var)})),
		valueof(t_RSL_IE(RSL_IE_MS_POWER_PARAM, RSL_IE_Body:{ms_power_params := pp}))
	};

	/* establish with power parameters */
	f_est_dchan(more_ies := addl_ies);

	timer T1 := 10.0;
	T1.start;
	alt {
	[] L1CTL.receive(tr_L1CTL_DATA_IND(g_chan_nr, tr_RslLinkID_SACCH(?))) -> value l1_dl {
		/* Update sent MS power to follow what BTS requests */
		f_L1CTL_PARAM(L1CTL, g_pars.l1_pars.ms_actual_ta, oct2int(l1_dl.payload.data_ind.payload[0]));
		repeat;
		}
	[] L1CTL.receive { repeat; }
	[] T1.timeout {
		if( oct2int(l1_dl.payload.data_ind.payload[0]) != pwr_var){
			setverdict(fail, "Power level in L1 header should not have changed");
		}
		}
	}

	f_rsl_chan_deact();
	f_L1CTL_DM_REL_REQ(L1CTL, g_chan_nr);

}

/* see if we reach the band max power */
function f_TC_rsl_ms_pwr_dyn_up(charstring id) runs on ConnHdlr {
	var L1ctlDlMessage l1_dl;
	var uint5_t pwr_var := 15;
	var uint5_t pwr_max_var := f_get_max_power_from_band();

	/* set a low value to ensure power increases */
	f_trxc_fake_rssi(rxlev2dbm(10));
	f_l1_tune(L1CTL);
	RSL.clear;

	var template (value) RSL_IE_MS_Power ms_power := ts_RSL_IE_MS_Power(pwr_var);
	var template (value) RSL_IE pwr := t_RSL_IE(RSL_IE_MS_POWER, RSL_IE_Body:{ms_power := ms_power});

	/* establish with fixed power level */
	f_est_dchan(more_ies :={valueof(pwr)});

	/* check our initial power level */
	f_wait_for_l1_power_level(pwr_var);

	/* update power param to enable power loop
	48.058 The maximum power to be used is indicated in the BS and MS Power elements respectively. */
	RSL.send(ts_RSL_MS_PWR_CTRL_with_pp(g_chan_nr, pwr_max_var));

	/* wait, then check that our power level was reduced */
	timer T1 := 10.0;
	T1.start;
	alt {
	[] L1CTL.receive(tr_L1CTL_DATA_IND(g_chan_nr, tr_RslLinkID_SACCH(?))) -> value l1_dl {
		/* Update sent MS power to follow what BTS requests */
		f_L1CTL_PARAM(L1CTL, g_pars.l1_pars.ms_actual_ta, oct2int(l1_dl.payload.data_ind.payload[0]));
		repeat;
		}
	[] L1CTL.receive { repeat; }
	[] T1.timeout {
		var int8_t rcv := oct2int(l1_dl.payload.data_ind.payload[0]);
		if( f_power_level_is_highest_dbm(rcv) ){
			setverdict(pass, "Power level in L1 header reduced as expected");
		} else {
			Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail,
			log2str("Power Level in L1 header did not reach the expected value, e:",pwr_max_var," r:",rcv));
		}
		}
	}

	f_rsl_chan_deact();
	f_L1CTL_DM_REL_REQ(L1CTL, g_chan_nr);

}

/* see if we reach the band min power */
function f_TC_rsl_ms_pwr_dyn_down(charstring id) runs on ConnHdlr {
	var L1ctlDlMessage l1_dl;

	/* set a high value to ensure power decreases */
	f_trxc_fake_rssi(rxlev2dbm(50));
	f_l1_tune(L1CTL);
	RSL.clear;

	var uint5_t pwr_var := 5;
	var uint5_t pwr_target_val := 15;

	var template (value) RSL_IE_MS_Power ms_power := ts_RSL_IE_MS_Power(pwr_var);
	var template (value) RSL_IE pwr := t_RSL_IE(RSL_IE_MS_POWER, RSL_IE_Body:{ms_power := ms_power});

	/* establish with fixed power level */
	f_est_dchan(more_ies :={valueof(pwr)});

	/* check our initial power level */
	f_wait_for_l1_power_level(pwr_var);

	/* update power param to enable power loop
	 as per spec the supplied ms power IE should set the max allowed power...*/
	RSL.send(ts_RSL_MS_PWR_CTRL_with_pp(g_chan_nr, pwr_target_val));

	/* wait, then check that our power level was increased */
	timer T1 := 10.0;
	T1.start;
	alt {
	[] L1CTL.receive(tr_L1CTL_DATA_IND(g_chan_nr, tr_RslLinkID_SACCH(?))) -> value l1_dl {
		/* Update sent MS power to follow what BTS requests */
		f_L1CTL_PARAM(L1CTL, g_pars.l1_pars.ms_actual_ta, oct2int(l1_dl.payload.data_ind.payload[0]));
		repeat;
		}
	[] L1CTL.receive { repeat; }
	[] T1.timeout {
		if( f_power_level_is_lowest_dbm(oct2int(l1_dl.payload.data_ind.payload[0])) ){
			setverdict(pass, "Power level in L1 header increased to lowest power value");
		} else {
			Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail,
			"Power level in L1 header NOT increased to lowest power value");
		}
		}
	}

	f_rsl_chan_deact();
	f_L1CTL_DM_REL_REQ(L1CTL, g_chan_nr);

}

/* see if we change the power level without receiving power parameters, which should not happen
rsl chan act WITHOUT power parameters */
function f_TC_rsl_ms_pwr_dyn_active(charstring id) runs on ConnHdlr {
	var L1ctlDlMessage l1_dl;

	/* set a high value to ensure power decreases */
	f_trxc_fake_rssi(rxlev2dbm(50));
	f_l1_tune(L1CTL);
	RSL.clear;

	var uint5_t pwr_var := 5;

	var template (value) RSL_IE_MS_Power ms_power := ts_RSL_IE_MS_Power(pwr_var);
	var template (value) RSL_IE pwr := t_RSL_IE(RSL_IE_MS_POWER, RSL_IE_Body:{ms_power := ms_power});

	/* establish with fixed power level */
	f_est_dchan(more_ies :={valueof(pwr)});

	/* check our initial power level */
	f_wait_for_l1_power_level(pwr_var);

	/* wait, then check that our power level did not change */
	timer T1 := 10.0;
	T1.start;
	alt {
	[] L1CTL.receive(tr_L1CTL_DATA_IND(g_chan_nr, tr_RslLinkID_SACCH(?))) -> value l1_dl {
		if ( oct2int(l1_dl.payload.data_ind.payload[0]) != pwr_var) {
			Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail,
			"BS power control should not be active unless we receive a power parameters IE!");
		}
		repeat;
		}
	[] L1CTL.receive { repeat; }
	[] T1.timeout { setverdict(pass); }
	}

	f_rsl_chan_deact();
	f_L1CTL_DM_REL_REQ(L1CTL, g_chan_nr);

}

/* see if we change the power level without receiving power parameters, which should not happen
ms power control WITHOUT power parameters */
function f_TC_rsl_ms_pwr_dyn_active2(charstring id) runs on ConnHdlr {
	var L1ctlDlMessage l1_dl;

	/* set a high value to ensure power decreases */
	f_trxc_fake_rssi(rxlev2dbm(50));
	f_l1_tune(L1CTL);
	RSL.clear;

	var uint5_t pwr_var := 5;

	var template (value) RSL_IE_MS_Power ms_power := ts_RSL_IE_MS_Power(pwr_var);
	var template (value) RSL_IE pwr := t_RSL_IE(RSL_IE_MS_POWER, RSL_IE_Body:{ms_power := ms_power});

	/* establish with fixed power level */
	f_est_dchan(more_ies :={valueof(pwr)});

	/* check our initial power level */
	f_wait_for_l1_power_level(pwr_var);

	/* pwr control without power params IE, should NOT activate MS power control*/
	RSL.send(ts_RSL_MS_PWR_CTRL(g_chan_nr, ms_power));

	/* wait, then check that our power level did not change */
	timer T1 := 10.0;
	T1.start;
	alt {
	[] L1CTL.receive(tr_L1CTL_DATA_IND(g_chan_nr, tr_RslLinkID_SACCH(?))) -> value l1_dl {
		if ( oct2int(l1_dl.payload.data_ind.payload[0]) != pwr_var) {
			Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail,
			"BS power control should not be active unless we receive a power parameters IE!");
		}
		repeat;
		}
	[] L1CTL.receive { repeat; }
	[] T1.timeout { setverdict(pass); }
	}

	f_rsl_chan_deact();
	f_L1CTL_DM_REL_REQ(L1CTL, g_chan_nr);

}

function f_wait_for_l1_power_level(integer level) runs on ConnHdlr {
	var L1ctlDlMessage l1_dl;
	timer T0 := 10.0;
	T0.start;
	alt {
	[] L1CTL.receive(tr_L1CTL_DATA_IND(g_chan_nr, tr_RslLinkID_SACCH(?))) -> value l1_dl {
		if (not (l1_dl.payload.data_ind.payload[0] == int2oct(level, 1))) {
			Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail,
			"Power level in L1 header != signaled (RSL) power level.");
		}
		}
	[] L1CTL.receive { repeat; }
	[] T0.timeout {
			Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail,
			"Timeout waiting for initial power level");
		}
	}
	T0.stop;
}

private function f_power_level_is_lowest_dbm(integer level) runs on ConnHdlr return boolean  {
	var IntegerRecord min_dbm_level;
	var IntegerRecord max_dbm_level;
	var IntegerRecord x := f_power_from_band(g_pars.bts0_band, min_dbm_level, max_dbm_level);

	for (var integer i := 0; i < sizeof(min_dbm_level); i := i+1) {
		if (min_dbm_level[i] == level) {
			return true;
		}
	}
	return false;
}

private function f_power_level_is_highest_dbm(integer level) runs on ConnHdlr return boolean {
	var IntegerRecord min_dbm_level;
	var IntegerRecord max_dbm_level;
	var IntegerRecord x := f_power_from_band(g_pars.bts0_band, min_dbm_level, max_dbm_level);

	for (var integer i := 0; i < sizeof(max_dbm_level); i := i+1) {
		if (max_dbm_level[i] == level) {
			return true;
		}
	}
	return false;
}

private function f_get_max_power_from_band() runs on ConnHdlr return integer {
	var IntegerRecord min_dbm_level;
	var IntegerRecord max_dbm_level;
	var IntegerRecord x := f_power_from_band(g_pars.bts0_band, min_dbm_level, max_dbm_level);
	return max_dbm_level[0];
}

type charstring BtsBand ("GSM450","GSM480","GSM750","GSM810","GSM850","GSM900","DCS1800","PCS1900");
template charstring BtsBand_allGSM:= pattern "GSM???";
private function f_power_from_band(in BtsBand band, out IntegerRecord min_dbm_level, out IntegerRecord max_dbm_level) return IntegerRecord {
	// 45.005 4.1.1
	var IntegerRecord gsm_power :={31, 30, 29, 28, 27, 26, 25, 24, 23, 22, 21, 20, 19,
	 18, 17, 16, 15, 14, 13, 12, 11, 10, 9, 8, 7, 6, 5, 4, 3,
	 2, 1, 0};
	var IntegerRecord dcs_power :={28, 27, 26, 25, 24, 23, 22, 21, 20, 19, 18, 17, 16, 15,
	 14, 13, 12, 11, 10, 9, 8, 7, 6, 5, 4, 3, 2, 1, 0, 31, 30, 29};
	var IntegerRecord pcs_power :={15, 14, 13, 12, 11, 10, 9, 8, 7, 6, 5, 4, 3, 2, 1, 0, 31, 30};
	var IntegerRecord rv;

	select(band){
	case (BtsBand_allGSM){
		rv := gsm_power;
		min_dbm_level := {31, 30, 29, 28, 27, 26, 25, 24, 23, 22, 21, 20, 19} ;
		max_dbm_level := {2, 1, 0};
	}
	case("DCS1800"){
		rv := dcs_power;
		min_dbm_level := {28, 27, 26, 25, 24, 23, 22, 21, 20, 19, 18, 17, 16, 15};
		max_dbm_level := {0, 29}; // let's cheat here, assume MS_TXPWR_MAX_CCH might be being broadcast, so maybe no 29,30,31
	}
	case("PCS1900"){
		rv := pcs_power;
		min_dbm_level := {15};
		max_dbm_level := {30};
	}
	}

	return rv;
}

private function f_vty_get_bts0_band() runs on test_CT return BtsBand {
	return f_vty_transceive_match_regex(BTSVTY, "show bts 0", "BTS 0 is of \w+ type in band (\w+),*", 0);
}

testcase TC_rsl_ms_pwr_dyn_ass_updown() runs on test_CT {
	var ConnHdlr vc_conn;
	var ConnHdlrPars pars;
	f_init();
	f_vty_config(BTSVTY, "phy 0", "osmotrx ms-power-loop -100");
	for (var integer tn := 1; tn <= 1; tn := tn+1) {
		pars := valueof(t_Pars(t_RslChanNr_Bm(tn), ts_RSL_ChanMode_SIGN));
		pars.bts0_band := f_vty_get_bts0_band();
		vc_conn := f_start_handler(refers(f_TC_rsl_ms_pwr_dyn_ass_updown), pars, trxc_comp := true);
		vc_conn.done;
	}
	f_vty_config(BTSVTY, "phy 0", "no osmotrx ms-power-loop");
	Misc_Helpers.f_shutdown(__BFILE__, __LINE__);
}

testcase TC_rsl_ms_pwr_dyn_up() runs on test_CT {
	var ConnHdlr vc_conn;
	var ConnHdlrPars pars;
	f_init();
	f_vty_config(BTSVTY, "phy 0", "osmotrx ms-power-loop -10");
	for (var integer tn := 1; tn <= 1; tn := tn+1) {
		pars := valueof(t_Pars(t_RslChanNr_Bm(tn), ts_RSL_ChanMode_SIGN));
		pars.bts0_band := f_vty_get_bts0_band();
		vc_conn := f_start_handler(refers(f_TC_rsl_ms_pwr_dyn_up), pars, trxc_comp := true);
		vc_conn.done;
	}
	f_vty_config(BTSVTY, "phy 0", "no osmotrx ms-power-loop");
	Misc_Helpers.f_shutdown(__BFILE__, __LINE__);
}

testcase TC_rsl_ms_pwr_dyn_max() runs on test_CT {
	var ConnHdlr vc_conn;
	var ConnHdlrPars pars;
	f_init();
	f_vty_config(BTSVTY, "phy 0", "osmotrx ms-power-loop -10");
	for (var integer tn := 1; tn <= 1; tn := tn+1) {
		pars := valueof(t_Pars(t_RslChanNr_Bm(tn), ts_RSL_ChanMode_SIGN));
		pars.bts0_band := f_vty_get_bts0_band();
		vc_conn := f_start_handler(refers(f_TC_rsl_ms_pwr_dyn_max), pars, trxc_comp := true);
		vc_conn.done;
	}
	f_vty_config(BTSVTY, "phy 0", "no osmotrx ms-power-loop");
	Misc_Helpers.f_shutdown(__BFILE__, __LINE__);
}

testcase TC_rsl_ms_pwr_dyn_down() runs on test_CT {
	var ConnHdlr vc_conn;
	var ConnHdlrPars pars;
	f_init();
	f_vty_config(BTSVTY, "phy 0", "osmotrx ms-power-loop -100");
	for (var integer tn := 1; tn <= 1; tn := tn+1) {
		pars := valueof(t_Pars(t_RslChanNr_Bm(tn), ts_RSL_ChanMode_SIGN));
		pars.bts0_band := f_vty_get_bts0_band();
		vc_conn := f_start_handler(refers(f_TC_rsl_ms_pwr_dyn_down), pars, trxc_comp := true);
		vc_conn.done;
	}
	f_vty_config(BTSVTY, "phy 0", "no osmotrx ms-power-loop");
	Misc_Helpers.f_shutdown(__BFILE__, __LINE__);
}

testcase TC_rsl_ms_pwr_dyn_active() runs on test_CT {
	var ConnHdlr vc_conn;
	var ConnHdlrPars pars;
	f_init();
	f_vty_config(BTSVTY, "phy 0", "osmotrx ms-power-loop -100");
	for (var integer tn := 1; tn <= 1; tn := tn+1) {
		pars := valueof(t_Pars(t_RslChanNr_Bm(tn), ts_RSL_ChanMode_SIGN));
		pars.bts0_band := f_vty_get_bts0_band();
		vc_conn := f_start_handler(refers(f_TC_rsl_ms_pwr_dyn_active), pars, trxc_comp := true);
		vc_conn.done;
	}
	f_vty_config(BTSVTY, "phy 0", "no osmotrx ms-power-loop");
	Misc_Helpers.f_shutdown(__BFILE__, __LINE__);
}

testcase TC_rsl_ms_pwr_dyn_active2() runs on test_CT {
	var ConnHdlr vc_conn;
	var ConnHdlrPars pars;
	f_init();
	f_vty_config(BTSVTY, "phy 0", "osmotrx ms-power-loop -100");
	for (var integer tn := 1; tn <= 1; tn := tn+1) {
		pars := valueof(t_Pars(t_RslChanNr_Bm(tn), ts_RSL_ChanMode_SIGN));
		pars.bts0_band := f_vty_get_bts0_band();
		vc_conn := f_start_handler(refers(f_TC_rsl_ms_pwr_dyn_active2), pars, trxc_comp := true);
		vc_conn.done;
	}
	f_vty_config(BTSVTY, "phy 0", "no osmotrx ms-power-loop");
	Misc_Helpers.f_shutdown(__BFILE__, __LINE__);
}

testcase TC_meas_res_sign_tchf() runs on test_CT {
	var ConnHdlr vc_conn;
	var ConnHdlrPars pars;
	f_init();
	for (var integer tn := 1; tn <= 4; tn := tn+1) {
		pars := valueof(t_Pars(t_RslChanNr_Bm(tn), ts_RSL_ChanMode_SIGN));
		vc_conn := f_start_handler(refers(f_TC_meas_res_periodic), pars,
					   pcu_comp := false, trxc_comp := true);
		vc_conn.done;
	}
	Misc_Helpers.f_shutdown(__BFILE__, __LINE__);
}
testcase TC_meas_res_sign_tchh() runs on test_CT {
	var ConnHdlr vc_conn;
	var ConnHdlrPars pars;
	f_init();
	for (var integer ss := 0; ss <= 1; ss := ss+1) {
		pars := valueof(t_Pars(t_RslChanNr_Lm(5, ss), ts_RSL_ChanMode_SIGN));
		vc_conn := f_start_handler(refers(f_TC_meas_res_periodic), pars,
					   pcu_comp := false, trxc_comp := true);
		vc_conn.done;
	}
	Misc_Helpers.f_shutdown(__BFILE__, __LINE__);
}
testcase TC_meas_res_sign_sdcch4() runs on test_CT {
	var ConnHdlr vc_conn;
	var ConnHdlrPars pars;
	f_init();
	for (var integer ss := 0; ss <= 3; ss := ss+1) {
		pars := valueof(t_Pars(t_RslChanNr_SDCCH4(0, ss), ts_RSL_ChanMode_SIGN));
		vc_conn := f_start_handler(refers(f_TC_meas_res_periodic), pars,
					   pcu_comp := false, trxc_comp := true);
		vc_conn.done;
	}
	Misc_Helpers.f_shutdown(__BFILE__, __LINE__);
}
testcase TC_meas_res_sign_sdcch8() runs on test_CT {
	var ConnHdlr vc_conn;
	var ConnHdlrPars pars;
	f_init();
	for (var integer ss := 0; ss <= 7; ss := ss+1) {
		pars := valueof(t_Pars(t_RslChanNr_SDCCH8(6, ss), ts_RSL_ChanMode_SIGN));
		vc_conn := f_start_handler(refers(f_TC_meas_res_periodic), pars,
					   pcu_comp := false, trxc_comp := true);
		vc_conn.done;
	}
	Misc_Helpers.f_shutdown(__BFILE__, __LINE__);
}
testcase TC_meas_res_sign_tchh_toa256() runs on test_CT {
	var ConnHdlr vc_conn;
	var ConnHdlrPars pars;
	f_init();
	f_vty_config(BTSVTY, "bts 0", "supp-meas-info toa256");
	for (var integer ss := 0; ss <= 1; ss := ss+1) {
		pars := valueof(t_Pars(t_RslChanNr_Lm(5, ss), ts_RSL_ChanMode_SIGN));
		pars.l1_pars.toa256_enabled := true;
		vc_conn := f_start_handler(refers(f_TC_meas_res_periodic), pars);
		vc_conn.done;
	}
	Misc_Helpers.f_shutdown(__BFILE__, __LINE__);
}

/* establish DChan, and send MS POWER CONTROL messages via RSL, verify that
 * the BTS is forwarding those values to the MS via the SACCH L1 header. */
function f_tc_rsl_ms_pwr_ctrl(charstring id) runs on ConnHdlr {
	var L1ctlDlMessage l1_dl;
	var RSL_IE_MS_Power ms_power;
	var RSL_Message rsl;
	var uint5_t power_level := 0;

	f_l1_tune(L1CTL);
	RSL.clear;

	f_est_dchan();

	ms_power.reserved := 0;
	ms_power.fpc_epc := false;

	/* Send the first power control command. This will disable any BTS/TRX
	 * internal power control and switch the MS (which is not in scope of
	 * this test) to a constant power level. We start with a power level
	 * of 0 */
	ms_power.power_level := power_level;
	rsl := valueof(ts_RSL_MS_PWR_CTRL(g_chan_nr, ms_power));
	RSL.send(rsl);

	alt {

	/* Pick all SACCH blocks for checking */
	[] L1CTL.receive(tr_L1CTL_DATA_IND(g_chan_nr, tr_RslLinkID_SACCH(?))) -> value l1_dl {

		/* The first byte of the L1 header contains the power level.
		 * The reserved bits and the fpc bit is set to 0, so we may
		 * compare directly. */
		if (not (l1_dl.payload.data_ind.payload[0] == int2oct(power_level, 1))) {
			setverdict(fail, "Power level in L1 header does not match the signaled (RSL) power level.");
		}

		/* Signal a new power level via RSL for the next turn. */
		if (power_level < 31) {
			power_level := power_level + 1;
			ms_power.power_level := power_level;
			rsl := valueof(ts_RSL_MS_PWR_CTRL(g_chan_nr, ms_power));
			RSL.send(rsl);
			repeat;
		}

		}

	/* Ignore all other blocks */
	[] L1CTL.receive { repeat; }

	}

	f_rsl_chan_deact();
	f_L1CTL_DM_REL_REQ(L1CTL, g_chan_nr);

	setverdict(pass);
}

testcase TC_rsl_ms_pwr_ctrl() runs on test_CT {
	var ConnHdlr vc_conn;
	var ConnHdlrPars pars;
	f_init();

	for (var integer tn := 1; tn <= 4; tn := tn+1) {
		pars := valueof(t_Pars(t_RslChanNr_Bm(tn), ts_RSL_ChanMode_SIGN));
		vc_conn := f_start_handler(refers(f_tc_rsl_ms_pwr_ctrl), pars);
		vc_conn.done;
	}
	Misc_Helpers.f_shutdown(__BFILE__, __LINE__);
}

/* establish DChan, verify that the BTS sets the TA in the first SACCH L1 header. 
TA for the IMM ASS messages is still controlled by g_pars.l1_pars.ms_actual_ta! */
function f_tc_rsl_chan_initial_ta(charstring id) runs on ConnHdlr {
	var L1ctlDlMessage l1_dl;
	var uint5_t ta_to_test := 16;


	f_l1_tune(L1CTL);
	RSL.clear;

	/* tell fake_trx to use a given timing offset for all bursts */
	f_trxc_fake_toffs256(ta_to_test*256);

	f_est_dchan(more_ies :={valueof(t_RSL_IE(RSL_IE_TIMING_ADVANCE, RSL_IE_Body:{timing_adv := ta_to_test}))} );


	alt {

	/* Pick all SACCH blocks for checking */
	[] L1CTL.receive(tr_L1CTL_DATA_IND(g_chan_nr, tr_RslLinkID_SACCH(?))) -> value l1_dl {

		/* The second byte of the L1 header contains the TA. */
		if (not (l1_dl.payload.data_ind.payload[1] == int2oct(ta_to_test, 1))) {
			setverdict(fail, "TA in L1 header does not match the signaled (RSL) TA.");
		}

		}

	/* Ignore all other blocks */
	[] L1CTL.receive { repeat; }

	}

	f_rsl_chan_deact();
	f_L1CTL_DM_REL_REQ(L1CTL, g_chan_nr);

	setverdict(pass);
}

testcase TC_rsl_chan_initial_ta() runs on test_CT {
	var ConnHdlr vc_conn;
	var ConnHdlrPars pars;
	f_init();
	pars := valueof(t_Pars(t_RslChanNr_Bm(1), ts_RSL_ChanMode_SIGN));
	vc_conn := f_start_handler(refers(f_tc_rsl_chan_initial_ta), pars,
				   pcu_comp := false, trxc_comp := true);
	vc_conn.done;
	Misc_Helpers.f_shutdown(__BFILE__, __LINE__);
}

/* establish DChan, verify that the BTS sets MS power in the first SACCH L1 header. */
function f_tc_rsl_chan_initial_ms_pwr(charstring id) runs on ConnHdlr {
	var L1ctlDlMessage l1_dl;
	var uint5_t ms_power_level := 7;

	var RSL_IE_MS_Power ms_power;
	ms_power.reserved := 0;
	ms_power.fpc_epc := false;
	ms_power.power_level := ms_power_level;

	f_l1_tune(L1CTL);
	RSL.clear;

	f_est_dchan(more_ies :={valueof(t_RSL_IE(RSL_IE_MS_POWER, RSL_IE_Body:{ms_power := ms_power}))} );

	timer T := 1.0;
	T.start;
	alt {
	/* Pick all SACCH blocks for checking */
	[] L1CTL.receive(tr_L1CTL_DATA_IND(g_chan_nr, tr_RslLinkID_SACCH(?))) -> value l1_dl {
		/* The first byte of the L1 header contains the power level.. */
		if (not (l1_dl.payload.data_ind.payload[0] == int2oct(ms_power_level, 1))) {
			setverdict(fail, "Power Level in L1 header does not match the signaled (RSL) MS Power Level.");
		}
		}
	/* Ignore all other blocks */
	[] L1CTL.receive { repeat; }
	[] T.timeout {
		setverdict(fail, "Power Level in L1 header does not match the signaled (RSL) MS Power Level.");
		}
	}

	f_rsl_chan_deact();
	f_L1CTL_DM_REL_REQ(L1CTL, g_chan_nr);
	setverdict(pass);
}

testcase TC_rsl_chan_initial_ms_pwr() 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_rsl_chan_initial_ms_pwr));
}

/* Test if a channel without valid uplink bursts generates RSL CONN FAIL IND (TS 48.058 4.10) */
private function f_TC_conn_fail_crit(charstring id) runs on ConnHdlr {
	f_l1_tune(L1CTL);
	RSL.clear;

	f_est_dchan();
	f_sleep(2.0);
	L1CTL.send(ts_L1CTL_DM_REL_REQ(g_chan_nr));

	timer T := 40.0;
	T.start;
	alt {
	[] RSL.receive(tr_RSL_CONN_FAIL_IND(g_chan_nr, ?)) {
		setverdict(pass)
		}
	[] RSL.receive { repeat };
	[] T.timeout {
		Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, "No CONN FAIL IND received");
		}
	}
	f_rsl_chan_deact();
}
testcase TC_conn_fail_crit() runs on test_CT {
	var ConnHdlr vc_conn;
	var ConnHdlrPars pars;
	f_init();
	pars := valueof(t_Pars(t_RslChanNr_SDCCH8(6, 3), ts_RSL_ChanMode_SIGN));
	pars.t_guard := 60.0;
	vc_conn := f_start_handler(refers(f_TC_conn_fail_crit), pars);
	vc_conn.done;
}

/***********************************************************************
 * Paging
 ***********************************************************************/

function tmsi_is_dummy(TMSIP_TMSI_V tmsi) return boolean {
	if (tmsi == 'FFFFFFFF'O) {
		return true;
	} else {
		return false;
	}
}

type record allowedFn { integer frame_nr }
template allowedFn bs_ag_blks_res_0  := { frame_nr := (6, 12, 16, 22, 26, 32, 36, 42, 46) }
template allowedFn bs_ag_blks_res_1  := { frame_nr := (12, 16, 22, 26, 32, 36, 42, 46) }
template allowedFn bs_ag_blks_res_2  := { frame_nr := (16, 22, 26, 32, 36, 42, 46) }
template allowedFn bs_ag_blks_res_3  := { frame_nr := (22, 26, 32, 36, 42, 46) }
template allowedFn bs_ag_blks_res_4  := { frame_nr := (26, 32, 36, 42, 46) }
template allowedFn bs_ag_blks_res_5  := { frame_nr := (32, 36, 42, 46) }
template allowedFn bs_ag_blks_res_6  := { frame_nr := (36, 42, 46) }
template allowedFn bs_ag_blks_res_7  := { frame_nr := (42, 46) }
function check_pch_fn(integer frame_nr, integer bs_ag_blks_res) runs on test_CT
{
	var integer frame_nr_51;
	frame_nr_51 := frame_nr mod 51

	var allowedFn fn_check;
	fn_check.frame_nr := frame_nr_51;

	if (bs_ag_blks_res < 0 or bs_ag_blks_res > 7) {
		Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, "bs_ag_blks_res out of valid range (0..7)");
		return;
	}

	if (bs_ag_blks_res == 0 and match(fn_check, bs_ag_blks_res_0)) {
		return;
	}
	if (bs_ag_blks_res == 1 and match(fn_check, bs_ag_blks_res_1)) {
		return;
	}
	if (bs_ag_blks_res == 2 and match(fn_check, bs_ag_blks_res_2)) {
		return;
	}
	if (bs_ag_blks_res == 3 and match(fn_check, bs_ag_blks_res_3)) {
		return;
	}
	if (bs_ag_blks_res == 4 and match(fn_check, bs_ag_blks_res_4)) {
		return;
	}
	if (bs_ag_blks_res == 5 and match(fn_check, bs_ag_blks_res_5)) {
		return;
	}
	if (bs_ag_blks_res == 6 and match(fn_check, bs_ag_blks_res_6)) {
		return;
	}
	if (bs_ag_blks_res == 7 and match(fn_check, bs_ag_blks_res_7)) {
		return;
	}

	Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, "received paging on AGCH");
	return;
}

altstep as_l1_count_paging(inout integer num_paging_rcv_msgs, inout integer num_paging_rcv_ids, PagingTestCfg cfg)
runs on test_CT {
	var L1ctlDlMessage dl;
	[] L1CTL.receive(tr_L1CTL_DATA_IND(t_RslChanNr_PCH_AGCH(0), ?, c_DummyUI)) {
		repeat;
	}
	[] L1CTL.receive(tr_L1CTL_DATA_IND(t_RslChanNr_PCH_AGCH(0))) -> value dl {
		var octetstring without_plen :=
			substr(dl.payload.data_ind.payload, 1, lengthof(dl.payload.data_ind.payload)-1);
		var PDU_ML3_NW_MS rr := dec_PDU_ML3_NW_MS(without_plen);

		check_pch_fn(dl.dl_info.frame_nr, cfg.bs_ag_blks_res);

		if (match(rr, tr_PAGING_REQ1)) {
			num_paging_rcv_msgs := num_paging_rcv_msgs + 1;
			num_paging_rcv_ids := num_paging_rcv_ids + 1;
			if (isvalue(rr.msgs.rrm.pagingReq_Type1.mobileIdentity2)) {
				num_paging_rcv_ids := num_paging_rcv_ids + 1;
			}
		} else if (match(rr, tr_PAGING_REQ2)) {
			num_paging_rcv_msgs := num_paging_rcv_msgs + 1;
			if (not tmsi_is_dummy(rr.msgs.rrm.pagingReq_Type2.mobileIdentity1)) {
				num_paging_rcv_ids := num_paging_rcv_ids + 1;
			}
			if (not tmsi_is_dummy(rr.msgs.rrm.pagingReq_Type2.mobileIdentity2)) {
				num_paging_rcv_ids := num_paging_rcv_ids + 1;
			}
			if (isvalue(rr.msgs.rrm.pagingReq_Type2.mobileIdentity3)) {
				num_paging_rcv_ids := num_paging_rcv_ids + 1;
			}
		} else if (match(rr, tr_PAGING_REQ3)) {
			num_paging_rcv_msgs := num_paging_rcv_msgs + 1;
			if (not tmsi_is_dummy(rr.msgs.rrm.pagingReq_Type3.mobileIdentity1)) {
				num_paging_rcv_ids := num_paging_rcv_ids + 1;
			}
			if (not tmsi_is_dummy(rr.msgs.rrm.pagingReq_Type3.mobileIdentity2)) {
				num_paging_rcv_ids := num_paging_rcv_ids + 1;
			}
			if (not tmsi_is_dummy(rr.msgs.rrm.pagingReq_Type3.mobileIdentity3)) {
				num_paging_rcv_ids := num_paging_rcv_ids + 1;
			}
			if (not tmsi_is_dummy(rr.msgs.rrm.pagingReq_Type3.mobileIdentity4)) {
				num_paging_rcv_ids := num_paging_rcv_ids + 1;
			}
		}
		repeat;
	}
}

type record PagingTestCfg {
	boolean combined_ccch,
	integer bs_ag_blks_res,
	float load_factor,
	boolean exp_load_ind,
	boolean exp_overload,
	boolean use_tmsi
}

type record PagingTestState {
	integer num_paging_sent,
	integer num_paging_rcv_msgs,
	integer num_paging_rcv_ids,
	integer num_overload
}

/* receive + ignore RSL RF RES IND */
altstep as_rsl_res_ind() runs on test_CT {
	[] RSL_CCHAN.receive(tr_RSL_UD(tr_RSL_RF_RES_IND)) {
		repeat;
	}
}

/* Helper function for paging related testing */
private function f_TC_paging(PagingTestCfg cfg) runs on test_CT return PagingTestState {
	f_init();
	f_init_l1ctl();
	f_l1_tune(L1CTL);

	var PagingTestState st := {
		num_paging_sent := 0,
		num_paging_rcv_msgs := 0,
		num_paging_rcv_ids := 0,
		num_overload := 0
	};

	var float max_pch_blocks_per_sec := f_pch_block_rate_est(cfg.combined_ccch, cfg.bs_ag_blks_res);
	var float max_pch_imsi_per_sec;
	if (cfg.use_tmsi) {
		max_pch_imsi_per_sec := max_pch_blocks_per_sec * 4.0; /* Type 3 */
	} else {
		max_pch_imsi_per_sec := max_pch_blocks_per_sec * 2.0; /* Type 1 */
	}
	var float pch_blocks_per_sec := max_pch_imsi_per_sec * cfg.load_factor;
	var float interval := 1.0 / pch_blocks_per_sec;
	var float time_total := 20.0;
	var integer pkt_total := float2int(time_total * pch_blocks_per_sec);
	log("pch_blocks_total=", pkt_total," pch_blocks_per_sec=", pch_blocks_per_sec, " interval=", interval);

	timer T_total := 300.0; /* big value (far bigger than time_total), used to count elapsed time */
	T_total.start;

	timer T_itv := 0.0;
	T_itv.start;
	while (st.num_paging_sent < pkt_total) {
		alt {
		/* check for presence of CCCH LOAD IND (paging load) */
		[cfg.exp_overload] RSL_CCHAN.receive(tr_RSL_UD(tr_RSL_PAGING_LOAD_IND(0))) {
			st.num_overload := st.num_overload + 1;
			repeat;
			}
		[not cfg.exp_overload]  RSL_CCHAN.receive(tr_RSL_UD(tr_RSL_PAGING_LOAD_IND(0))) {
			Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, "Unexpected PCH Overload");
			}
		[cfg.exp_load_ind] RSL_CCHAN.receive(tr_RSL_UD(tr_RSL_PAGING_LOAD_IND)) {
			log("Rx LOAD_IND");
			/* FIXME: analyze/verify interval + contents */
			repeat;
			}
		/* check if paging requests arrive on Um side */
		[] as_l1_count_paging(st.num_paging_rcv_msgs, st.num_paging_rcv_ids, cfg);
		[] L1CTL.receive { repeat; }
		[] T_itv.timeout {
			/* Send paging cmds based on elapsed time */
			var integer new_sent := f_min(pkt_total, float2int(T_total.read * pch_blocks_per_sec) + 1);
			while (st.num_paging_sent < new_sent) {
				var MobileIdentityV mi;

				/* build mobile Identity */
				if (cfg.use_tmsi) {
					mi := valueof(t_MI_TMSI(f_rnd_octstring(4)));
				} else {
					mi := valueof(ts_MI_IMSI(f_gen_imsi(st.num_paging_sent)));
				}

				/* Send RSL PAGING COMMAND */
				RSL_CCHAN.send(ts_RSL_UD(ts_RSL_PAGING_CMD(mi, st.num_paging_sent mod 4)));

				st.num_paging_sent := st.num_paging_sent + 1;
			}
			if (st.num_paging_sent < pkt_total) {
				/* Wait for interval to next PAGING COMMAND */
				var float time_now := T_total.read;
				var float next_sched := int2float(st.num_paging_sent)*interval;
				if (next_sched > time_now) {
					T_itv.start(next_sched - time_now);
				} else {
					T_itv.start(0.0);
				}
			} else {
				/* We are done, no need to keep counting */
				T_total.stop;
			}
			}
		[] T_total.timeout { }
		[] as_rsl_res_ind();
		}
	}

	/* wait for max 18s for paging queue to drain (size: 200, ~ 13 per s -> 15s) */
	timer T_wait := 18.0;
	T_wait.start;
	alt {
	[] as_l1_count_paging(st.num_paging_rcv_msgs, st.num_paging_rcv_ids, cfg);
	[] L1CTL.receive { repeat; }
	/* 65535 == empty paging queue, we can terminate*/
	[] RSL_CCHAN.receive(tr_RSL_UD(tr_RSL_PAGING_LOAD_IND(65535))) { }
	[] RSL_CCHAN.receive(tr_RSL_UD(tr_RSL_PAGING_LOAD_IND)) { repeat; }
	[] T_wait.timeout {
		Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, "Waiting for empty paging queue");
		}
	[] as_rsl_res_ind();
	}

	log("num_paging_sent=", st.num_paging_sent, " rcvd_msgs=", st.num_paging_rcv_msgs,
	    " rcvd_ids=", st.num_paging_rcv_ids);
	return st;
}

/* Create ~ 80% paging load (IMSI only) sustained for about 20s, verifying that
 *  - the number of Mobile Identities on Um PCH match the number of pages on RSL
 *  - that CCCH LOAD IND (PCH) are being generated
 *  - that CCCH LOAD IND (PCH) [no load] is received after paging flood is over */
testcase TC_paging_imsi_80percent() runs on test_CT {
	var SystemInformation si3 := valueof(ts_SI3_default);
	var PagingTestCfg cfg := {
		combined_ccch := true,
		bs_ag_blks_res := si3.payload.si3.ctrl_chan_desc.bs_ag_blks_res,
		load_factor := 0.8,
		exp_load_ind := true,
		exp_overload := false,
		use_tmsi := false
	};
	var PagingTestState st := f_TC_paging(cfg);
	if (st.num_paging_sent != st.num_paging_rcv_ids) {
		Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, log2str("Expected ", st.num_paging_sent, " pagings but have ",
			   st.num_paging_rcv_ids));
	} else {
		setverdict(pass);
	}
	Misc_Helpers.f_shutdown(__BFILE__, __LINE__);
}

/* Create ~ 80% paging load (TMSI only) sustained for about 20s, verifying that
 *  - the number of Mobile Identities on Um PCH match the number of pages on RSL
 *  - that CCCH LOAD IND (PCH) are being generated
 *  - that CCCH LOAD IND (PCH) [no load] is received after paging flood is over */
testcase TC_paging_tmsi_80percent() runs on test_CT {
	var SystemInformation si3 := valueof(ts_SI3_default);
	var PagingTestCfg cfg := {
		combined_ccch := true,
		bs_ag_blks_res := si3.payload.si3.ctrl_chan_desc.bs_ag_blks_res,
		load_factor := 0.8,
		exp_load_ind := true,
		exp_overload := false,
		use_tmsi := true
	};
	var PagingTestState st := f_TC_paging(cfg);
	if (st.num_paging_sent != st.num_paging_rcv_ids) {
		Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, log2str("Expected ", st.num_paging_sent, " pagings but have ",
			   st.num_paging_rcv_ids));
	} else {
		setverdict(pass);
	}
	Misc_Helpers.f_shutdown(__BFILE__, __LINE__);
}

/* Create ~ 200% paging load (IMSI only) sustained for about 20s, verifying that
 *  - the number of Mobile Identities on Um PCH are ~ 82% of the number of pages on RSL
 *  - that CCCH LOAD IND (PCH) are being generated and reach 0 at some point
 *  - that CCCH LOAD IND (PCH) [no load] is received after paging flood is over */
testcase TC_paging_imsi_200percent() runs on test_CT {
	var SystemInformation si3 := valueof(ts_SI3_default);
	var PagingTestCfg cfg := {
		combined_ccch := true,
		bs_ag_blks_res := si3.payload.si3.ctrl_chan_desc.bs_ag_blks_res,
		load_factor := 2.0,
		exp_load_ind := true,
		exp_overload := true,
		use_tmsi := false
	};
	var PagingTestState st := f_TC_paging(cfg);
	/* We expect about 80-85% to pass, given that we can fill the paging buffer of 200
	 * slots and will fully drain that buffer before returning */
	var template integer tpl := (st.num_paging_sent*78/100 .. st.num_paging_sent *85/100);
	if (not match(st.num_paging_rcv_ids, tpl)) {
		Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, log2str("Expected ", tpl, " pagings but have ", st.num_paging_rcv_ids));
	} else {
		setverdict(pass);
	}
	Misc_Helpers.f_shutdown(__BFILE__, __LINE__);
}

/* Create ~ 200% paging load (TMSI only) sustained for about 20s, verifying that
 *  - the number of Mobile Identities on Um PCH are ~ 82% of the number of pages on RSL
 *  - that CCCH LOAD IND (PCH) are being generated and reach 0 at some point
 *  - that CCCH LOAD IND (PCH) [no load] is received after paging flood is over */
testcase TC_paging_tmsi_200percent() runs on test_CT {
	var SystemInformation si3 := valueof(ts_SI3_default);
	var PagingTestCfg cfg := {
		combined_ccch := true,
		bs_ag_blks_res := si3.payload.si3.ctrl_chan_desc.bs_ag_blks_res,
		load_factor := 2.0,
		exp_load_ind := true,
		exp_overload := true,
		use_tmsi := true
	};
	var PagingTestState st := f_TC_paging(cfg);
	/* We expect about 70% to pass, given that we can fill the paging buffer of 200
	 * slots and will fully drain that buffer before returning */
	var template integer tpl := (st.num_paging_sent*64/100 .. st.num_paging_sent *72/100);
	if (not match(st.num_paging_rcv_ids, tpl)) {
		Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, log2str("Expected ", tpl, " pagings but have ", st.num_paging_rcv_ids));
	} else {
		setverdict(pass);
	}
	Misc_Helpers.f_shutdown(__BFILE__, __LINE__);
}


/***********************************************************************
 * Immediate Assignment / AGCH
 ***********************************************************************/
const MobileAllocation c_MA_null := {
	len := 0,
	ma := ''B
}

template (value) ChannelDescription ts_ChanDesc(template (value) RslChannelNr chan_nr, uint3_t tsc := 7,
						uint12_t arfcn := 871) := {
	chan_nr := chan_nr,
	tsc := tsc,
	h := false,
	arfcn := arfcn,
	maio_hsn := omit
}

private function f_fmt_ia_stats(integer num_tx, integer num_rx, integer num_del) return charstring {
	return int2str(num_tx) & " sent, "
		  & int2str(num_rx) & " received, "
		  & int2str(num_del) & " deleted";
}

private function f_TC_imm_ass(integer num_total, float sleep_s, float exp_pass) runs on test_CT {
	var L1ctlDlMessage l1_dl;
	timer T := 10.0;
	var integer num_tx := 0;
	var integer num_rx := 0;
	var integer num_del := 0;
	var charstring res_str;
	var float rx_ratio;

	f_init();
	f_init_l1ctl();
	f_l1_tune(L1CTL);

	for (var integer i := 0; i < num_total; i := i+1) {
		var ChannelDescription ch_desc := valueof(ts_ChanDesc(valueof(t_RslChanNr_SDCCH4(0, 0))));
		var GsmRrMessage ia := valueof(ts_IMM_ASS(42, i, 5, ch_desc, c_MA_null));
		var octetstring ia_enc := enc_GsmRrMessage(ia);
		RSL_CCHAN.send(ts_RSL_UD(ts_RSL_IMM_ASSIGN(ia_enc, 0)));
		num_tx := num_tx+1;
		f_sleep(sleep_s);
	}
	/* FIXME: check if imm.ass arrive on Um side */
	T.start;
	alt {
	[] RSL_CCHAN.receive(tr_RSL_UD(tr_RSL_DELETE_IND(?, 0))) {
		num_del := num_del+1;
		repeat;
		}
	[] RSL_CCHAN.receive {
		repeat;
		}
	[] L1CTL.receive(tr_L1CTL_DATA_IND(t_RslChanNr_PCH_AGCH(0), ?)) -> value l1_dl {
		/* somehow dec_SystemInformation will try to decode even non-RR as SI */
		var GsmRrMessage rr := dec_GsmRrMessage(l1_dl.payload.data_ind.payload);
		if (not match(rr, tr_IMM_ASS(42, ?, 5, ?, ?))) {
			/* FIXME: Why are we seeing paging requests on PCH/AGCH? */
			//Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, log2str("Unexpected IMM-ASS values on AGCH: ", rr));
		} else {
			num_rx := num_rx+1;
		}
		repeat;
		}
	[] L1CTL.receive { repeat; }
	[] T.timeout { }
	}
	res_str := f_fmt_ia_stats(num_tx, num_rx, num_del);
	log("AGCH test: " & res_str);
	if (num_rx + num_del != num_tx) {
		Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, "RX + DEL != TX ?!?: " & res_str);
	}
	rx_ratio := int2float(num_rx) / int2float(num_tx);
	if (rx_ratio < exp_pass*0.8 or rx_ratio > exp_pass*1.2) {
		Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, "RX ratio ("&float2str(rx_ratio)&") far from expected ("&float2str(exp_pass)&") " & res_str);
	} else {
		setverdict(pass);
	}
	Misc_Helpers.f_shutdown(__BFILE__, __LINE__);
}

/* send a long burst of 1000 IMM.ASS with 20ms spacing (50 per s); expect 75% of them to be deleted */
testcase TC_imm_ass_1000_20ms() runs on test_CT {
	f_TC_imm_ass(1000, 0.02, 0.25);
}

/* send a short burst of 200 IMM.ASS without any spacing; expect 95% of them to be deleted */
testcase TC_imm_ass_200_0ms() runs on test_CT {
	f_TC_imm_ass(200, 0.0, 0.05);
}

/* send 150 IMM.ASS at rate of 13/s; expect none of them to be deleted */
testcase TC_imm_ass_200_76ms() runs on test_CT {
	f_TC_imm_ass(150, 0.076, 1.00);
}



/***********************************************************************
 * BCCH
 ***********************************************************************/

/* tuple of Frame Number + decoded SI */
type record SystemInformationFn {
	GsmFrameNumber frame_number,
	SystemInformation si
}

/* an arbitrary-length vector of decoded SI + gsmtap header */
type record of SystemInformationFn SystemInformationVector;

/* an array of SI-vectors indexed by TC value */
type SystemInformationVector SystemInformationVectorPerTc[8];

/* determine if a given SI vector contains given SI type at least once */
function f_si_vecslot_contains(SystemInformationVector arr, RrMessageType key, boolean bcch_ext := false) return boolean {
	for (var integer i:= 0; i< sizeof(arr); i := i + 1) {
		var integer fn_mod51 := arr[i].frame_number mod 51;
		if (not bcch_ext and fn_mod51 == 2 or
		        bcch_ext and fn_mod51 == 6) {
			if (arr[i].si.header.message_type == key) {
				return true;
			}
		}
	}
	return false;
}

/* ensure a given TC slot of the SI vector contains given SI type at least once at TC */
function f_ensure_si_vec_contains(SystemInformationVectorPerTc arr, integer tc, RrMessageType key, boolean ext_bcch := false) {
	if (not f_si_vecslot_contains(arr[tc], key, ext_bcch)) {
		Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, log2str("No ", key, " in TC=", tc, "!"));
	}
}

/* check if a given SI vector contains given SI type at least once on any TC */
function f_si_vec_contains(SystemInformationVectorPerTc arr, RrMessageType key) return boolean {
	for (var integer tc:= 0; tc < sizeof(arr); tc := tc + 1) {
		if (f_si_vecslot_contains(arr[tc], key) or
		    f_si_vecslot_contains(arr[tc], key, true)) {
			return true;
		}
	}
	return false;
}

/* determine if a given SI vector contains given SI type at least N of M times */
function f_si_vecslot_contains_n_of_m(SystemInformationVector arr, RrMessageType key, boolean bcch_ext := false, integer n := 1, integer m := 4) return boolean {
	var integer count := 0;
	if (sizeof(arr) < m) {
		Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, "Error: Insufficient SI in array");
	}
	for (var integer i:= 0; i < m; i := i + 1) {
		var integer fn_mod51 := arr[i].frame_number mod 51;
		if (not bcch_ext and fn_mod51 == 2 or
		        bcch_ext and fn_mod51 == 6) {
			if (arr[i].si.header.message_type == key) {
				count := count + 1;
			}
		}
	}
	if (count >= n) {
		return true;
	} else {
		return false;
	}
}

/* ensure a given TC slot of the SI vector contains given SI type at least N out of M times at TC */
function f_ensure_si_vec_contains_n_of_m(SystemInformationVectorPerTc arr, integer tc, RrMessageType key, boolean ext_bcch := false, integer n, integer m) {
	if (not f_si_vecslot_contains_n_of_m(arr[tc], key, ext_bcch, n, m)) {
		Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, log2str("Not ", n, "/", m, " of ", key, " in TC=", tc, "!"));
	}
}

/* determine if a given SI vector contains given SI type at least once */
function f_si_vecslot_contains_only(SystemInformationVector arr, RrMessageType key, boolean bcch_ext := false) return boolean {
	for (var integer i:= 0; i< sizeof(arr); i := i + 1) {
		var integer fn_mod51 := arr[i].frame_number mod 51;
		if (not bcch_ext and fn_mod51 == 2 or
		        bcch_ext and fn_mod51 == 6) {
			if (arr[i].si.header.message_type != key) {
				return false;
			}
		}
	}
	return true;
}

/* ensure a given TC slot of the SI vector contains only given SI type */
function f_ensure_si_vec_contains_only(SystemInformationVectorPerTc arr, integer tc, RrMessageType key, boolean ext_bcch := false) {
	if (not f_si_vecslot_contains_only(arr[tc], key, ext_bcch)) {
		Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, log2str("Not all ", key, " in TC=", tc, "!"));
	}
}

/* SI configuration of cell, against which we validate actual SI messages */
type set SystemInformationConfig {
	boolean bcch_extended,
	boolean si1_present,
	boolean si2bis_present,
	boolean si2ter_present,
	boolean si2quater_present,
	boolean si7_present,
	boolean si8_present,
	boolean si9_present,
	boolean si13_present,
	boolean si13alt_present,
	boolean si15_present,
	boolean si16_present,
	boolean si17_present,
	boolean si2n_present,
	boolean si21_present,
	boolean si22_present
}

/* validate the SI scheduling according to TS 45.002 version 14.1.0 Release 14, Section 6.3.1.3 */
function f_validate_si_scheduling(SystemInformationConfig cfg, SystemInformationVectorPerTc si_per_tc) {
	var integer i;
	for (i := 0; i < sizeof(si_per_tc); i := i + 1) {
		if (sizeof(si_per_tc[i]) == 0) {
			Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, log2str("No SI messages for TC=", i));
		}
	}
	if (cfg.si1_present) {
		/* ii) System Information Type 1 needs to be sent if frequency hopping is in use or
		 * when the NCH is present in a cell. If the MS finds another message on BCCH Norm
		 * when TC = 0, it can assume that System Information Type 1 is not in use. */
		f_ensure_si_vec_contains(si_per_tc, 0, SYSTEM_INFORMATION_TYPE_1);
		/* make sure *ALL* contain SI1 */
		f_ensure_si_vec_contains_only(si_per_tc, 0, SYSTEM_INFORMATION_TYPE_1);
	}
	f_ensure_si_vec_contains(si_per_tc, 1, SYSTEM_INFORMATION_TYPE_2);
	/* iii) A SI 2 message will be sent at least every time TC = 1 */
	f_ensure_si_vec_contains(si_per_tc, 2, SYSTEM_INFORMATION_TYPE_3);
	f_ensure_si_vec_contains(si_per_tc, 6, SYSTEM_INFORMATION_TYPE_3);
	f_ensure_si_vec_contains(si_per_tc, 3, SYSTEM_INFORMATION_TYPE_4);
	f_ensure_si_vec_contains(si_per_tc, 7, SYSTEM_INFORMATION_TYPE_4);

	/*  iii) System information type 2 bis or 2 ter messages are sent if needed, as determined by the
	 *  system operator. If only one of them is needed, it is sent when TC = 5. If both are
	 *  needed, 2bis is sent when TC = 5 and 2ter is sent at least once within any of 4
	 *  consecutive occurrences of TC = 4. */
	if (cfg.si2bis_present and not cfg.si2ter_present) {
		f_ensure_si_vec_contains(si_per_tc, 5, SYSTEM_INFORMATION_TYPE_2bis);
	} else if (cfg.si2ter_present and not cfg.si2bis_present) {
		f_ensure_si_vec_contains(si_per_tc, 5, SYSTEM_INFORMATION_TYPE_2ter);
	} else if (cfg.si2ter_present and cfg.si2bis_present) {
		f_ensure_si_vec_contains(si_per_tc, 5, SYSTEM_INFORMATION_TYPE_2bis);
		f_ensure_si_vec_contains_n_of_m(si_per_tc, 4, SYSTEM_INFORMATION_TYPE_2ter, false, 1, 4);
	}

	if (cfg.si7_present or cfg.si8_present) {
		/* vi) Use of System Information type 7 and 8 is not always necessary. It is necessary
		 * if System Information type 4 does not contain all information needed for cell
		 * selection and reselection. */
		if (not cfg.bcch_extended) {
			testcase.stop("Error: SI7/SI8 require BCCH Extd.");
		}
		if (cfg.si7_present) {
			f_ensure_si_vec_contains(si_per_tc, 7, SYSTEM_INFORMATION_TYPE_7, true);
		}
		if (cfg.si8_present) {
			f_ensure_si_vec_contains(si_per_tc, 3, SYSTEM_INFORMATION_TYPE_8, true);
		}
	}

	if (cfg.si2quater_present) {
		/*  iii) System information type 2 quater is sent if needed, as determined by the system
		 *  operator.  If sent on BCCH Norm, it shall be sent when TC = 5 if neither of 2bis
		 *  and 2ter are used, otherwise it shall be sent at least once within any of 4
		 *  consecutive occurrences of TC = 4. If sent on BCCH Ext, it is sent at least once
		 *  within any of 4 consecutive occurrences of TC = 5. */
		if (not (cfg.bcch_extended)) {
			if (not (cfg.si2bis_present or cfg.si2ter_present)) {
				f_ensure_si_vec_contains(si_per_tc, 5, SYSTEM_INFORMATION_TYPE_2quater);
			} else {
				f_ensure_si_vec_contains_n_of_m(si_per_tc, 4, SYSTEM_INFORMATION_TYPE_2quater, false, 1, 4);
			}
		} else {
			f_ensure_si_vec_contains_n_of_m(si_per_tc, 5, SYSTEM_INFORMATION_TYPE_2quater, true, 1, 4);
		}
	}
	if (cfg.si9_present) {
		/* vi) System Information type 9 is sent in those blocks with TC = 4 which are specified
		 * in system information type 3 as defined in 3GPP TS 44.018. */
		f_ensure_si_vec_contains(si_per_tc, 4, SYSTEM_INFORMATION_TYPE_9); // FIXME SI3
	}
	if (cfg.si13_present) {
		/* vii) System Information type 13 is only related to the GPRS service. System Information
		 * Type 13 need only be sent if GPRS support is indicated in one or more of System
		 * Information Type 3 or 4 or 7 or 8 messages. These messages also indicate if the
		 * message is sent on the BCCH Norm or if the message is transmitted on the BCCH Ext.
		 * In the case that the message is sent on the BCCH Norm, it is sent at least once
		 * within any of 4 consecutive occurrences of TC=4. */
		if (not cfg.bcch_extended) {
			log("not-bccch-extended");
			f_ensure_si_vec_contains_n_of_m(si_per_tc, 4, SYSTEM_INFORMATION_TYPE_13, false, 1, 4);
		} else {
			log("bccch-extended");
			f_ensure_si_vec_contains(si_per_tc, 0, SYSTEM_INFORMATION_TYPE_13, true);
		}
		if (f_si_vec_contains(si_per_tc, SYSTEM_INFORMATION_TYPE_13alt)) {
			Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, "Cannot have SI13alt and SI13");
		}
	}
	if (cfg.si16_present or cfg.si17_present) {
		/* viii) System Information type 16 and 17 are only related to the SoLSA service. They
		 * should not be sent in a cell where network sharing is used (see rule xv). */
		if (cfg.si22_present) {
			testcase.stop("Error: Cannot have SI16/SI17 and SI22!");
		}
		if (f_si_vec_contains(si_per_tc, SYSTEM_INFORMATION_TYPE_22)) {
			Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, "Cannot have SI16/SI17 and SI22!");
		}
		if (not cfg.bcch_extended) {
			testcase.stop("Error: SI16/SI17 requires BCCH Extd!");
		}
		if (cfg.si16_present) {
			f_ensure_si_vec_contains(si_per_tc, 6, SYSTEM_INFORMATION_TYPE_16, true);
		}
		if (cfg.si17_present) {
			f_ensure_si_vec_contains(si_per_tc, 2, SYSTEM_INFORMATION_TYPE_17, true);
		}
	}

		/* ix) System Information type 18 and 20 are sent in order to transmit non-GSM
		 * broadcast information. The frequency with which they are sent is determined by the
		 * system operator. System Information type 9 identifies the scheduling of System
		 * Information type 18 and 20 messages. */

		/* x) System Information Type 19 is sent if COMPACT neighbours exist. If System
		 * Information Type 19 is present, then its scheduling shall be indicated in System
		 * Information Type 9. */

	if (cfg.si15_present) {
		/* xi) System Information Type 15 is broadcast if dynamic ARFCN mapping is used in the
		 * PLMN. If sent on BCCH Norm, it is sent at least once within any of 4 consecutive
		 * occurrences of TC = 4. If sent on BCCH Ext, it is sent at least once within any of
		 * 4 consecutive occurrences of TC = 1. */
		if (not cfg.bcch_extended) {
			f_ensure_si_vec_contains_n_of_m(si_per_tc, 4, SYSTEM_INFORMATION_TYPE_15, false, 1, 4);
		} else {
			f_ensure_si_vec_contains_n_of_m(si_per_tc, 1, SYSTEM_INFORMATION_TYPE_15, true, 1, 4);
		}
	}
	if (cfg.si13alt_present) {
		/* xii) System Information type 13 alt is only related to the GERAN Iu mode. System
		 * Information Type 13 alt need only be sent if GERAN Iu mode support is indicated in
		 * one or more of System Information Type 3 or 4 or 7 or 8 messages and SI 13 is not
		 * broadcast. These messages also indicate if the message is sent on the BCCH Norm or
		 * if the message is transmitted on the BCCH Ext. In the case that the message is sent
		 * on the BCCH Norm, it is sent at least once within any of 4 consecutive occurrences
		 * of TC = 4. */
		if (cfg.si13_present) {
			testcase.stop("Error: Cannot have SI13alt and SI13");
		}
		if (f_si_vec_contains(si_per_tc, SYSTEM_INFORMATION_TYPE_13)) {
			Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, "Cannot have SI13alt and SI13");
		}
		if (not cfg.bcch_extended) {
			f_ensure_si_vec_contains_n_of_m(si_per_tc, 4, SYSTEM_INFORMATION_TYPE_13alt, false, 1, 4);
		} else {
			f_ensure_si_vec_contains(si_per_tc, 0, SYSTEM_INFORMATION_TYPE_13alt, true);
		}
	}
	if (cfg.si2n_present) {
		/* xiii) System Information Type 2n is optionally sent on BCCH Norm or BCCH Ext if needed,
		 * as determined by the system operator. In the case that the message is sent on the
		 * BCCH Norm, it is sent at least once within any of 4 consecutive occurrences of TC =
		 * 4. If the message is sent on BCCH Ext, it is sent at least once within any of 2
		 * consecutive occurrences of TC = 4. */
		if (not cfg.bcch_extended) {
			f_ensure_si_vec_contains_n_of_m(si_per_tc, 4, SYSTEM_INFORMATION_TYPE_2n, false, 1, 4);
		} else {
			f_ensure_si_vec_contains_n_of_m(si_per_tc, 4, SYSTEM_INFORMATION_TYPE_2n, true, 2, 4);
		}
	}
	if (cfg.si21_present) {
		/* xiv) System Information Type 21 is optionally sent on BCCH Norm or BCCH Ext, as
		 * determined by the system operator. If Extended Access Barring is in use in the cell
		 * then this message is sent at least once within any of 4 consecutive occurrences of
		 * TC = 4 regardless if it is sent on BCCH Norm or BCCH Ext. If BCCH Ext is used in a
		 * cell then this message shall only be sent on BCCH Ext. */
		if (not cfg.bcch_extended) {
			f_ensure_si_vec_contains_n_of_m(si_per_tc, 4, SYSTEM_INFORMATION_TYPE_21, false, 1, 4);
		} else {
			f_ensure_si_vec_contains_n_of_m(si_per_tc, 4, SYSTEM_INFORMATION_TYPE_21, true, 1, 4);
			if (f_si_vecslot_contains(si_per_tc[4], SYSTEM_INFORMATION_TYPE_21)) {
				Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, "Cannot have SI21 on BCCH Norm if BCCH Extd enabled!");
			}
		}
	}
	if (cfg.si22_present) {
		/* xv) System Information Type 22 is sent if network sharing is in use in the cell. It
		 * should not be sent in a cell where SoLSA is used (see rule viii). System
		 * Information Type 22 instances shall be sent on BCCH Ext within any occurrence of TC
		 * =2 and TC=6. */
		if (cfg.si16_present or cfg.si17_present) {
			testcase.stop("Error: Cannot have SI16/SI17 and SI22!");
		}
		if (f_si_vec_contains(si_per_tc, SYSTEM_INFORMATION_TYPE_16) or
		    f_si_vec_contains(si_per_tc, SYSTEM_INFORMATION_TYPE_17)) {
			Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, "Cannot have SI16/SI17 and SI22!");
		}
		if (not cfg.bcch_extended) {
			testcase.stop("Error: SI22 requires BCCH Extd!");
		} else {
			f_ensure_si_vec_contains_only(si_per_tc, 2, SYSTEM_INFORMATION_TYPE_22, true);
			f_ensure_si_vec_contains_only(si_per_tc, 6, SYSTEM_INFORMATION_TYPE_22, true);
		}
	}
}

/* sample Systme Information for specified duration via L1CTL */
function f_l1_sample_si(L1CTL_PT pt, float duration := 8.0) return SystemInformationVectorPerTc {
	timer T := duration;
	var SystemInformationVectorPerTc si_per_tc;
	var L1ctlDlMessage l1_dl;

	/* initialize all per-TC vectors empty */
	for (var integer i:= 0; i < sizeof(si_per_tc); i := i+1) {
		si_per_tc[i] := {};
	}

	/* flush all previous L1 queued msgs */
	pt.clear;

	T.start;
	alt {
	[] pt.receive(tr_L1CTL_DATA_IND(t_RslChanNr_BCCH(0), ?)) -> value l1_dl {
		/* somehow dec_SystemInformation will try to decode even non-RR as SI */
		if (not (l1_dl.payload.data_ind.payload[1] ==  '06'O)) {
			log("Ignoring non-RR SI ", l1_dl);
			repeat;
		}
		var SystemInformationFn sig := {
			frame_number := l1_dl.dl_info.frame_nr,
			si := dec_SystemInformation(l1_dl.payload.data_ind.payload)
		}
		var integer tc := f_gsm_compute_tc(sig.frame_number);
		log("SI received at TC=", tc, ": ", sig.si);
		/* append to the per-TC bucket */
		si_per_tc[tc] := si_per_tc[tc] & { sig };
		repeat;
		}
	[] pt.receive { repeat; }
	[] T.timeout { }
	}

	for (var integer i:= 0; i < sizeof(si_per_tc); i := i+1) {
		log(testcasename(), ": TC=", i, " has #of SI=", sizeof(si_per_tc[i]));
	}
	log("si_per_tc=", si_per_tc);
	return si_per_tc;
}

/* helper function: Set given SI via RSL + validate scheduling.
 * CALLER MUST MAKE SURE TO CHANGE GLOBAL si_cfg! */
function f_TC_si_sched() runs on test_CT {
	var SystemInformationVectorPerTc si_per_tc;
	f_init_l1ctl();
	f_l1_tune(L1CTL);

	/* Sample + Validate Scheduling */
	si_per_tc := f_l1_sample_si(L1CTL);
	f_validate_si_scheduling(si_cfg, si_per_tc);

	setverdict(pass);
}

testcase TC_si_sched_default() runs on test_CT {
	f_init();
	/* 2+3+4 are mandatory and set in f_init() */
	f_TC_si_sched();
	Misc_Helpers.f_shutdown(__BFILE__, __LINE__);
}

testcase TC_si_sched_1() runs on test_CT {
	f_init();
	si_cfg.si1_present := true;
	f_rsl_bcch_fill_raw(RSL_SYSTEM_INFO_1, '5506198fb38000000000000000000000000000e504002b'O);
	f_TC_si_sched();
	Misc_Helpers.f_shutdown(__BFILE__, __LINE__);
}

testcase TC_si_sched_2bis() runs on test_CT {
	f_init();
	si_cfg.si2bis_present := true;
	f_rsl_bcch_fill_raw(RSL_SYSTEM_INFO_2bis, '550602bfe809b3ff00000000000000000000007900002b'O);
	f_TC_si_sched();
	Misc_Helpers.f_shutdown(__BFILE__, __LINE__);
}

testcase TC_si_sched_2ter() runs on test_CT {
	f_init();
	si_cfg.si2ter_present := true;
	f_rsl_bcch_fill_raw(RSL_SYSTEM_INFO_2ter, '010603bf66b0aa0a00000002000000000000002b2b2b2b'O);
	f_TC_si_sched();
	Misc_Helpers.f_shutdown(__BFILE__, __LINE__);
}

testcase TC_si_sched_2ter_2bis() runs on test_CT {
	f_init();
	si_cfg.si2bis_present := true;
	f_rsl_bcch_fill_raw(RSL_SYSTEM_INFO_2bis, '550602bfe809b3ff00000000000000000000007900002b'O);
	si_cfg.si2ter_present := true;
	f_rsl_bcch_fill_raw(RSL_SYSTEM_INFO_2ter, '010603bf66b0aa0a00000002000000000000002b2b2b2b'O);
	f_TC_si_sched();
	Misc_Helpers.f_shutdown(__BFILE__, __LINE__);
}

testcase TC_si_sched_2quater() runs on test_CT {
	f_init();
	si_cfg.si2quater_present := true;
	f_rsl_bcch_fill_raw(RSL_SYSTEM_INFO_2quater, '050607a8a0364aa698d72ff424feee0506d5e7fff02043'O);
	f_TC_si_sched();
	Misc_Helpers.f_shutdown(__BFILE__, __LINE__);
}

testcase TC_si_sched_13() runs on test_CT {
	f_init();
	si_cfg.si13_present := true;
	f_rsl_bcch_fill_raw(RSL_SYSTEM_INFO_13, '0106009000185a6fc9e08410ab2b2b2b2b2b2b2b2b2b2b'O);
	f_TC_si_sched();
	Misc_Helpers.f_shutdown(__BFILE__, __LINE__);
}

testcase TC_si_sched_13_2bis_2ter_2quater() runs on test_CT {
	f_init();
	si_cfg.si2bis_present := true;
	f_rsl_bcch_fill_raw(RSL_SYSTEM_INFO_2bis, '550602bfe809b3ff00000000000000000000007900002b'O);
	si_cfg.si2ter_present := true;
	f_rsl_bcch_fill_raw(RSL_SYSTEM_INFO_2ter, '010603bf66b0aa0a00000002000000000000002b2b2b2b'O);
	si_cfg.si2quater_present := true;
	f_rsl_bcch_fill_raw(RSL_SYSTEM_INFO_2quater, '050607a8a0364aa698d72ff424feee0506d5e7fff02043'O);
	si_cfg.si13_present := true;
	f_rsl_bcch_fill_raw(RSL_SYSTEM_INFO_13, '0106009000185a6fc9e08410ab2b2b2b2b2b2b2b2b2b2b'O);
	f_TC_si_sched();
	Misc_Helpers.f_shutdown(__BFILE__, __LINE__);
}


testcase TC_bcch_info() runs on test_CT {
	f_init();
	/* FIXME: enable / disable individual BCCH info */
	//ts_RSL_BCCH_INFO(si_type, info);
	/* expect no ERROR REPORT after either of them *
	/* negative test: ensure ERROR REPORT on unsupported types */
	Misc_Helpers.f_shutdown(__BFILE__, __LINE__);
}

/***********************************************************************
 * Low-Level Protocol Errors / ERROR REPORT
 ***********************************************************************/

private function f_exp_err_rep(template RSL_Cause cause) runs on test_CT {
	timer T := 5.0;
	T.start;
	alt {
	[] RSL_CCHAN.receive(tr_RSL_UD(tr_RSL_ERROR_REPORT(cause))) {
		setverdict(pass);
		}
	[] RSL_CCHAN.receive(tr_RSL_UD(tr_RSL_ERROR_REPORT(?))) {
		Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, "Wrong cause in RSL ERR REP");
		}
	[] RSL_CCHAN.receive {
		repeat;
		}
	[] T.timeout {
		Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, "Timeout waiting for RSL ERR REP");
		}
	}
}

/* Provoke a protocol error (message too short) and match on ERROR REPORT */
testcase TC_rsl_protocol_error() runs on test_CT {
	f_init();
	var RSL_Message rsl := valueof(ts_RSL_BCCH_INFO(RSL_SYSTEM_INFO_1, ''O));
	rsl.ies := omit;
	RSL_CCHAN.send(ts_RSL_UD(rsl));

	f_exp_err_rep(RSL_ERR_PROTO);
}

/* Provoke a mandatory IE error and match on ERROR REPORT */
testcase TC_rsl_mand_ie_error() runs on test_CT {
	f_init();

	var RSL_Message rsl := valueof(ts_RSL_BCCH_INFO(RSL_SYSTEM_INFO_1, ''O));
	rsl.ies := { rsl.ies[0] };
	RSL_CCHAN.send(ts_RSL_UD(rsl));

	f_exp_err_rep(RSL_ERR_MAND_IE_ERROR);
}

/* Provoke an IE content error and match on ERROR REPORT */
testcase TC_rsl_ie_content_error() runs on test_CT {
	f_init();
	var RSL_Message rsl := valueof(ts_RSL_BCCH_INFO(RSL_SYSTEM_INFO_1, ''O));
	rsl.ies[1].body.sysinfo_type := RSL_SYSTEM_INFO_5;
	RSL_CCHAN.send(ts_RSL_UD(rsl));

	f_exp_err_rep(RSL_ERR_IE_CONTENT);
}

/* attempt to activate channel with wrong RSL Message Discriminator IE */
function f_TC_chan_act_wrong_mdisc(charstring id) runs on ConnHdlr {
	var template RSL_Message rsl := ts_RSL_CHAN_ACT(g_chan_nr, g_pars.chan_mode);
	rsl.msg_disc := ts_RSL_MsgDisc(RSL_MDISC_RESERVED, false);
	RSL.send(rsl);
	f_rslem_unregister(0, g_chan_nr);
}
testcase TC_err_rep_wrong_mdisc() runs on test_CT {
	var ConnHdlr vc_conn;
	var ConnHdlrPars pars := valueof(t_Pars(ts_RslChanNr_SDCCH4(0,0), ts_RSL_ChanMode_SIGN));

	f_init();

	vc_conn := f_start_handler(refers(f_TC_chan_act_wrong_mdisc), pars);
	vc_conn.done;
	f_exp_err_rep(RSL_ERR_MSG_DISCR);

	Misc_Helpers.f_shutdown(__BFILE__, __LINE__);
}

/* Send messages with wrong message type */
function f_TC_wrong_msg_type_dchan(charstring id) runs on ConnHdlr {
	var template (value) RSL_Message rsl_tx;
	rsl_tx := ts_RSL_CHAN_ACT(g_chan_nr, g_pars.chan_mode);
	rsl_tx.msg_type := RSL_MT_NOT_CMD;
	RSL.send(rsl_tx);
	f_rslem_unregister(0, g_chan_nr);
}
function f_TC_wrong_msg_type_rll(charstring id) runs on ConnHdlr {
	var template (value) RSL_Message rsl_tx;
	/* we first have to activate the dedicated channel */
	f_rsl_chan_act(g_pars.chan_mode);
	/* ... to then send an invalid RLL message */
	rsl_tx := ts_RSL_UNITDATA_REQ(g_chan_nr, ts_RslLinkID_DCCH(0), '0102'O);
	rsl_tx.msg_type := RSL_MT_CBCH_LOAD_IND;
	RSL.send(rsl_tx);
	f_rslem_unregister(0, g_chan_nr);
}
testcase TC_err_rep_wrong_msg_type() runs on test_CT {
	var ConnHdlr vc_conn;
	var ConnHdlrPars pars := valueof(t_Pars(ts_RslChanNr_SDCCH4(0,0), ts_RSL_ChanMode_SIGN));
	var template (value) RSL_Message rsl_tx;

	f_init();

	/* Common Channel with wrong message type */
	RSL_CCHAN.clear;
	rsl_tx := valueof(ts_RSL_BCCH_INFO(RSL_SYSTEM_INFO_1, ''O));
	rsl_tx.msg_type := RSL_MT_LOCATION_INFO;
	RSL_CCHAN.send(ts_RSL_UD(rsl_tx));
	f_exp_err_rep(RSL_ERR_MSG_TYPE);

	/* TRX Management */
	RSL_CCHAN.clear;
	rsl_tx := ts_RSL_SACCH_FILL(RSL_SYSTEM_INFO_5, ''O);
	rsl_tx.msg_type := RSL_MT_UNIT_DATA_IND;
	RSL_CCHAN.send(ts_RSL_UD(rsl_tx));
	f_exp_err_rep(RSL_ERR_MSG_TYPE);

	/* Dedicated Channel */
	RSL_CCHAN.clear;
	vc_conn := f_start_handler(refers(f_TC_wrong_msg_type_dchan), pars);
	vc_conn.done;
	f_exp_err_rep(RSL_ERR_MSG_TYPE);

	/* RLL */
	RSL_CCHAN.clear;
	vc_conn := f_start_handler(refers(f_TC_wrong_msg_type_rll), pars);
	vc_conn.done;
	f_exp_err_rep(RSL_ERR_MSG_TYPE);
}

/* Send messages in wrong sequence (RLL to an inactive lchan) */
function f_TC_err_rep_wrong_sequence(charstring id) runs on ConnHdlr {
	RSL.send(ts_RSL_UNITDATA_REQ(g_chan_nr, ts_RslLinkID_DCCH(0), '0102'O));
	f_rslem_unregister(0, g_chan_nr);
}
testcase TC_err_rep_wrong_sequence() runs on test_CT {
	var ConnHdlr vc_conn;
	var ConnHdlrPars pars := valueof(t_Pars(ts_RslChanNr_SDCCH4(0,0), ts_RSL_ChanMode_SIGN));

	f_init();

	RSL_CCHAN.clear;
	vc_conn := f_start_handler(refers(f_TC_err_rep_wrong_sequence), pars);
	vc_conn.done;
	f_exp_err_rep(RSL_ERR_MSG_SEQ);
}

/***********************************************************************
 * IPA CRCX/MDCX/DLCS media stream handling
 ***********************************************************************/

/* Send IPA DLCX to inactive lchan */
function f_TC_ipa_dlcx_not_active(charstring id) runs on ConnHdlr {
	f_rsl_transceive(ts_RSL_IPA_DLCX(g_chan_nr, 0), tr_RSL_IPA_DLCX_ACK(g_chan_nr, ?, ?),
			 "IPA DLCX ACK");
}
testcase TC_ipa_dlcx_not_active() runs on test_CT {
	var ConnHdlrPars pars := valueof(t_Pars(t_RslChanNr_Bm(1), ts_RSL_ChanMode_SIGN));
	f_init();
	var ConnHdlr vc_conn := f_start_handler(refers(f_TC_ipa_dlcx_not_active), pars);
	vc_conn.done;
}

/* Send IPA CRCX twice to inactive lchan */
function f_TC_ipa_crcx_twice_not_active(charstring id) runs on ConnHdlr {
	f_rsl_transceive(ts_RSL_IPA_CRCX(g_chan_nr), tr_RSL_IPA_CRCX_ACK(g_chan_nr, ?, ?, ?),
			 "IPA CRCX ACK");
	f_rsl_transceive(ts_RSL_IPA_CRCX(g_chan_nr), tr_RSL_IPA_CRCX_NACK(g_chan_nr, RSL_ERR_RES_UNAVAIL),
			 "IPA CRCX NACK");
}
testcase TC_ipa_crcx_twice_not_active() runs on test_CT {
	var ConnHdlrPars pars := valueof(t_Pars(t_RslChanNr_Bm(1), ts_RSL_ChanMode_SIGN));
	f_init();
	var ConnHdlr vc_conn := f_start_handler(refers(f_TC_ipa_crcx_twice_not_active), pars);
	vc_conn.done;
}

/* Regular sequence of CRCX/MDCX/DLCX */
function f_TC_ipa_crcx_mdcx_dlcx_not_active(charstring id) runs on ConnHdlr {
	f_rsl_transceive(ts_RSL_IPA_CRCX(g_chan_nr), tr_RSL_IPA_CRCX_ACK(g_chan_nr, ?, ?, ?),
			 "IPA CRCX ACK");
	var uint32_t remote_ip := f_rnd_int(c_UINT32_MAX);
	var uint16_t remote_port := f_rnd_int(c_UINT16_MAX);
	var uint7_t rtp_pt2 := f_rnd_int(127);
	var uint16_t fake_conn_id := 23; /* we're too lazy to read it out from the CRCX ACK above */
	f_rsl_transceive(ts_RSL_IPA_MDCX(g_chan_nr, fake_conn_id, remote_ip, remote_port, rtp_pt2),
			 tr_RSL_IPA_MDCX_ACK(g_chan_nr, ?, ?, ?, rtp_pt2),
			 "IPA MDCX ACK");
	f_rsl_transceive(ts_RSL_IPA_DLCX(g_chan_nr, fake_conn_id), tr_RSL_IPA_DLCX_ACK(g_chan_nr, ?, ?),
			 "IPA DLCX ACK");
}
testcase TC_ipa_crcx_mdcx_dlcx_not_active() runs on test_CT {
	var ConnHdlrPars pars := valueof(t_Pars(t_RslChanNr_Bm(1), ts_RSL_ChanMode_SIGN));
	f_init();
	var ConnHdlr vc_conn := f_start_handler(refers(f_TC_ipa_crcx_mdcx_dlcx_not_active), pars);
	vc_conn.done;
}

/* Sequence of CRCX, 2x MDCX, DLCX */
function f_TC_ipa_crcx_mdcx_mdcx_dlcx_not_active(charstring id) runs on ConnHdlr {
	f_rsl_transceive(ts_RSL_IPA_CRCX(g_chan_nr), tr_RSL_IPA_CRCX_ACK(g_chan_nr, ?, ?, ?),
			 "IPA CRCX ACK");
	var uint32_t remote_ip := f_rnd_int(c_UINT32_MAX);
	var uint16_t remote_port := f_rnd_int(c_UINT16_MAX);
	var uint7_t rtp_pt2 := f_rnd_int(127);
	var uint16_t fake_conn_id := 23; /* we're too lazy to read it out from the CRCX ACK above */
	f_rsl_transceive(ts_RSL_IPA_MDCX(g_chan_nr, fake_conn_id, remote_ip, remote_port, rtp_pt2),
			 tr_RSL_IPA_MDCX_ACK(g_chan_nr, ?, ?, ?, rtp_pt2),
			 "IPA MDCX ACK");
	/* Second MDCX */
	remote_ip := f_rnd_int(c_UINT32_MAX);
	remote_port := f_rnd_int(c_UINT16_MAX);
	f_rsl_transceive(ts_RSL_IPA_MDCX(g_chan_nr, fake_conn_id, remote_ip, remote_port, rtp_pt2),
			 tr_RSL_IPA_MDCX_ACK(g_chan_nr, ?, ?, ?, rtp_pt2),
			 "IPA MDCX ACK");
	f_rsl_transceive(ts_RSL_IPA_DLCX(g_chan_nr, fake_conn_id), tr_RSL_IPA_DLCX_ACK(g_chan_nr, ?, ?),
			 "IPA DLCX ACK");
}
testcase TC_ipa_crcx_mdcx_mdcx_dlcx_not_active() runs on test_CT {
	var ConnHdlrPars pars := valueof(t_Pars(t_RslChanNr_Bm(1), ts_RSL_ChanMode_SIGN));
	f_init();
	var ConnHdlr vc_conn := f_start_handler(refers(f_TC_ipa_crcx_mdcx_mdcx_dlcx_not_active), pars);
	vc_conn.done;
}

/* IPA CRCX on SDCCH/4 and SDCCH/8 (doesn't make sense) */
function f_TC_ipa_crcx_sdcch_not_active(charstring id) runs on ConnHdlr {
	f_rsl_transceive(ts_RSL_IPA_CRCX(g_chan_nr), tr_RSL_IPA_CRCX_NACK(g_chan_nr, ?),
			 "IPA CRCX NACK");
}
testcase TC_ipa_crcx_sdcch_not_active() runs on test_CT {
	var ConnHdlrPars pars;
	var ConnHdlr vc_conn;
	f_init();

	pars := valueof(t_Pars(t_RslChanNr_SDCCH4(0,1), ts_RSL_ChanMode_SIGN));
	vc_conn := f_start_handler(refers(f_TC_ipa_crcx_sdcch_not_active), pars);
	vc_conn.done;

	pars := valueof(t_Pars(t_RslChanNr_SDCCH8(6,5), ts_RSL_ChanMode_SIGN));
	vc_conn := f_start_handler(refers(f_TC_ipa_crcx_sdcch_not_active), pars);
	vc_conn.done;
}


/***********************************************************************
 * PCU Socket related tests
 ***********************************************************************/

/* Verify no RTS before ACT_REQ; verify RTS after ACT_REQ */
friend function f_TC_pcu_act_req(uint8_t bts_nr, uint8_t trx_nr, uint8_t ts_nr, boolean exp_success)
runs on test_CT {
	timer T := 3.0;

	/* we don't expect any RTS.req before PDCH are active */
	T.start;
	alt {
	[] PCU.receive(t_SD_PCUIF(g_pcu_conn_id, tr_PCUIF_RTS_REQ(bts_nr))) {
		Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, "PCU RTS.req before PDCH active?");
		}
	[] PCU.receive { repeat; }
	[] T.timeout { }
	}

	/* Send PDCH activate request for known PDCH timeslot */
	PCU.send(t_SD_PCUIF(g_pcu_conn_id, ts_PCUIF_ACT_REQ(bts_nr, trx_nr, ts_nr)));

	/* we now expect RTS.req for this timeslot (only) */
	T.start;
	alt {
	[exp_success] PCU.receive(t_SD_PCUIF(g_pcu_conn_id, tr_PCUIF_RTS_REQ(bts_nr, trx_nr, ts_nr))) {
		setverdict(pass);
		}
	[not exp_success] PCU.receive(t_SD_PCUIF(g_pcu_conn_id,
						 tr_PCUIF_RTS_REQ(bts_nr, trx_nr, ts_nr))) {
		Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, "Unexpected RTS.req for supposedly failing activation");
		}
	[] PCU.receive(t_SD_PCUIF(g_pcu_conn_id, tr_PCUIF_RTS_REQ)) {
		Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, "RTS.req for wrong TRX/TS");
		}
	[] PCU.receive { repeat; }
	[exp_success] T.timeout {
		Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, "Timeout waiting for PCU RTS.req");
		}
	[not exp_success] T.timeout {
		setverdict(pass);
		}
	}
}

/* verify no more RTS after DEACT_REQ */
friend function f_TC_pcu_deact_req(uint8_t bts_nr, uint8_t trx_nr, uint8_t ts_nr)
runs on test_CT {
	timer T := 3.0;

	/* Send PDCH activate request for known PDCH timeslot */
	PCU.send(t_SD_PCUIF(g_pcu_conn_id, ts_PCUIF_DEACT_REQ(bts_nr, trx_nr, ts_nr)));

	PCU.clear;
	/* we now expect no RTS.req for this timeslot */
	T.start;
	alt {
	[] PCU.receive(t_SD_PCUIF(g_pcu_conn_id, tr_PCUIF_RTS_REQ(bts_nr, trx_nr, ts_nr))) {
		Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, "Received unexpected PCU RTS.req");
		}
	[] PCU.receive { repeat; }
	[] T.timeout {
		setverdict(pass);
		}
	}
}

friend function f_init_pcu_test() runs on test_CT {
	f_init();
	PCU.send(t_SD_PCUIF(g_pcu_conn_id, ts_PCUIF_TXT_IND(0, PCU_VERSION, testcasename())));
}

/* PDCH activation via PCU socket; check for presence of RTS.req */
testcase TC_pcu_act_req() runs on test_CT {
	f_init_pcu_test();

	f_TC_pcu_act_req(0, 0, 7, true);
}

/* PDCH activation via PCU socket on non-PDCU timeslot */
testcase TC_pcu_act_req_wrong_ts() runs on test_CT {
	f_init_pcu_test();

	f_TC_pcu_act_req(0, 0, 1, false);
}

/* PDCH activation via PCU socket on wrong BTS */
testcase TC_pcu_act_req_wrong_bts() runs on test_CT {
	f_init_pcu_test();

	f_TC_pcu_act_req(23, 0, 7, false);
}

/* PDCH activation via PCU socket on wrong TRX */
testcase TC_pcu_act_req_wrong_trx() runs on test_CT {
	f_init_pcu_test();

	f_TC_pcu_act_req(0, 23, 7, false);
}

/* PDCH deactivation via PCU socket; check for absence of RTS.req */
testcase TC_pcu_deact_req() runs on test_CT {
	f_init_pcu_test();

	/* Activate PDCH */
	f_TC_pcu_act_req(0, 0, 7, true);
	f_sleep(1.0);
	/* and De-Activate again */
	f_TC_pcu_deact_req(0, 0, 7);
}

/* Attempt to deactivate a PDCH on a non-PDCH timeslot */
testcase TC_pcu_deact_req_wrong_ts() runs on test_CT {
	f_init_pcu_test();

	f_TC_pcu_deact_req(0, 0, 1);
}

/* Test the PCU->BTS Version and BTS->PCU SI13 handshake */
testcase TC_pcu_ver_si13() runs on test_CT {
	const octetstring si13 := '00010203040506070909'O;
	var PCUIF_send_data sd;
	timer T:= 3.0;
	f_init_pcu_test();

	/* Set SI13 via RSL */
	f_rsl_bcch_fill_raw(RSL_SYSTEM_INFO_13, si13);

	T.start;
	alt {
	[] PCU.receive(t_SD_PCUIF(g_pcu_conn_id, tr_PCUIF_DATA_IND(0, 0, 0, ?, PCU_IF_SAPI_BCCH))) -> value sd {
		if (substr(sd.data.u.data_ind.data, 0, lengthof(si13)) == si13) {
			setverdict(pass);
		} else {
			repeat;
		}
		}
	[] PCU.receive { repeat; }
	[] T.timeout {
		Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, "Timeout waiting for SI13");
		}
	}
}

private const octetstring c_PCU_DATA := '000102030405060708090a0b0c0d0e0f10111213141516'O;

/* helper function to send a PCU DATA.req */
friend function f_pcu_data_req(uint8_t bts_nr, uint8_t trx_nr, uint8_t ts_nr,
				uint8_t block_nr, uint32_t fn, PCUIF_Sapi sapi, octetstring data)
runs on test_CT
{
	PCU.send(t_SD_PCUIF(g_pcu_conn_id,
			ts_PCUIF_DATA_REQ(bts_nr, trx_nr, ts_nr, block_nr, fn, sapi, data)));
}

/* helper function to wait for RTS.ind for given SAPI on given BTS/TRX/TS and then send */
friend function f_pcu_wait_rts_and_data_req(uint8_t bts_nr, uint8_t trx_nr, uint8_t ts_nr,
					    PCUIF_Sapi sapi, octetstring data)
runs on test_CT
{
	var PCUIF_send_data sd;

	timer T := 3.0;
	T.start;
	alt {
	[] PCU.receive(t_SD_PCUIF(g_pcu_conn_id,
				tr_PCUIF_RTS_REQ(bts_nr, trx_nr, ts_nr, sapi))) -> value sd {
		f_pcu_data_req(bts_nr, trx_nr, ts_nr, sd.data.u.rts_req.block_nr,
				  sd.data.u.rts_req.fn, sapi, data);
		}
	[] PCU.receive { repeat; }
	[] T.timeout {
		Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, "Timeout waiting for RTS.ind");
		}
	}
}

/* Send DATA.req on invalid BTS */
testcase TC_pcu_data_req_wrong_bts() runs on test_CT {
	var TfiUsfArr tua := f_TfiUsfArrInit();
	var octetstring data := '0000'O & f_rnd_octstring(21);

	f_virtphy_common();

	f_TC_pcu_act_req(0, 0, 7, true);
	f_TfiUsfArrSet(tua, 7, 0);
	f_L1CTL_TBF_CFG(L1CTL, false, tua);
	f_sleep(1.0);

	f_pcu_to_l1(23, 0, 7, PCU_IF_SAPI_PDTCH, data, false, false);
}

/* Send DATA.req on invalid TRX */
testcase TC_pcu_data_req_wrong_trx() runs on test_CT {
	var TfiUsfArr tua := f_TfiUsfArrInit();
	var octetstring data := '0000'O & f_rnd_octstring(21);

	f_virtphy_common();

	f_TC_pcu_act_req(0, 0, 7, true);
	f_TfiUsfArrSet(tua, 7, 0);
	f_L1CTL_TBF_CFG(L1CTL, false, tua);
	f_sleep(1.0);

	f_pcu_to_l1(0, 100, 7, PCU_IF_SAPI_PDTCH, data, false, false);
}

/* Send DATA.req on invalid timeslot */
testcase TC_pcu_data_req_wrong_ts() runs on test_CT {
	var TfiUsfArr tua := f_TfiUsfArrInit();
	var octetstring data := '0000'O & f_rnd_octstring(21);

	f_virtphy_common();

	f_TC_pcu_act_req(0, 0, 7, true);
	f_TfiUsfArrSet(tua, 7, 0);
	f_L1CTL_TBF_CFG(L1CTL, false, tua);
	f_sleep(1.0);

	f_pcu_to_l1(0, 0, 70, PCU_IF_SAPI_PDTCH, data, false, false);
}

/* Send DATA.req on timeslot that hasn't been activated */
testcase TC_pcu_data_req_ts_inactive() runs on test_CT {
	var TfiUsfArr tua := f_TfiUsfArrInit();
	var octetstring data := '0000'O & f_rnd_octstring(21);

	f_virtphy_common();

	f_TfiUsfArrSet(tua, 7, 0);
	f_L1CTL_TBF_CFG(L1CTL, false, tua);
	f_sleep(1.0);

	f_pcu_to_l1(0, 0, 7, PCU_IF_SAPI_PDTCH, data, false, false);
}

private function f_pcu_to_l1(uint8_t bts_nr, uint8_t trx_nr, uint8_t ts_nr,
			     PCUIF_Sapi sapi, octetstring data, boolean expect_data := true,
			     boolean wait_rts := true)
runs on test_CT {
	timer T := 5.0;
	var L1ctlDlMessage rx_dl;

	PCU.clear;
	if (wait_rts) {
		f_pcu_wait_rts_and_data_req(bts_nr, trx_nr, ts_nr, sapi, data);
	} else {
		f_pcu_data_req(bts_nr, trx_nr, ts_nr, 0, 0, sapi, data);
	}

	T.start;
	alt {
	[expect_data] L1CTL.receive(tr_L1CTL_DATA_IND(t_RslChanNr_PDCH(ts_nr), ?, data)) {
		/* FIXME: why is fn of DATA_IND different to fn of RTS / DATA_REQ above? */
		setverdict(pass);
		}
	[not expect_data] L1CTL.receive(tr_L1CTL_DATA_IND(t_RslChanNr_PDCH(ts_nr), ?, data)) -> value rx_dl {
		setverdict(fail, "Received unexpected ", rx_dl);
		}
	[] L1CTL.receive {
		repeat;
		}
	[expect_data] T.timeout {
		setverdict(fail, "Timeout waiting for ", data);
		}
	[not expect_data] T.timeout {
		setverdict(pass);
		}
	}
}

private function f_disable_dynamic_ts() runs on test_CT
{
	f_init_vty_bsc();
	/* I'm not quite sure why we need this with osmo-bts-virtual.  Somehow it deosn't seem to
	 * support dynamic timeslots?  But it uses the same scheduler as osmo-bts-trx ?!? */
	f_vty_config2(BSCVTY, {"network", "bts 0", "trx 0", "timeslot 3"}, "phys_chan_config TCH/F");
	f_vty_config2(BSCVTY, {"network", "bts 0", "trx 0", "timeslot 4"}, "phys_chan_config TCH/F");
	f_init_pcu_test();
}

private function f_virtphy_common() runs on test_CT {
	f_disable_dynamic_ts();
	f_init_l1ctl();
	f_l1_tune(L1CTL);
}

testcase TC_pcu_data_req_pdtch() runs on test_CT {
	var TfiUsfArr tua := f_TfiUsfArrInit();
	var octetstring data := '0000'O & f_rnd_octstring(21);

	f_virtphy_common();

	f_TC_pcu_act_req(0, 0, 7, true);
	f_TfiUsfArrSet(tua, 7, 0);
	f_L1CTL_TBF_CFG(L1CTL, false, tua);
	f_sleep(1.0);

	f_pcu_to_l1(0, 0, 7, PCU_IF_SAPI_PDTCH, data); //c_PCU_DATA);
}

/* FIXME: PTTCH has nothing to do with TBFs */
testcase TC_pcu_data_req_ptcch() runs on test_CT {
	var TfiUsfArr tua := f_TfiUsfArrInit();
	var octetstring data := '0000'O & f_rnd_octstring(21);

	f_virtphy_common();

	f_TC_pcu_act_req(0, 0, 7, true);
	f_TfiUsfArrSet(tua, 7, 0);
	f_L1CTL_TBF_CFG(L1CTL, false, tua);
	f_sleep(1.0);

	f_pcu_to_l1(0, 0, 7, PCU_IF_SAPI_PTCCH, data);
}

private function f_TC_pcu_ptcch_ul(uint16_t ra)
runs on test_CT {
	var template PCUIF_Message pcu_rach_ind;
	var PCUIF_send_data sd;
	var GsmFrameNumber fn;
	timer T;

	/* Send an Access Burst on PTCCH/U over the Um-interface */
	fn := f_L1CTL_RACH(L1CTL, ra := ra, combined := 0, offset := 0,
			   chan_nr := ts_RslChanNr_PDCH(7),
			   link_id := ts_RslLinkID_OSMO_PTCCH(0));

	pcu_rach_ind := tr_PCUIF_RACH_IND(bts_nr := 0, trx_nr := 0, ts_nr := 7,
					  ra := ra, fn := fn, sapi := PCU_IF_SAPI_PTCCH);

	/* Expect a RACH.ind on the PCU interface (timeout is one multi-frame) */
	T.start(52.0 * 4.615 / 1000.0);
	alt {
	[] PCU.receive(t_SD_PCUIF(g_pcu_conn_id, pcu_rach_ind)) -> value sd {
		log("Rx an Access Burst on the PCU interface: ", sd.data);
		setverdict(pass);
		T.stop;
		}
	[] PCU.receive { repeat; }
	[] T.timeout {
		setverdict(fail, "Timeout waiting for RACH.ind on the PCU interface");
		/* Keep going, that's not the end of the world */
		}
	}
}

testcase TC_pcu_ptcch() runs on test_CT {
	var L1ctlDlMessage dl;
	var octetstring data;
	timer T;

	f_init_pcu_test();
	f_init_l1ctl();
	f_l1_tune(L1CTL);

	/* Activate PDCH channel on TS7 */
	f_TC_pcu_act_req(0, 0, 7, true);

	/* Tune trxcon to that PDCH channel */
	L1CTL.send(ts_L1CTL_DM_EST_REQ(arfcn := { false, mp_trx0_arfcn },
				       chan_nr := valueof(ts_RslChanNr_PDCH(7)),
				       tsc := 7));

	/* Verify PTCCH/U: send several access bursts, make sure they're received */
	for (var integer i := 0; i < 16; i := i + 1) {
		log("Sending an Access Burst towards the L1CTL interface");
		f_TC_pcu_ptcch_ul(oct2int(f_rnd_ra_ps()));
	}

	/* Generate a random payload for PTCCH/D (23 octets, CS-1) */
	data := f_rnd_octstring(23);

	/* Verify PTCCH/D: send a random data block, make sure it's received */
	log("Sending a PTCCH/D block towards the PCU interface: ", data);
	f_pcu_wait_rts_and_data_req(0, 0, 7, PCU_IF_SAPI_PTCCH, data);

	/* PTCCH/D period is 2 multi-frames (2 * 52 * 4.615 ms), but
	 * let's give it more time in case if we miss the beginning. */
	T.start(2.0 * 2.0 * 52.0 * 4.615 / 1000.0);
	alt {
	/* PDCH is considered as traffic in trxcon => expect TRAFFIC.ind */
	[] L1CTL.receive(tr_L1CTL_TRAFFIC_IND(chan_nr := t_RslChanNr_PDCH(7),
					      link_id := tr_RslLinkID_OSMO_PTCCH(?),
					      frame := data)) -> value dl {
		log("Rx PTCCH/D data (traffic) block on L1CTL: ", dl);
		setverdict(pass);
		T.stop;
		}
	/* Other PHYs (e.g. virt_phy) may consider PDCH as data => expect DATA.ind */
	[] L1CTL.receive(tr_L1CTL_DATA_IND(chan_nr := t_RslChanNr_PDCH(7),
					   link_id := tr_RslLinkID_OSMO_PTCCH(?),
					   l2_data := data)) -> value dl {
		log("Rx PTCCH/D data block on L1CTL: ", dl);
		setverdict(pass);
		T.stop;
		}
	[] L1CTL.receive { repeat; }
	[] T.timeout {
		setverdict(fail, "Timeout waiting for DATA.ind on L1CTL");
		}
	}
}

/* Send AGCH from PCU; check it appears on Um side */
testcase TC_pcu_data_req_agch() runs on test_CT {
	timer T := 3.0;
	f_init_pcu_test();
	f_init_l1ctl();
	f_l1_tune(L1CTL);

	f_TC_pcu_act_req(0, 0, 7, true);
	f_pcu_data_req(0, 0, 7, 0, 0, PCU_IF_SAPI_AGCH, c_PCU_DATA);

	T.start;
	alt {
	[] L1CTL.receive(tr_L1CTL_DATA_IND(t_RslChanNr_PCH_AGCH(0), ?, c_PCU_DATA)) {
		setverdict(pass);
		}
	[] L1CTL.receive { repeat; }
	[] T.timeout {
		Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, "Timeout waiting for PCU-originated AGCH block on Um");
		}
	}
}

/* Send AGCH from PCU; check it appears on Um side */
testcase TC_pcu_data_req_pch() runs on test_CT {
	timer T := 3.0;
	f_init_pcu_test();
	f_init_l1ctl();
	f_l1_tune(L1CTL);

	f_TC_pcu_act_req(0, 0, 7, true);
	/* three characters prefix: last 3 digits of IMSI as ASCII */
	f_pcu_data_req(0, 0, 7, 0, 0, PCU_IF_SAPI_PCH, '313233'O & c_PCU_DATA);

	T.start;
	alt {
	[] L1CTL.receive(tr_L1CTL_DATA_IND(t_RslChanNr_PCH_AGCH(0), ?, c_PCU_DATA)) {
		setverdict(pass);
		}
	[] L1CTL.receive { repeat; }
	[] T.timeout {
		Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, "Timeout waiting for PCU-originated PCH block on Um");
		}
	}
}

/* Send IMM.ASS from PCU for PCH; check it appears on Um side */
testcase TC_pcu_data_req_imm_ass_pch() runs on test_CT {
	var octetstring imm_ass := f_rnd_octstring(23);
	f_init_pcu_test();
	f_init_l1ctl();
	f_l1_tune(L1CTL);

	/* append 3 last imsi digits so BTS can compute pagng group */
	var uint32_t fn := f_PCUIF_tx_imm_ass_pch(PCU, g_pcu_conn_id, imm_ass, '123459987'H);

	timer T := 0.5;
	T.start;
	alt {
	[] L1CTL.receive(tr_L1CTL_DATA_IND(t_RslChanNr_PCH_AGCH(0), ?, imm_ass)) {
		/* TODO: verify paging group */
		setverdict(pass);
		}
	[] L1CTL.receive { repeat; }
	[] T.timeout {
		Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, "Timeout waiting for PCU-originated AGCH block on Um");
		}
	}
}

/* Send RACH from Um side, expect it to show up on PCU socket */
testcase TC_pcu_rach_content() runs on test_CT {
	f_init_pcu_test();
	f_init_l1ctl();
	f_l1_tune(L1CTL);

	var GsmFrameNumber fn_last := 0;
	for (var integer i := 0; i < 1000; i := i+1) {
		var OCT1 ra := f_rnd_ra_ps();
		var GsmFrameNumber fn := f_L1CTL_RACH(L1CTL, oct2int(ra));
		if (fn == fn_last) {
			Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, "Two RACH in same FN?!?");
		}
		fn_last := fn;

		timer T := 2.0;
		T.start;
		alt {
		[] PCU.receive(t_SD_PCUIF(g_pcu_conn_id, tr_PCUIF_RACH_IND(0, 0, 0, oct2int(ra), 0, ?, fn))) {
			T.stop;
			}
		[] PCU.receive(t_SD_PCUIF(g_pcu_conn_id, tr_PCUIF_RACH_IND)) {
			Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, "Unexpected RACH IND");
			}
		[] PCU.receive { repeat; }
		[] T.timeout {
			Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, "Timeout waiting for RACH IND");
			}
		}
	}
	setverdict(pass);
}

/* Send extended (11-bit, TS1 & TS2) RACH bursts from the Um side,
 * expect them to show up on PCU socket (with proper BURST_TYPE_*). */
testcase TC_pcu_ext_rach_content() runs on test_CT {
	var template PCUIF_Message pcu_rach_ind;
	var GsmFrameNumber fn_last := 0;
	var L1ctlRachSynchSeq synch_seq;
	var PCUIF_BurstType pcu_bt;
	var GsmFrameNumber fn;
	var BIT11 ra11;

	f_init_pcu_test();
	f_init_l1ctl();
	f_l1_tune(L1CTL);

	for (var integer i := 0; i < 1000; i := i+1) {
		/* We need to test both TS1 & TS2 */
		if (i rem 2 == 0) {
			synch_seq := RACH_SYNCH_SEQ_TS1;
			pcu_bt := BURST_TYPE_1;
		} else {
			synch_seq := RACH_SYNCH_SEQ_TS2;
			pcu_bt := BURST_TYPE_2;
		}

		ra11 := f_rnd_ra11_ps();
		fn := f_L1CTL_EXT_RACH(L1CTL, bit2int(ra11), synch_seq);
		if (fn == fn_last) {
			Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail,
						"Two RACH in same FN?!?");
		}
		fn_last := fn;

		/* Compose the expected message */
		pcu_rach_ind := tr_PCUIF_RACH_IND(
			bts_nr := 0, trx_nr := 0, ts_nr := 0,
			ra := bit2int(ra11),
			is_11bit := 1,
			burst_type := pcu_bt,
			fn := fn);

		timer T := 2.0;
		T.start;
		alt {
		[] PCU.receive(t_SD_PCUIF(g_pcu_conn_id, pcu_rach_ind)) {
			T.stop;
			}
		[] PCU.receive(t_SD_PCUIF(g_pcu_conn_id, tr_PCUIF_RACH_IND)) {
			Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, "Unexpected RACH IND");
			}
		[] PCU.receive { repeat; }
		[] T.timeout {
			Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, "Timeout waiting for RACH IND");
			}
		}
	}
	setverdict(pass);
}

private function f_TC_pcu_data_ind_lqual_cb(int16_t lqual_cb_exp, int16_t thresh)
runs on test_CT {
	var template PCUIF_send_data sdt;
	var PCUIF_send_data sd;
	var int16_t lqual_cb;
	timer T := 1.0;

	/* PCUIF_DATA.ind is encapsulated into a supplementary record */
	sdt := t_SD_PCUIF_MSGT(g_pcu_conn_id, PCU_IF_MSG_DATA_IND);

	/* Send a random PDTCH frame over Um */
	L1CTL.send(ts_L1CTL_TRAFFIC_REQ(ts_RslChanNr_PDCH(7), ts_RslLinkID_DCCH(0),
					'0000'O & f_rnd_octstring(21)));

	T.start;
	alt {
	/* If expected link quality is above the threshold */
	[lqual_cb_exp >= thresh] PCU.receive(sdt) -> value sd {
		lqual_cb := sd.data.u.data_ind.lqual_cb;
		log("Rx PCUIF_DATA.ind (lqual_cb=", lqual_cb, ")");

		/* Make sure the actual link quality matches the expected value */
		if (not match(lqual_cb, lqual_cb_exp)) {
			setverdict(fail, log2str("Link quality ", lqual_cb, " does not match ",
						 "expected value ", lqual_cb_exp));
		} else {
			setverdict(pass);
		}
		}
	/* If expected link quality is below the threshold */
	[lqual_cb_exp < thresh] PCU.receive(sdt) -> value sd {
		Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail,
					log2str("Rx unexpected PCUIF_DATA.ind: ", sd.data));
		}
	/* Ignore PCUIF_RTS.req and PCUIF_TIME.ind */
	[] PCU.receive { repeat; }
	[lqual_cb_exp < thresh] T.timeout {
		log("Rx nothing, as expected");
		setverdict(pass);
		}
	[lqual_cb_exp >= thresh] T.timeout {
		Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail,
					"Timeout waiting for PCUIF_DATA.ind");
		}
	}
}

/* Verify C/I (Carrier-to-Interference ratio) processing of PDTCH frames */
testcase TC_pcu_data_ind_lqual_cb() runs on test_CT {
	f_init_pcu_test();
	PCU.clear;

	f_init_l1ctl();
	f_l1_tune(L1CTL);

	/* Activate a PDCH channel on TS7 */
	f_TC_pcu_act_req(0, 0, 7, true);

	/* Tune trxcon to that PDCH channel on TS7 */
	f_L1CTL_DM_EST_REQ(L1CTL, { false, mp_trx0_arfcn },
			   valueof(ts_RslChanNr_PDCH(7)), 7);

	/* C/I in centiBels, test range: -256 .. +1280, step 128 */
	for (var int16_t i := -256; i <= 1280; i := i + 128) {
		var TrxcMessage ret;

		ret := f_TRXC_transceive(BTS_TRXC, g_bts_trxc_conn_id,
					 valueof(ts_TRXC_FAKE_CI(i)));

		/* FIXME: OsmoBTS may have different threshold (see MIN_QUAL_NORM) */
		f_TC_pcu_data_ind_lqual_cb(i, thresh := 0);
	}
}

/* Send PAGING via RSL, expect it to shw up on PCU socket */
testcase TC_pcu_paging_from_rsl() runs on test_CT {
	f_init_pcu_test();

	for (var integer i := 0; i < 100; i := i+1) {
		var MobileIdentityLV mi_lv;
		var octetstring mi_lv_enc;
		var MobileIdentityV mi;
		timer T := 3.0;

		if (i < 50) {
			mi := valueof(t_MI_TMSI(f_rnd_octstring(4)));
		} else {
			mi := valueof(ts_MI_IMSI(f_gen_imsi(i)));
		}

		/* Fancy encoding for PCUIF */
		mi_lv := valueof(ts_MI_LV(mi));
		mi_lv_enc := enc_MobileIdentityLV(mi_lv);
		mi_lv_enc := f_pad_oct(mi_lv_enc, 9, '00'O);

		/* Send RSL PAGING COMMAND */
		RSL_CCHAN.send(ts_RSL_UD(ts_RSL_PAGING_CMD(mi, i mod 4)));
		T.start;
		alt {
		[] PCU.receive(t_SD_PCUIF(g_pcu_conn_id, tr_PCUIF_PAG_REQ(0, mi_lv_enc))) {
			}
		[] PCU.receive(t_SD_PCUIF(g_pcu_conn_id, tr_PCUIF_PAG_REQ)) {
			Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, "Unexpected PAGING REQ");
			}
		[] PCU.receive { repeat; }
		[] T.timeout {
			Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, "Timeout waiting for PAGING REQ");
			}
		}
	}
	setverdict(pass);
}

/* test for periodic TIME_IND; check number of FN expired and number of TIME_IND within frames */
testcase TC_pcu_time_ind() runs on test_CT {
	var PCUIF_send_data pcu_sd;
	var integer num_time_ind := 0;
	var integer first_fn, last_fn;
	var float test_duration := 5.0;
	timer T;

	f_init_pcu_test();
	f_TC_pcu_act_req(0, 0, 7, true);

	PCU.clear;
	T.start(test_duration);
	alt {
	[] PCU.receive(t_SD_PCUIF(g_pcu_conn_id, tr_PCUIF_TIME_IND(0, ?))) -> value pcu_sd {
		num_time_ind := num_time_ind + 1;
		if (not isbound(first_fn)) {
			first_fn := pcu_sd.data.u.time_ind.fn;
		}
		last_fn := pcu_sd.data.u.time_ind.fn;
		repeat;
		}
	[] PCU.receive(t_SD_PCUIF(g_pcu_conn_id, tr_PCUIF_TIME_IND(?, ?))) -> value pcu_sd {
		setverdict(fail, "Received unexpected PCUIF_TIME_IND: ", pcu_sd.data);
		repeat;
		}
	[] PCU.receive {
		repeat;
		}
	[] T.timeout {}
	}
	var integer fn_expired := last_fn - first_fn;
	log(fn_expired, " fn expired with ", num_time_ind, " PCU_TIME.ind");

	/* verify the number of frames expired matches our expectation */
	const float c_GSM_FN_DURATION_MS := 4.61538;
	var float fn_expected := test_duration * 1000.0 / c_GSM_FN_DURATION_MS;
	var template integer t_fn_expected := f_tolerance(float2int(fn_expected), 1, 100000, 20);
	if (not match(fn_expired, t_fn_expected)) {
		setverdict(fail, "Number of TDMA Frames (", fn_expired, ") not matching ", t_fn_expected);
	}

	/* There are three TIME.ind in every fn MOD 13 */
	var float time_ind_expected := int2float(fn_expired) * 3.0 / 13.0;
	/* Add some tolerance */
	var template integer t_time_ind_exp := f_tolerance(float2int(time_ind_expected), 1, 100000, 5);
	if (not match(num_time_ind, t_time_ind_exp)) {
		setverdict(fail, "Number of TIME.ind (", num_time_ind, ") not matching ", t_time_ind_exp);
	}

	setverdict(pass);
}

/* test for periodic RTS_REQ; check number of FN expired and number of RTS_IND per SAPI */
testcase TC_pcu_rts_req() runs on test_CT {
	var PCUIF_send_data pcu_sd;
	var integer first_fn, last_fn;
	var integer num_rts_pdtch := 0;
	var integer num_rts_ptcch := 0;
	var float test_duration := 5.0;
	timer T;

	f_init_pcu_test();
	f_TC_pcu_act_req(0, 0, 7, true);

	PCU.clear;
	T.start(test_duration);
	alt {
	[] PCU.receive(t_SD_PCUIF(g_pcu_conn_id, tr_PCUIF_RTS_REQ(0, 0, 7, PCU_IF_SAPI_PDTCH, ?, ?)))
			-> value pcu_sd {
		num_rts_pdtch := num_rts_pdtch + 1;
		if (not isbound(first_fn)) {
			first_fn := pcu_sd.data.u.rts_req.fn;
		}
		last_fn := pcu_sd.data.u.rts_req.fn;
		repeat;
		}
	[] PCU.receive(t_SD_PCUIF(g_pcu_conn_id, tr_PCUIF_RTS_REQ(0, 0, 7, PCU_IF_SAPI_PTCCH, ?, ?)))
			-> value pcu_sd {
		num_rts_ptcch := num_rts_ptcch + 1;
		if (not isbound(first_fn)) {
			first_fn := pcu_sd.data.u.rts_req.fn;
		}
		last_fn := pcu_sd.data.u.rts_req.fn;
		repeat;
		}
	[] PCU.receive(t_SD_PCUIF(g_pcu_conn_id, tr_PCUIF_RTS_REQ)) -> value pcu_sd {
		setverdict(fail, "Received unexpected PCUIF_RTS_REQ: ", pcu_sd.data);
		repeat;
		}
	[] PCU.receive {
		repeat;
		}
	[] T.timeout {}
	}
	var integer fn_expired := last_fn - first_fn;
	log(fn_expired, " fn expired with num_rts_pdtch=", num_rts_pdtch,
		", num_rts_ptcch=", num_rts_ptcch);

	/* verify the number of frames expired matches our expectation */
	const float c_GSM_FN_DURATION_MS := 4.61538;
	var float fn_expected := test_duration * 1000.0 / c_GSM_FN_DURATION_MS;
	var template integer t_fn_expected := f_tolerance(float2int(fn_expected), 1, 100000, 20);
	if (not match(fn_expired, t_fn_expected)) {
		setverdict(fail, "Number of TDMA Frames (", fn_expired, ") not matching ", t_fn_expected);
	}

	/* PTCCH is in pos. 12 + 38 of 52-multiframe, but four slots/bursts required per block */
	var float ptcch_expected := int2float(fn_expired) / 52.0 * 0.5;
	var template integer t_ptcch_exp := f_tolerance(float2int(ptcch_expected), 1, 100000, 1);
	if (not match(num_rts_ptcch, t_ptcch_exp)) {
		setverdict(fail, "Number of RTS.ind for PTCCH (", num_rts_ptcch, ") not matching ",
				t_ptcch_exp);
	}

	/* We have 12 PDTCH blocks every 52-multiframe */
	var float pdtch_expected := int2float(fn_expired) / 52.0 * 12.0;
	var template integer t_pdtch_exp := f_tolerance(float2int(pdtch_expected), 1, 100000, 2);
	if (not match(num_rts_pdtch, t_pdtch_exp)) {
		setverdict(fail, "Number of RTS.ind for PDTCH (", num_rts_pdtch, ") not matching ",
				t_pdtch_exp);
	}

	setverdict(pass);
}

/* test for generating Abis side OML ALERT from the PCU */
testcase TC_pcu_oml_alert() runs on test_CT {
	var PCUIF_send_data pcu_sd;
	var integer num_time_ind := 0;
	var integer first_fn, last_fn;
	var float test_duration := 5.0;
	timer T;

	f_init_pcu_test();
	f_TC_pcu_act_req(0, 0, 7, true);

	/* re-connect CTRL port from BTS to BSC */
	f_ipa_ctrl_stop();
	f_ipa_ctrl_start(mp_bsc_ctrl_ip, mp_bsc_ctrl_port);

	/* Send that OML Alert */
	PCU.send(t_SD_PCUIF(g_pcu_conn_id, ts_PCUIF_TXT_IND(0, PCU_OML_ALERT, testcasename())));

	/* This requires https://gerrit.osmocom.org/#/c/osmo-bsc/+/14177 to be merged */
	f_ctrl_exp_trap(IPA_CTRL, "bts.0.oml_failure_report", ?);
	setverdict(pass);
}

template (value) PDU_ML3_MS_NW ts_RRM_GprsSuspReq(template (value) OCT4 tlli,
						  template (value) RoutingAreaIdentificationV rai,
						  template (value) OCT1 cause) := {
	discriminator := '0000'B, /* overwritten */
	tiOrSkip := {
	skipIndicator := '0000'B
	},
	msgs := {
		rrm := {
			gPRS_suspensionRequest := {
				messageType := '00110100'B,
				tLLI := tlli,
				routingAreaIdentification := rai,
				suspensionCause := cause,
				service_Support := omit
			}
		}
	}
}

/* test for forwarding of RR SUSPEND from CS lchan to PCU via PCU socket */
private function f_TC_rr_suspend_req(charstring id) runs on ConnHdlr {
	var PCUIF_Message first_info;
	var integer pcu_conn_id := -1;
	var RslLinkId link_id := valueof(ts_RslLinkID_DCCH(0));
	var RoutingAreaIdentificationV rai := f_RAI('262'H, '42F'H, '2342'O, '55'O);
	var OCT4 tlli := '01020304'O;
	var OCT1 cause := '23'O;
	timer T := 5.0;

	f_init_pcu(PCU, id, pcu_conn_id, first_info);

	f_l1_tune(L1CTL);
	RSL.clear;

	f_est_dchan();
	L1CTL.clear;

	f_est_rll_mo(link_id.sapi, link_id, '23420815'O);

	var PDU_ML3_MS_NW susp_req := valueof(ts_RRM_GprsSuspReq(tlli, rai, cause));
	var octetstring l3 := enc_PDU_ML3_MS_NW(susp_req);
	f_tx_lapdm(ts_LAPDm_I(link_id.sapi, cr_MO_CMD, true, 1, 0, l3), link_id);

	/* ConnHdlr has terminated after sending the RR SUSP REQ over a dedicaed channel */
	T.start;
	alt {
	[] PCU.receive(t_SD_PCUIF(pcu_conn_id, tr_PCUIF_SUSP_REQ(0, tlli, ?, oct2int(cause)))) {
		setverdict(pass);
		}
	[] PCU.receive(t_SD_PCUIF(pcu_conn_id, tr_PCUIF_SUSP_REQ(?, ?, ?, ?))) {
		setverdict(fail, "Received unexpected PCUIF SUSPE REQ: ");
		}
	[] PCU.receive {
		repeat;
		}
	[] T.timeout {
		setverdict(fail, "Timeout waiting for SUSP REQ on PCUIF");
		}
	}

	/* release the channel */
	f_rsl_chan_deact();
	f_L1CTL_DM_REL_REQ(L1CTL, g_chan_nr);
	f_rslem_unregister(0, g_chan_nr);
}
testcase TC_pcu_rr_suspend() runs on test_CT {
	var ConnHdlrPars pars;
	var ConnHdlr vc_conn;

	f_init();

	pars := valueof(t_Pars(t_RslChanNr_SDCCH4(0,3), ts_RSL_ChanMode_SIGN));
	vc_conn := f_start_handler(refers(f_TC_rr_suspend_req), pars, true);
	vc_conn.done;
}

/* Ensure that PCUIF socket can accept only a single connection */
testcase TC_pcu_socket_connect_multi() runs on test_CT {
	timer T := 5.0;

	/* this (among other things) establishes the first connection to the PCUIF socket */
	f_init();

	/* try to establish a second connection, expect it to fail */
	PCU.send(UD_connect:{mp_pcu_socket, -1});
	T.start;
	alt {
	[] PCU.receive(UD_connect_result:{id := ?, result := { result_code := ERROR, err := ? }}) {
		setverdict(pass);
		}
	[] PCU.receive(UD_connect_result:?) {
		setverdict(fail, "Unexpected unix domain connect result");
		}
	[] T.timeout {
		setverdict(pass);
		}
	}
	Misc_Helpers.f_shutdown(__BFILE__, __LINE__);
}

/* Ensure that PCUIF socket can disconnect + reconnect */
testcase TC_pcu_socket_reconnect() runs on test_CT {
	/* this (among other things) establishes the first connection to the PCUIF socket */
	f_init();

	f_sleep(1.0);

	f_pcuif_close(PCU, g_pcu_conn_id);
	g_pcu_conn_id := -1;

	f_sleep(1.0);

	/* re-connect */
	PCU.clear;
	f_init_pcu(PCU, testcasename(), g_pcu_conn_id, g_pcu_last_info);
	setverdict(pass);

	Misc_Helpers.f_shutdown(__BFILE__, __LINE__);
}

/* Ensure that GPRS capability is not advertised before PCU socket conncet */
private function f_get_si3(L1CTL_PT pt) runs on test_CT return SystemInformationType3 {
	var L1ctlDlMessage l1_dl;
	var SystemInformation si;
	timer T := 5.0;
	T.start;
	alt {
	[] pt.receive(tr_L1CTL_DATA_IND(t_RslChanNr_BCCH(0), ?)) -> value l1_dl {
		/* somehow dec_SystemInformation will try to decode even non-RR as SI */
		if (not (l1_dl.payload.data_ind.payload[1] ==  '06'O)) {
			log("Ignoring non-RR SI ", l1_dl);
			repeat;
		}
		si := dec_SystemInformation(l1_dl.payload.data_ind.payload)
		if (not ischosen(si.payload.si3)) {
			repeat;
		}
		}
	[] pt.receive {
		repeat;
		}
	[] T.timeout {
		setverdict(fail, "Timeout waiting for SI3");
		}
	}
	return si.payload.si3;
}

/* CSN.1 L/H logic: is the bit at the current position using "inverted logic" (true) or not? */
private function f_bitpos_is_inv(integer idx) return boolean {
	select (idx mod 8) {
	case ((2, 4, 6, 7)) { return true; } /* 1-bits of 0x2B */
	case else { return false; } /* 0-bits of 0x2B */
	}
}
/* determine if the bit at position 'idx' in 'str' is a CSN.1 'H' (true) or 'L' (false) */
private function f_bit_is_high(bitstring str, integer idx) return boolean {
	var boolean invert := f_bitpos_is_inv(idx);
	if (invert) {
		if (str[idx] == '1'B) {
			return false;
		} else {
			return true;
		}
	} else {
		if (str[idx] == '1'B) {
			return true;
		} else {
			return false;
		}
	}
}
/* As the TITAN RAW codec cannot expres the CSN.1 L/H concept yet, we have to do this
   manually.  Let's hope https://www.eclipse.org/forums/index.php/t/1099087/ takes off and
   we can replace this piece of code soon ... */
private function f_si3_has_gprs_indicator(OCT4 si3_restoctets) return boolean {
	var bitstring bits := oct2bit(si3_restoctets);
	var integer idx := 0;

	if (f_bit_is_high(bits, idx)) {
		/* skip Optional selection parameters */
		idx := idx + 16;
	} else {
		idx := idx + 1;
	}

	if (f_bit_is_high(bits, idx)) {
		/* skip Optional power offset */
		idx := idx + 3;
	} else {
		idx := idx + 1;
	}

	/* skip SI2ter Indicator */
	idx := idx + 1;

	/* skip Early CM Sending Control */
	idx := idx + 1;

	/* skip Scheduling if and where */
	if (f_bit_is_high(bits, idx)) {
		idx := idx + 4;
	} else {
		idx := idx + 1;
	}

	return f_bit_is_high(bits, idx);
}

testcase TC_pcu_socket_noconnect_nosi3gprs() runs on test_CT {
	var SystemInformationType3 si3;
	timer T := 5.0;

	/* don't call f_init() as this would connect PCU socket */
	f_init_rsl(testcasename());
	T.start;
	alt {
	[] RSL_CCHAN.receive(ASP_IPA_Event:{up_down := ASP_IPA_EVENT_UP});
	[] T.timeout {
		Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, "Timeout waiting for ASP_IPA_EVENT_UP");
		}
	}
	f_rsl_bcch_fill(RSL_SYSTEM_INFO_3, ts_SI3_default);

	f_init_l1ctl();
	f_l1_tune(L1CTL);

	f_sleep(2.0);
	L1CTL.clear;
	si3 := f_get_si3(L1CTL);
	if (f_si3_has_gprs_indicator(si3.rest_octets)) {
		setverdict(fail, "SI3 indicates GPRS even before PCU socket connected");
	} else {
		setverdict(pass);
	}
	Misc_Helpers.f_shutdown(__BFILE__, __LINE__);
}

/* Ensure that GPRS capability is advertised after PCU socket connect */
testcase TC_pcu_socket_connect_si3gprs() runs on test_CT {
	var SystemInformationType3 si3;

	/* this (among other things) establishes the first connection to the PCUIF socket */
	f_init();
	f_init_l1ctl();
	f_l1_tune(L1CTL);

	f_sleep(2.0);
	L1CTL.clear;
	si3 := f_get_si3(L1CTL);
	if (not f_si3_has_gprs_indicator(si3.rest_octets)) {
		setverdict(fail, "SI3 indicates no GPRS despite PCU socket connected");
	} else {
		setverdict(pass);
	}
	Misc_Helpers.f_shutdown(__BFILE__, __LINE__);
}

/* Ensure that GPRS capability is no longer advertised after PCU socket disconnect */
testcase TC_pcu_socket_disconnect_nosi3gprs() runs on test_CT {
	var SystemInformationType3 si3;

	/* this (among other things) establishes the first connection to the PCUIF socket */
	f_init();
	f_init_l1ctl();
	f_l1_tune(L1CTL);

	f_pcuif_close(PCU, g_pcu_conn_id);
	g_pcu_conn_id := -1;

	f_sleep(1.0);

	/* re-connect */
	PCU.clear;
	f_init_pcu(PCU, testcasename(), g_pcu_conn_id, g_pcu_last_info);

	f_sleep(2.0);
	L1CTL.clear;
	si3 := f_get_si3(L1CTL);
	if (f_si3_has_gprs_indicator(si3.rest_octets)) {
		setverdict(fail, "SI3 indicates GPRS after PCU socket disconnected");
	} else {
		setverdict(pass);
	}

	Misc_Helpers.f_shutdown(__BFILE__, __LINE__);
}

/* Verify that the cell_id of SI3 (TS 04.08 9.1.35) and other values are passed properly to the PCU socket (OS#3854) */
testcase TC_pcu_socket_verify_info_ind() runs on test_CT {
	var SystemInformation si3 := valueof(ts_SI3_default);

	f_init();

	/* Verify cell_id */
	var uint16_t cell_id_si3 := si3.payload.si3.cell_id;
	var uint16_t cell_id_pcu := g_pcu_last_info.u.info_ind.cell_id;
	if (cell_id_si3 != cell_id_pcu) {
		setverdict(fail, "Expected cell_id '", cell_id_si3, "' and got '", cell_id_pcu, "'. This either means,",
				 " that the BTS is sending the wrong cell_id, or that the BTS sent it too early",
				 " (OS#4179)");
	}

	/* Verify LAC */
	var uint16_t lac_si3 := si3.payload.si3.lai.lac;
	var uint16_t lac_pcu := g_pcu_last_info.u.info_ind.lac;
	if (lac_si3 != lac_pcu) {
		setverdict(fail, "Expected LAC ", lac_si3, " got: ", lac_pcu);
	}

	setverdict(pass);
}

/***********************************************************************
 * Osmocom Style Dynamic Timeslot Support
 ***********************************************************************/

private function f_dyn_osmo_pdch_act(integer pcu_conn_id, integer bts_nr, integer trx_nr)
runs on ConnHdlr {
	var PCUIF_send_data sd;
	/* Expect BTS to immediately acknowledge activation as PDCH */
	PCU.clear;
	f_rsl_chan_act(g_pars.chan_mode);
	/* expect INFO_IND on PCU interface listing TS as PDCH */
	timer T_wait := 2.0;
	T_wait.start;
	alt {
	[] PCU.receive(t_SD_PCUIF(pcu_conn_id, tr_PCUIF_INFO_IND(bts_nr, ?))) -> value sd {
		if (substr(sd.data.u.info_ind.trx[trx_nr].pdch_mask, g_chan_nr.tn, 1) != '1'B) {
			log("PCUIF_INFO_IND PDCH_MASK not yet '1' after PDCH ACT on TS", g_chan_nr.tn,
			    " mask:", sd.data.u.info_ind.trx[trx_nr].pdch_mask);
			repeat;
		}
		}
	[] PCU.receive { repeat; }
	[] T_wait.timeout {
		Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail,
			log2str("Timeout waiting for PCUIF_INFO_IND PDCH_MASK to be '1' on TS", g_chan_nr.tn));
		}
	}
	/* try to activate this PDCH from the PCU point of view */
	PCU.send(t_SD_PCUIF(pcu_conn_id, ts_PCUIF_ACT_REQ(bts_nr, trx_nr, g_chan_nr.tn)));
	/* FIXME: is there a response? */
}

private function f_dyn_osmo_pdch_deact(integer pcu_conn_id, integer bts_nr, integer trx_nr)
runs on ConnHdlr {
	var PCUIF_send_data sd;
	/* Send RSL CHAN REL (deactivate) */
	PCU.clear;
	RSL.send(ts_RSL_RF_CHAN_REL(g_chan_nr));
	/* expect BTS to ask PCU to deactivate the channel */
	timer T_wait := 2.0;
	T_wait.start;
	alt {
	[] PCU.receive(t_SD_PCUIF(pcu_conn_id, tr_PCUIF_INFO_IND(bts_nr, ?))) -> value sd {
		if (substr(sd.data.u.info_ind.trx[trx_nr].pdch_mask, g_chan_nr.tn, 1) != '0'B) {
			log("PCUIF_INFO_IND PDCH_MASK not yet '0' after PDCH DEACT on TS", g_chan_nr.tn,
			    " mask:", sd.data.u.info_ind.trx[trx_nr].pdch_mask);
			repeat;
		}
		}
	[] PCU.receive { repeat; }
	[] T_wait.timeout {
		Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail,
			log2str("Timeout waiting for PCUIF_INFO_IND PDCH_MASK to be '0' on TS", g_chan_nr.tn));
		}
	}
	/* Emulate PCU asking BTS to deactivate PDCH */
	PCU.send(t_SD_PCUIF(pcu_conn_id, ts_PCUIF_DEACT_REQ(bts_nr, trx_nr, g_chan_nr.tn)));
	alt {
	[] RSL.receive(tr_RSL_RF_CHAN_REL_ACK(g_chan_nr)) {
		setverdict(pass);
		}
	[] RSL.receive { repeat; }
	}
}

/* Activate Osmocom-style dynamic PDCH from BSC side */
function f_TC_dyn_osmo_pdch_act_deact(charstring id) runs on ConnHdlr {
	var PCUIF_Message first_info;
	var integer ts_nr := g_chan_nr.tn;
	var integer trx_nr := 0;
	var integer bts_nr := 0;
	var integer pcu_conn_id := -1;

	f_init_pcu(PCU, id, pcu_conn_id, first_info);

	f_dyn_osmo_pdch_act(pcu_conn_id, bts_nr, trx_nr);
	f_sleep(3.0);
	f_dyn_osmo_pdch_deact(pcu_conn_id, bts_nr, trx_nr);
	setverdict(pass);
}
testcase TC_dyn_osmo_pdch_act_deact() runs on test_CT {
	var ConnHdlrPars pars;
	var ConnHdlr vc_conn;
	f_init();

	pars := valueof(t_Pars(t_RslChanNr_PDCH(4), ts_RSL_ChanMode_SIGN));
	vc_conn := f_start_handler(refers(f_TC_dyn_osmo_pdch_act_deact), pars, true);
	vc_conn.done;
}

/* send a RF CHAN REL for PDCH on an osmocom dynamci PDCH that's already inactive */
function f_TC_dyn_osmo_pdch_unsol_deact(charstring id) runs on ConnHdlr {
	var PCUIF_Message first_info;
	var integer pcu_conn_id := -1;

	f_init_pcu(PCU, id, pcu_conn_id, first_info);

	RSL.send(ts_RSL_RF_CHAN_REL(g_chan_nr));
	/* since the lchan is already released, we don't expect any PCU changes, just a rel ack. */
	RSL.receive(tr_RSL_RF_CHAN_REL_ACK(g_chan_nr));
	setverdict(pass);
}
testcase TC_dyn_osmo_pdch_unsol_deact() runs on test_CT {
	var ConnHdlrPars pars;
	var ConnHdlr vc_conn;
	f_init();

	pars := valueof(t_Pars(t_RslChanNr_PDCH(4), ts_RSL_ChanMode_SIGN));
	vc_conn := f_start_handler(refers(f_TC_dyn_osmo_pdch_unsol_deact), pars, true);
	vc_conn.done;
}

/* try to RSL CHAN ACT a PDCH on an osmocom-style PDCH that's already active */
function f_TC_dyn_osmo_pdch_double_act(charstring id) runs on ConnHdlr {
	var PCUIF_Message first_info;
	var integer ts_nr := g_chan_nr.tn;
	var integer trx_nr := 0;
	var integer bts_nr := 0;
	var integer pcu_conn_id := -1;

	f_init_pcu(PCU, id, pcu_conn_id, first_info);

	f_dyn_osmo_pdch_act(pcu_conn_id, bts_nr, trx_nr);
	/* Send a second Chan Activ and expect it to be NACKed */
	f_rsl_transceive(ts_RSL_CHAN_ACT(g_chan_nr, g_pars.chan_mode), tr_RSL_CHAN_ACT_NACK(g_chan_nr),
			 "RSL CHAN ACT NACK");
	setverdict(pass);
}
testcase TC_dyn_osmo_pdch_double_act() runs on test_CT {
	var ConnHdlrPars pars;
	var ConnHdlr vc_conn;
	f_init();

	pars := valueof(t_Pars(t_RslChanNr_PDCH(4), ts_RSL_ChanMode_SIGN));
	vc_conn := f_start_handler(refers(f_TC_dyn_osmo_pdch_double_act), pars, true);
	vc_conn.done;
}

/* try to RSL CHAN ACT a TCH/F on an osmocom-style PDCH */
function f_TC_dyn_osmo_pdch_tchf_act(charstring id) runs on ConnHdlr {
	var PCUIF_Message first_info;
	var integer ts_nr := g_chan_nr.tn;
	var integer trx_nr := 0;
	var integer bts_nr := 0;
	var integer pcu_conn_id := -1;
	var RslChannelNr chan_nr := valueof(t_RslChanNr_Bm(g_chan_nr.tn));

	/* register for the TCH/F channel number */
	f_rslem_register(0, chan_nr);

	f_init_pcu(PCU, id, pcu_conn_id, first_info);

	f_rsl_transceive(ts_RSL_CHAN_ACT(chan_nr, g_pars.chan_mode), tr_RSL_CHAN_ACT_ACK(chan_nr),
			 "RSL CHAN ACT");
	setverdict(pass);
}
testcase TC_dyn_osmo_pdch_tchf_act() runs on test_CT {
	var ConnHdlrPars pars;
	var ConnHdlr vc_conn;
	f_init();

	pars := valueof(t_Pars(t_RslChanNr_PDCH(4), ts_RSL_ChanMode_SIGN));
	vc_conn := f_start_handler(refers(f_TC_dyn_osmo_pdch_tchf_act), pars, true);
	vc_conn.done;
}

/* try to RSL CHAN ACT the TCH/H on an osmocom-style PDCH */
function f_TC_dyn_osmo_pdch_tchh_act(charstring id) runs on ConnHdlr {
	var PCUIF_Message first_info;
	var integer ts_nr := g_chan_nr.tn;
	var integer trx_nr := 0;
	var integer bts_nr := 0;
	var integer pcu_conn_id := -1;
	var RslChannelNr chan_nr[2] := { valueof(t_RslChanNr_Lm(g_chan_nr.tn, 0)),
					 valueof(t_RslChanNr_Lm(g_chan_nr.tn, 1)) };

	/* register for the TCH/H channel numbers */
	f_rslem_register(0, chan_nr[0]);
	f_rslem_register(0, chan_nr[1]);

	f_init_pcu(PCU, id, pcu_conn_id, first_info);

	f_rsl_transceive(ts_RSL_CHAN_ACT(chan_nr[1], g_pars.chan_mode),
			 tr_RSL_CHAN_ACT_ACK(chan_nr[1]), "RSL CHAN ACT [1]");
	f_rsl_transceive(ts_RSL_CHAN_ACT(chan_nr[0], g_pars.chan_mode),
			 tr_RSL_CHAN_ACT_ACK(chan_nr[0]), "RSL CHAN ACT [0]");
	setverdict(pass);
}
testcase TC_dyn_osmo_pdch_tchh_act() runs on test_CT {
	var ConnHdlrPars pars;
	var ConnHdlr vc_conn;
	f_init();

	pars := valueof(t_Pars(t_RslChanNr_PDCH(4), ts_RSL_ChanMode_SIGN));
	vc_conn := f_start_handler(refers(f_TC_dyn_osmo_pdch_tchh_act), pars, true);
	vc_conn.done;
}

/***********************************************************************
 * IPA Style Dynamic Timeslot Support
 ***********************************************************************/

private function f_dyn_ipa_pdch_act(integer pcu_conn_id, integer bts_nr, integer trx_nr)
runs on ConnHdlr {
	var PCUIF_send_data sd;
	/* Expect BTS to immediately acknowledge activation as PDCH */
	PCU.clear;
	RSL.send(ts_RSL_IPA_PDCH_ACT(g_chan_nr));
	/* expect INFO_IND on PCU interface listing TS as PDCH */
	timer T_wait := 2.0;
	T_wait.start;
	alt {
	[] PCU.receive(t_SD_PCUIF(pcu_conn_id, tr_PCUIF_INFO_IND(bts_nr, ?))) -> value sd {
		if (substr(sd.data.u.info_ind.trx[trx_nr].pdch_mask, g_chan_nr.tn, 1) != '1'B) {
			log("PCUIF_INFO_IND PDCH_MASK not yet '1' after PDCH ACT on TS", g_chan_nr.tn,
			    " mask:", sd.data.u.info_ind.trx[trx_nr].pdch_mask);
			repeat;
		}
		}
	[] PCU.receive { repeat; }
	[] T_wait.timeout {
	        Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail,
			log2str("Timeout waiting for PCUIF_INFO_IND PDCH_MASK to be '1' on TS", g_chan_nr.tn));
	        }
	}
	/* try to activate this PDCH from the PCU point of view */
	PCU.send(t_SD_PCUIF(pcu_conn_id, ts_PCUIF_ACT_REQ(bts_nr, trx_nr, g_chan_nr.tn)));
	/* FIXME: is there a response? */

	RSL.receive(tr_RSL_IPA_PDCH_ACT_ACK(g_chan_nr, ?));
}

private function f_dyn_ipa_pdch_deact(integer pcu_conn_id, integer bts_nr, integer trx_nr)
runs on ConnHdlr {
	var PCUIF_send_data sd;
	/* Send RSL CHAN REL (deactivate) */
	RSL.send(ts_RSL_IPA_PDCH_DEACT(g_chan_nr));
	PCU.clear;
	/* expect BTS to ask PCU to deactivate the channel */
	timer T_wait := 2.0;
	T_wait.start;
	alt {
	[] PCU.receive(t_SD_PCUIF(pcu_conn_id, tr_PCUIF_INFO_IND(bts_nr, ?))) -> value sd {
		if (substr(sd.data.u.info_ind.trx[trx_nr].pdch_mask, g_chan_nr.tn, 1) != '0'B) {
			log("PCUIF_INFO_IND PDCH_MASK not yet '0' after PDCH DEACT on TS", g_chan_nr.tn,
			    " mask:", sd.data.u.info_ind.trx[trx_nr].pdch_mask);
			repeat;
		}
		}
	[] PCU.receive { repeat; }
	[] T_wait.timeout {
	        Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail,
			log2str("Timeout waiting for PCUIF_INFO_IND PDCH_MASK to be '0' on TS", g_chan_nr.tn));
	        }
	}
	/* Emulate PCU asking BTS to deactivate PDCH */
	PCU.send(t_SD_PCUIF(pcu_conn_id, ts_PCUIF_DEACT_REQ(bts_nr, trx_nr, g_chan_nr.tn)));
	alt {
	[] RSL.receive(tr_RSL_IPA_PDCH_DEACT_ACK(g_chan_nr)) {
		setverdict(pass);
		}
	[] RSL.receive { repeat; }
	}
}

/* Activate and de-activate an IPA-style dynamic TCH/F + PDCH */
function f_TC_dyn_ipa_pdch_act_deact(charstring id) runs on ConnHdlr {
	var PCUIF_Message first_info;
	var integer ts_nr := g_chan_nr.tn;
	var integer trx_nr := 0;
	var integer bts_nr := 0;
	var integer pcu_conn_id := -1;

	f_init_pcu(PCU, id, pcu_conn_id, first_info);

	f_dyn_ipa_pdch_act(pcu_conn_id, bts_nr, trx_nr);
	f_sleep(3.0);
	f_dyn_ipa_pdch_deact(pcu_conn_id, bts_nr, trx_nr);

	setverdict(pass);

}
testcase TC_dyn_ipa_pdch_act_deact() runs on test_CT {
	var ConnHdlrPars pars;
	var ConnHdlr vc_conn;
	f_init();

	pars := valueof(t_Pars(t_RslChanNr_Bm(3), ts_RSL_ChanMode_SIGN));
	vc_conn := f_start_handler(refers(f_TC_dyn_ipa_pdch_act_deact), pars, true);
	vc_conn.done;
}

/* try to RSL CHAN ACT a TCH/F on an IPA-style PDCH */
function f_TC_dyn_ipa_pdch_tchf_act(charstring id) runs on ConnHdlr {
	var PCUIF_Message first_info;
	var integer ts_nr := g_chan_nr.tn;
	var integer trx_nr := 0;
	var integer bts_nr := 0;
	var integer pcu_conn_id := -1;

	f_init_pcu(PCU, id, pcu_conn_id, first_info);

	f_rsl_transceive(ts_RSL_CHAN_ACT(g_chan_nr, g_pars.chan_mode), tr_RSL_CHAN_ACT_ACK(g_chan_nr),
			 "RSL CHAN ACT");
	f_rsl_transceive(ts_RSL_RF_CHAN_REL(g_chan_nr), tr_RSL_RF_CHAN_REL_ACK(g_chan_nr),
			"RF CHAN REL", true);
	setverdict(pass);
}
testcase TC_dyn_ipa_pdch_tchf_act() runs on test_CT {
	var ConnHdlrPars pars;
	var ConnHdlr vc_conn;
	f_init();

	pars := valueof(t_Pars(t_RslChanNr_Bm(3), ts_RSL_ChanMode_SIGN));
	vc_conn := f_start_handler(refers(f_TC_dyn_ipa_pdch_tchf_act), pars, true);
	vc_conn.done;
}

/* Activate IPA style dyn PDCH as TCH/F and then illegally try to activate it as PDCH, too */
function f_TC_dyn_ipa_pdch_tchf_act_pdch_act_nack(charstring id) runs on ConnHdlr {
	var PCUIF_Message first_info;
	var integer ts_nr := g_chan_nr.tn;
	var integer trx_nr := 0;
	var integer bts_nr := 0;
	var integer pcu_conn_id := -1;

	f_init_pcu(PCU, id, pcu_conn_id, first_info);

	f_rsl_transceive(ts_RSL_CHAN_ACT(g_chan_nr, g_pars.chan_mode), tr_RSL_CHAN_ACT_ACK(g_chan_nr),
			 "RSL CHAN ACT");

	RSL.send(ts_RSL_IPA_PDCH_ACT(g_chan_nr));
	alt {
	[] RSL.receive(tr_RSL_IPA_PDCH_ACT_NACK(g_chan_nr, ?));
	[] RSL.receive(tr_RSL_IPA_PDCH_ACT_ACK(g_chan_nr, ?)) {
		Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, "Unexpected PDCH ACT ACK");
		}
	[] RSL.receive { repeat; }
	}

	f_rsl_transceive(ts_RSL_RF_CHAN_REL(g_chan_nr), tr_RSL_RF_CHAN_REL_ACK(g_chan_nr),
			"RF CHAN REL", true);
	setverdict(pass);
}
testcase TC_dyn_ipa_pdch_tchf_act_pdch_act_nack() runs on test_CT {
	var ConnHdlrPars pars;
	var ConnHdlr vc_conn;
	f_init();

	pars := valueof(t_Pars(t_RslChanNr_Bm(3), ts_RSL_ChanMode_SIGN));
	vc_conn := f_start_handler(refers(f_TC_dyn_ipa_pdch_tchf_act_pdch_act_nack), pars, true);
	vc_conn.done;
}

/* try to RSL CHAN ACT a TCH/F on an IPA-style PDCH that's already in PDCH mode; expect NACK */
function f_TC_dyn_ipa_pdch_act_tchf_act_nack(charstring id) runs on ConnHdlr {
	var PCUIF_Message first_info;
	var integer ts_nr := g_chan_nr.tn;
	var integer trx_nr := 0;
	var integer bts_nr := 0;
	var integer pcu_conn_id := -1;

	/* register for the TCH/F channel number */
	f_rslem_register(0, g_chan_nr);

	f_init_pcu(PCU, id, pcu_conn_id, first_info);

	f_dyn_ipa_pdch_act(pcu_conn_id, bts_nr, trx_nr);

	f_rsl_transceive(ts_RSL_CHAN_ACT(g_chan_nr, g_pars.chan_mode), tr_RSL_CHAN_ACT_NACK(g_chan_nr),
			 "RSL CHAN ACT");

	f_dyn_ipa_pdch_deact(pcu_conn_id, bts_nr, trx_nr);

	setverdict(pass);
}
testcase TC_dyn_ipa_pdch_act_tchf_act_nack() runs on test_CT {
	var ConnHdlrPars pars;
	var ConnHdlr vc_conn;
	f_init();

	pars := valueof(t_Pars(t_RslChanNr_Bm(3), ts_RSL_ChanMode_SIGN));
	vc_conn := f_start_handler(refers(f_TC_dyn_ipa_pdch_act_tchf_act_nack), pars, true);
	vc_conn.done;
}


/***********************************************************************
 * LAPDm / RLL related
 ***********************************************************************/

private function f_tx_lapdm(template (value) LapdmFrame l,
			    template (value) RslLinkId link_id) runs on ConnHdlr {
	var octetstring l2 := enc_LapdmFrame(valueof(l));
	var template (value) SacchL1Header l1h;

	/* TODO: we can use an extension of TTCN-3 for padding, i.e. PADDING('2B'O) */
	if (valueof(link_id.c) == SACCH) {
		/* Compose dummy L1 header */
		l1h := ts_SacchL1Header(g_pars.l1_pars.ms_power_level, false, g_pars.l1_pars.ms_actual_ta);
		L1CTL.send(ts_L1CTL_DATA_REQ_SACCH(g_chan_nr, link_id, l1h, f_pad_oct(l2, 21, '2B'O)));
	} else {
		/* If required, pad L2 frame with constant 0x2b filling */
		L1CTL.send(ts_L1CTL_DATA_REQ(g_chan_nr, link_id, f_pad_oct(l2, 23, '2B'O)));
	}
}

type record RllTestCase {
	uint3_t		sapi,
	RslLinkId	link_id,
	octetstring	l3,
	boolean		exp
}
type record of RllTestCase RllTestCases;
template RllTestCase t_EITC(uint3_t sapi, RslLinkId id, octetstring l3, boolean exp) := {
	sapi := sapi,
	link_id := id,
	l3 := l3,
	exp := exp
}

/* execute the same callback function with a set of different parameters (tcs) on a
 * variety of logical channels */
private function f_rll_testmatrix(RllTestCases tcs, void_fn fn) runs on test_CT {
	var ConnHdlrPars pars;
	var ConnHdlr vc_conn;
	f_init();

	/* test on each of the channels we have */
	for (var integer i := 0; i < sizeof(g_AllChanTypes); i := i+1) {
		pars := valueof(t_Pars(g_AllChanTypes[i], ts_RSL_ChanMode_SIGN));

		/* test each of the test cases on the current channel */
		for (var integer j := 0; j < sizeof(tcs); j := j+1) {
			pars.spec.rll := tcs[j];
			log(testcasename(), ": XXX Starting ", tcs[j] , " on ", g_AllChanTypes[i]);
			vc_conn := f_start_handler(fn, pars);
			vc_conn.done;
		}
	}

	Misc_Helpers.f_shutdown(__BFILE__, __LINE__);
}

/* test if SABM on Um triggers EST IND (TS 48.058 3.1) */
private function f_TC_rll_est_ind(charstring id) runs on ConnHdlr {
	var RllTestCase tc := g_pars.spec.rll;
	timer T := 3.0;

	f_l1_tune(L1CTL);
	RSL.clear;

	/* activate the logical channel */
	f_est_dchan();
	L1CTL.clear;

	f_tx_lapdm(ts_LAPDm_SABM(tc.sapi, cr_MO_CMD, true, tc.l3), tc.link_id);
	T.start;
	alt {
	[tc.l3 != ''O] RSL.receive(tr_RSL_EST_IND(g_chan_nr, tc.link_id, tc.l3)) {
		if (tc.exp) {
			setverdict(pass);
		} else {
			Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, log2str("Unexpected EST IND with L3 in ", tc));
		}
		}
	[tc.l3 == ''O] RSL.receive(tr_RSL_EST_IND_NOL3(g_chan_nr, tc.link_id)) {
		if (tc.exp) {
			setverdict(pass);
		} else {
			Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, log2str("Unexpected EST IND without L3 in ", tc));
		}
		}
	/* We also expect to receive the measurements */
	[] as_meas_res(verify_meas := false);
	[tc.exp] T.timeout {
		Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, "Timeout waiting for EST IND");
		}
	[not tc.exp] T.timeout {
		setverdict(pass);
		}
	}

	f_rsl_chan_deact();
	f_L1CTL_DM_REL_REQ(L1CTL, g_chan_nr);
	f_rslem_unregister(0, g_chan_nr);
}
testcase TC_rll_est_ind() runs on test_CT {
	var RllTestCases tcs := {
		/* SAPI0 establishment (contention resolution) */
		valueof(t_EITC(0, valueof(ts_RslLinkID_DCCH(0)), '01020304'O, true)),
		/* normal SAPI0 establishment */
		valueof(t_EITC(0, valueof(ts_RslLinkID_DCCH(0)), ''O, true)),
		/* SAPI 3 doesn't support contention resolution */
		valueof(t_EITC(3, valueof(ts_RslLinkID_DCCH(3)), '01020304'O, false)),
		valueof(t_EITC(3, valueof(ts_RslLinkID_SACCH(3)), '01020304'O, false)),
		/* normal SAPI3 establishment on main DCCH */
		valueof(t_EITC(3, valueof(ts_RslLinkID_DCCH(3)), ''O, true)),
		/* normal SAPI3 establishment on SACCH */
		valueof(t_EITC(3, valueof(ts_RslLinkID_SACCH(3)), ''O, true))
	};
	f_rll_testmatrix(tcs, refers(f_TC_rll_est_ind));
}

/* test if RLL EST REQ trigeres SABM on Um; UA on Um triggers EST CONF (TS 48.058 3.2) */
private function f_TC_rll_est_req(charstring id) runs on ConnHdlr {
	var RllTestCase tc := g_pars.spec.rll;
	var L1ctlDlMessage dl;
	timer T := 3.0;

	f_l1_tune(L1CTL);
	RSL.clear;

	/* activate the logical channel */
	f_est_dchan();
	L1CTL.clear;

	/* Send a RSL EST REQ for SAPI3 on main DCCH */
	RSL.send(ts_RSL_EST_REQ(g_chan_nr, tc.link_id));
	T.start;
	alt {
	[] L1CTL.receive(tr_L1CTL_DATA_IND(g_chan_nr, ?)) -> value dl {
		var LapdmFrame lapdm;
		var octetstring l2 := dl.payload.data_ind.payload;
		if (dl.dl_info.link_id.c == SACCH) {
			/* remove L1 header */
			l2 := substr(l2, 2, lengthof(l2)-2);
		}
		lapdm.ab := dec_LapdmFrameAB(l2);
		if (match(lapdm, tr_LAPDm_SABM(tc.sapi, cr_MT_CMD, true, ''O))) {
			setverdict(pass);
		} else {
			repeat;
		}
		}
	[] L1CTL.receive { repeat; }
	[] T.timeout {
		Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, "Timeout waiting for SABM");
		}
	}

	f_rsl_chan_deact();
	f_L1CTL_DM_REL_REQ(L1CTL, g_chan_nr);
	f_rslem_unregister(0, g_chan_nr);
}
testcase TC_rll_est_req_DCCH_3() runs on test_CT {
	var RllTestCases tcs := {
		/* normal SAPI3 establishment on main DCCH */
		valueof(t_EITC(3, valueof(ts_RslLinkID_DCCH(3)), ''O, true))//,
	};
	f_rll_testmatrix(tcs, refers(f_TC_rll_est_req));
}
testcase TC_rll_est_req_ACCH_3() runs on test_CT {
	var RllTestCases tcs := {
		/* normal SAPI3 establishment on SACCH */
		valueof(t_EITC(3, valueof(ts_RslLinkID_SACCH(3)), ''O, true))
	}
	f_rll_testmatrix(tcs, refers(f_TC_rll_est_req));
}

/* altstep to receive a LAPDm frame matching the given template */
private altstep as_l1_exp_lapdm(template LapdmFrame exp) runs on ConnHdlr {
	var L1ctlDlMessage dl;
	[] L1CTL.receive(tr_L1CTL_DATA_IND(g_chan_nr, ?)) -> value dl {
		var LapdmFrame lapdm;
		var octetstring l2 := dl.payload.data_ind.payload;
		if (dl.dl_info.link_id.c == SACCH) {
			/* remove L1 header */
			l2 := substr(l2, 2, lengthof(l2)-2);
		}
		if (ischosen(exp.ab)) {
			lapdm.ab := dec_LapdmFrameAB(l2);
		} else if (ischosen(exp.b4)) {
			lapdm.b4 := dec_LapdmFrameB4(l2);
		} else if (ischosen(exp.bbis)) {
			lapdm.bbis := dec_LapdmFrameBbis(l2);
		}
		log("Rx LAPDm ", lapdm);
		if (match(lapdm, exp)) {
			setverdict(pass);
		} else {
			repeat;
		}
		}
	[] L1CTL.receive { repeat; }
}
private function f_l1_exp_lapdm(template LapdmFrame exp, float t := 3.0) runs on ConnHdlr {
	timer T := t;
	T.start;
	alt {
	[] T.timeout {
		Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, log2str("Timeout waiting for LAPDm ", exp));
		}
	[] as_l1_exp_lapdm(exp);
	}
}

/* establish one Radio Link Layer via SABM -> UA. Use l3 for contention resolution */
private function f_est_rll_mo(uint3_t sapi, RslLinkId link_id, octetstring l3) runs on ConnHdlr {
	/* send SABM from MS -> BTS */
	f_tx_lapdm(ts_LAPDm_SABM(sapi, cr_MO_CMD, true, l3), link_id);
	/* expect RLL EST IND on Abis */
	alt {
	[l3 != ''O] RSL.receive(tr_RSL_EST_IND(g_chan_nr, link_id, l3));
	[l3 == ''O] RSL.receive(tr_RSL_EST_IND_NOL3(g_chan_nr, link_id));
	[] RSL.receive(tr_RSL_ERROR_IND(g_chan_nr, link_id, ?)) {
		Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, "Failing due to RSL_ERROR_IND");
		}
	[] RSL.receive { repeat; }
	}
	/* expect UA from BTS -> MS */
	f_l1_exp_lapdm(tr_LAPDm_UA(sapi, cr_MT_RSP, true, l3));
}

/* test if DISC on Um triggers RLL REL IND (TS 48.058 3.3) */
private function f_TC_rll_rel_ind(charstring id) runs on ConnHdlr {
	var RllTestCase tc := g_pars.spec.rll;

	f_l1_tune(L1CTL);
	RSL.clear;

	/* activate the logical channel */
	f_est_dchan();
	L1CTL.clear;

	/* first establish the link-layer */
	f_est_rll_mo(tc.sapi, tc.link_id, tc.l3);

	/* then send the DISC */
	f_tx_lapdm(ts_LAPDm_DISC(tc.sapi, cr_MO_CMD, true), tc.link_id);
	/* ... and expect the REL IND on the RSL side */
	alt {
	[] RSL.receive(tr_RSL_REL_IND(g_chan_nr, tc.link_id)) {
		setverdict(pass);
		}
	/* We also expect to receive the measurements */
	[] as_meas_res(verify_meas := false);
	}

	/* release the channel */
	f_rsl_chan_deact();
	f_L1CTL_DM_REL_REQ(L1CTL, g_chan_nr);
	f_rslem_unregister(0, g_chan_nr);
}
testcase TC_rll_rel_ind_DCCH_0() runs on test_CT {
	var RllTestCases tcs := {
		valueof(t_EITC(0, valueof(ts_RslLinkID_DCCH(0)), '01020304'O, true))
	};
	f_rll_testmatrix(tcs, refers(f_TC_rll_rel_ind));
}

testcase TC_rll_rel_ind_ACCH_0() runs on test_CT {
	var RllTestCases tcs := {
		valueof(t_EITC(0, valueof(ts_RslLinkID_SACCH(0)), ''O, true))
	};
	f_rll_testmatrix(tcs, refers(f_TC_rll_rel_ind));
}
testcase TC_rll_rel_ind_DCCH_3() runs on test_CT {
	var RllTestCases tcs := {
		valueof(t_EITC(3, valueof(ts_RslLinkID_DCCH(3)), ''O, true))
	};
	f_rll_testmatrix(tcs, refers(f_TC_rll_rel_ind));
}
testcase TC_rll_rel_ind_ACCH_3() runs on test_CT {
	var RllTestCases tcs := {
		valueof(t_EITC(3, valueof(ts_RslLinkID_SACCH(3)), ''O, true))
	};
	f_rll_testmatrix(tcs, refers(f_TC_rll_rel_ind));
}

/* test if RLL REL REQ triggers DISC on Um; UA/DM triggers RLL REL CONF (TS 48.058 3.4) */
private function f_TC_rll_rel_req(charstring id) runs on ConnHdlr {
	var RllTestCase tc := g_pars.spec.rll;
	f_l1_tune(L1CTL);
	RSL.clear;

	/* activate the logical channel */
	f_est_dchan();
	L1CTL.clear;

	/* first establish the link-layer */
	f_est_rll_mo(tc.sapi, tc.link_id, tc.l3);

	/* then send the REL REQ via RSL */
	RSL.send(ts_RSL_REL_REQ(g_chan_nr, tc.link_id, RSL_REL_MODE_NORMAL));
	/* ... and expect the DISC on the Um side */
	alt {
	[] as_l1_exp_lapdm(tr_LAPDm_DISC(tc.sapi, cr_MT_CMD, true))  {
		/* FIXME: send a UA in resposne to the DISC */
		}
	}

	/* release the channel */
	f_rsl_chan_deact();
	f_L1CTL_DM_REL_REQ(L1CTL, g_chan_nr);
	f_rslem_unregister(0, g_chan_nr);
}
testcase TC_rll_rel_req() runs on test_CT {
	var RllTestCases tcs := {
		valueof(t_EITC(0, valueof(ts_RslLinkID_DCCH(0)), '01020304'O, true)),
		valueof(t_EITC(0, valueof(ts_RslLinkID_SACCH(0)), ''O, true)),
		valueof(t_EITC(3, valueof(ts_RslLinkID_DCCH(3)), ''O, true)),
		valueof(t_EITC(3, valueof(ts_RslLinkID_SACCH(3)), ''O, true))
	};
	f_rll_testmatrix(tcs, refers(f_TC_rll_rel_req));
}

/* test if RLL DATA REQ triggers I-frames on Um (TS 48.058 3.5) */
testcase TC_rll_data_req() runs on test_CT {
}

/* test if I-frames on Um trigger RLL DATA IND (TS 48.058 3.6) */
testcase TC_rll_data_ind() runs on test_CT {
}

/* test if RLL UNIT DATA REQ triggers UI-frame on Um (TS 48.058 3.7) */
private function f_TC_rll_ud_req(charstring id) runs on ConnHdlr {
	var RllTestCase tc := g_pars.spec.rll;

	f_l1_tune(L1CTL);
	RSL.clear;

	f_est_dchan();
	L1CTL.clear;

	/* Send UNITDATA REQ on RSL side */
	RSL.send(ts_RSL_UNITDATA_REQ(g_chan_nr, tc.link_id, tc.l3));
	/* Expect it to arrive on the other side */
	if (tc.link_id.c == SACCH) {
		f_l1_exp_lapdm(tr_LAPDm_B4_UI(tc.sapi, cr_MT_CMD, tc.l3));
	} else {
		f_l1_exp_lapdm(tr_LAPDm_UI(tc.sapi, cr_MT_CMD, tc.l3));
	}

	/* release the channel */
	f_rsl_chan_deact();
	f_L1CTL_DM_REL_REQ(L1CTL, g_chan_nr);
	f_rslem_unregister(0, g_chan_nr);
}
testcase TC_rll_unit_data_req_DCCH() runs on test_CT {
	var octetstring l3 := f_rnd_octstring(15);
	var RllTestCases tcs := {
		valueof(t_EITC(0, valueof(ts_RslLinkID_DCCH(0)), l3, true)),
		valueof(t_EITC(3, valueof(ts_RslLinkID_DCCH(3)), l3, true))
	};
	f_rll_testmatrix(tcs, refers(f_TC_rll_ud_req));
}
testcase TC_rll_unit_data_req_ACCH() runs on test_CT {
	var octetstring l3 := f_rnd_octstring(19);
	var RllTestCases tcs := {
		valueof(t_EITC(0, valueof(ts_RslLinkID_SACCH(0)), l3, true)),
		valueof(t_EITC(3, valueof(ts_RslLinkID_SACCH(3)), l3, true))
	};
	f_rll_testmatrix(tcs, refers(f_TC_rll_ud_req));
}

/* test if UI-frames on Um trigger RLL UNIT DATA IND (TS 48.058 3.8) */
private function f_TC_rll_ud_ind(charstring id) runs on ConnHdlr {
	var RllTestCase tc := g_pars.spec.rll;

	f_l1_tune(L1CTL);
	RSL.clear;

	f_est_dchan();
	L1CTL.clear;

	/* Send LAPDm UI frame. There is no B4 format in uplink! */
	f_tx_lapdm(ts_LAPDm_UI(tc.sapi, cr_MO_CMD, tc.l3), tc.link_id);
	/* Expdct RLL UNITDATA IND on RSL side */
	alt {
	[] RSL.receive(tr_RSL_UNITDATA_IND(g_chan_nr, tc.link_id, tc.l3)) {
		setverdict(pass);
		}
	[] RSL.receive { repeat; }
	}

	/* release the channel */
	f_rsl_chan_deact();
	f_L1CTL_DM_REL_REQ(L1CTL, g_chan_nr);
	f_rslem_unregister(0, g_chan_nr);
}
testcase TC_rll_unit_data_ind_DCCH() runs on test_CT {
	var octetstring l3 := f_rnd_octstring(20);
	var RllTestCases tcs := {
		valueof(t_EITC(0, valueof(ts_RslLinkID_DCCH(0)), l3, true)),
		valueof(t_EITC(3, valueof(ts_RslLinkID_DCCH(3)), l3, true))
	};
	f_rll_testmatrix(tcs, refers(f_TC_rll_ud_ind));
}
testcase TC_rll_unit_data_ind_ACCH() runs on test_CT {
	var octetstring l3 := f_rnd_octstring(18);
	var RllTestCases tcs := {
		valueof(t_EITC(0, valueof(ts_RslLinkID_SACCH(0)), l3, true)),
		valueof(t_EITC(3, valueof(ts_RslLinkID_SACCH(3)), l3, true))
	};
	f_rll_testmatrix(tcs, refers(f_TC_rll_ud_ind));
}

/***********************************************************************
 * Encryption Related
 ***********************************************************************/

/* send UNITDATA_REQ from BTS to MS and expect it to arrive */
function f_unitdata_mt(RslLinkId link_id, octetstring l3) runs on ConnHdlr {
	RSL.send(ts_RSL_UNITDATA_REQ(g_chan_nr, link_id, l3));
	if (link_id.c == SACCH) {
		f_l1_exp_lapdm(tr_LAPDm_B4_UI(link_id.sapi, cr_MT_CMD, l3));
	} else {
		f_l1_exp_lapdm(tr_LAPDm_UI(link_id.sapi, cr_MT_CMD, l3));
	}
}

/* Expect (or not expect) other kinds of messages */
private altstep as_rsl_any_ind(boolean exp_any) runs on ConnHdlr {
	[exp_any] RSL.receive { repeat; }
	[not exp_any] RSL.receive {
		Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, "Unexpected RSL message!");
		}
}

/* Send UI frame from MS and expect it to arrive as RLL UNITDATA IND on Abis */
private function f_unitdata_mo(
	RslLinkId link_id,
	octetstring l3,
	boolean exp_sacch := true, /* Should tolerate SACCH messages? */
	boolean exp_any := false /* Should tolerate any other RSL messages? */
) runs on ConnHdlr {
	timer T := 3.0;
	f_tx_lapdm(ts_LAPDm_UI(link_id.sapi, cr_MO_CMD, l3), link_id);
	T.start;
	/* Expect RLL UNITDATA IND on RSL side */
	alt {
	[] RSL.receive(tr_RSL_UNITDATA_IND(g_chan_nr, link_id, l3)) {
		setverdict(pass);
		}
	[exp_sacch] as_meas_res(verify_meas := false);
	[] as_rsl_any_ind(exp_any);
	[] T.timeout {
		Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, "Timeout waiting for UNIT_DATA_IND");
		}
	}
}

/* Send I-frame from MS and expect it to arrive as RLL DATA IND on Abis */
private function f_data_mo(
	RslLinkId link_id,
	boolean p, uint3_t nr, uint3_t ns,
	octetstring l3,
	boolean exp_sacch := true, /* Should tolerate SACCH messages? */
	boolean exp_any := false /* Should tolerate any other RSL messages? */
) runs on ConnHdlr {
	timer T := 3.0;
	f_tx_lapdm(ts_LAPDm_I(link_id.sapi, cr_MO_CMD, p, nr, ns, l3), link_id);
	T.start;
	/* Expect RLL DATA IND on RSL side */
	alt {
	[] RSL.receive(tr_RSL_DATA_IND(g_chan_nr, link_id, l3)) {
		setverdict(pass);
		}
	[exp_sacch] as_meas_res(verify_meas := false);
	[] as_rsl_any_ind(exp_any);
	[] T.timeout {
		Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, "Timeout waiting for DATA_IND");
		}
	}
}

/* Test channel activation with A5/n right from the beginning (like in assignment + hand-over) */
function f_TC_chan_act_encr(charstring id) runs on ConnHdlr {
	f_l1_tune(L1CTL);
	f_est_dchan(true);

	/* now we actually need to transmit some data both ways to check if the encryption works */
	var L1ctlDlMessage dl;

	var octetstring l3 := f_rnd_octstring(20);
	var RslLinkId link_id := valueof(ts_RslLinkID_DCCH(0));

	/* send UNITDATA_REQ from BTS to MS and expect it to arrive */
	f_unitdata_mt(link_id, l3);

	/* Send UI frame from MS and expect it to arrive as RLL UNITDATA IND on Abis */
	f_unitdata_mo(link_id, l3);

	/* release the channel */
	f_rsl_chan_deact();
	f_L1CTL_DM_REL_REQ(L1CTL, g_chan_nr);
	f_rslem_unregister(0, g_chan_nr);
}
testcase TC_chan_act_a51() runs on test_CT {
	var ConnHdlrPars pars := valueof(t_Pars(t_RslChanNr_Bm(1), ts_RSL_ChanMode_SIGN));
	pars.encr := valueof(ts_RSL_IE_EncrInfo(RSL_ALG_ID_A5_1, f_rnd_octstring(8)));
	f_testmatrix_each_chan(pars, refers(f_TC_chan_act_encr));
}
testcase TC_chan_act_a52() runs on test_CT {
	var ConnHdlrPars pars := valueof(t_Pars(t_RslChanNr_Bm(1), ts_RSL_ChanMode_SIGN));
	pars.encr := valueof(ts_RSL_IE_EncrInfo(RSL_ALG_ID_A5_2, f_rnd_octstring(8)));
	f_testmatrix_each_chan(pars, refers(f_TC_chan_act_encr));
}
testcase TC_chan_act_a53() runs on test_CT {
	var ConnHdlrPars pars := valueof(t_Pars(t_RslChanNr_Bm(1), ts_RSL_ChanMode_SIGN));
	pars.encr := valueof(ts_RSL_IE_EncrInfo(RSL_ALG_ID_A5_3, f_rnd_octstring(8)));
	f_testmatrix_each_chan(pars, refers(f_TC_chan_act_encr));
}

/* Test channel activation with A5/n right from the beginning and RSL MODE MODIFY
 which should break the en/decryption on purpose by supplying a new key that is unknown to the MS*/
function f_TC_rsl_modify_encr(charstring id) runs on ConnHdlr {
	f_l1_tune(L1CTL);
	f_est_dchan(true);

	/* now we actually need to transmit some data both ways to check if the encryption works */
	var L1ctlDlMessage dl;

	var octetstring l3 := f_rnd_octstring(20);
	var RslLinkId link_id := valueof(ts_RslLinkID_DCCH(0));

	/* send UNITDATA_REQ from BTS to MS and expect it to arrive */
	f_unitdata_mt(link_id, l3);

	/* Send UI frame from MS and expect it to arrive as RLL UNITDATA IND on Abis */
	f_unitdata_mo(link_id, l3);

	var RSL_Message rsl;
	rsl := valueof(ts_RSL_MODE_MODIFY_REQ(g_chan_nr, valueof(ts_RSL_ChanMode_SIGN(false))));

	/* modify key to break proper encryption */
	g_pars.encr.key :=  f_rnd_octstring(8);
	var RSL_IE ei := valueof(t_RSL_IE(RSL_IE_ENCR_INFO, RSL_IE_Body:{encr_info := g_pars.encr}));
	rsl.ies := rsl.ies & { ei };
	RSL.send(rsl);

	timer T0 := 1.0;
	T0.start;
	/* Expect RSL MODIFY ACK */
	alt {
	[] RSL.receive(tr_RSL_MODE_MODIFY_ACK(g_chan_nr)) {}
	[] RSL.receive(tr_RSL_MODE_MODIFY_NACK(g_chan_nr, ?)) {
		Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail,"MODE MODIFY NACK");
		}
	[] T0.timeout {
		Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, "Timeout waiting for MODE MODIFY (N)ACK");
		}
	}

	var octetstring l3msg := f_rnd_octstring(15);
	timer T1 := 3.0;
	/* Send UI frame from MS, do not expect it to arrive as RLL UNITDATA IND on Abis
	due to broken encryption  */
	f_tx_lapdm(ts_LAPDm_UI(link_id.sapi, cr_MO_CMD, l3msg), link_id);
	T1.start;
	alt {
	[] RSL.receive(tr_RSL_UNITDATA_IND(g_chan_nr, link_id, l3msg)) {
		Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, "BTS shouldn't be able to decrypt after key change")
		}
	[] T1.timeout {
		setverdict(pass);
		}
	}

	/* release the channel */
	f_rsl_chan_deact();
	f_L1CTL_DM_REL_REQ(L1CTL, g_chan_nr);
	f_rslem_unregister(0, g_chan_nr);
}
testcase TC_rsl_modify_encr() runs on test_CT {
	var ConnHdlrPars pars := valueof(t_Pars(t_RslChanNr_Bm(1), ts_RSL_ChanMode_SIGN));
	pars.encr := valueof(ts_RSL_IE_EncrInfo(RSL_ALG_ID_A5_1, f_rnd_octstring(8)));
	f_testmatrix_each_chan(pars, refers(f_TC_rsl_modify_encr));
}

/* Test unencrypted channel activation followed by explicit ENCR CMD later */
function f_TC_encr_cmd(charstring id) runs on ConnHdlr {
	/* L3 payload doesn't matter, as it is passed transparently */
	var BIT3 l3_alg_id := f_alg_id_to_l3(g_pars.encr.alg_id);
	var octetstring l3 := enc_PDU_ML3_NW_MS(valueof(ts_RRM_CiphModeCmd(l3_alg_id)));
	var RslLinkId link_id := valueof(ts_RslLinkID_DCCH(0));

	f_l1_tune(L1CTL);

	/* first establish a dedicated channel in the clear */
	f_est_dchan(false);

	/* Establish ABM */
	f_est_rll_mo(link_id.sapi, link_id, '23420815'O);

	/* then send the RSL ENCR CMD with an actual RR CIPH MOD CMD inside */
	RSL.send(ts_RSL_ENCR_CMD(g_chan_nr, link_id, g_pars.encr.alg_id, g_pars.encr.key, l3));
	/* expect the L3 to arrive still unencrypted on the MS side */
	f_l1_exp_lapdm(tr_LAPDm_I(link_id.sapi, cr_MT_CMD, ?, ?, ?, l3));

	/* configure L1 to apply ciphering */
	var uint8_t alg_id := f_alg_id_to_l1ctl(g_pars.encr.alg_id);
	f_L1CTL_CRYPTO_REQ(L1CTL, g_pars.chan_nr, alg_id, g_pars.encr.key);

	/* send first ciphered I-frame in response and expect it on RSL */
	f_data_mo(link_id, true, 1, 0, '0a0b0c0d'O, exp_sacch := true);

	/* now the BTS code should have detected the first properly encrypted uplink I-frame,
	 * and hence enable encryption also on the downlink */

	/* expect bi-directional communication work in encrypted mode */
	f_unitdata_mo(link_id, f_rnd_octstring(15));
	f_unitdata_mt(link_id, f_rnd_octstring(15));

	/* release the channel */
	f_rsl_chan_deact();
	f_L1CTL_DM_REL_REQ(L1CTL, g_chan_nr);
	f_rslem_unregister(0, g_chan_nr);
}
testcase TC_encr_cmd_a51() runs on test_CT {
	var ConnHdlrPars pars := valueof(t_Pars(t_RslChanNr_Bm(1), ts_RSL_ChanMode_SIGN));
	pars.encr := valueof(ts_RSL_IE_EncrInfo(RSL_ALG_ID_A5_1, f_rnd_octstring(8)));
	f_testmatrix_each_chan(pars, refers(f_TC_encr_cmd));
}
testcase TC_encr_cmd_a52() runs on test_CT {
	var ConnHdlrPars pars := valueof(t_Pars(t_RslChanNr_Bm(1), ts_RSL_ChanMode_SIGN));
	pars.encr := valueof(ts_RSL_IE_EncrInfo(RSL_ALG_ID_A5_2, f_rnd_octstring(8)));
	f_testmatrix_each_chan(pars, refers(f_TC_encr_cmd));
}
testcase TC_encr_cmd_a53() runs on test_CT {
	var ConnHdlrPars pars := valueof(t_Pars(t_RslChanNr_Bm(1), ts_RSL_ChanMode_SIGN));
	pars.encr := valueof(ts_RSL_IE_EncrInfo(RSL_ALG_ID_A5_3, f_rnd_octstring(8)));
	f_testmatrix_each_chan(pars, refers(f_TC_encr_cmd));
}

private function f_assert_lapdm(octetstring enc, template LapdmFrame exp_match, charstring name := "") {
	var LapdmFrame lf;
	var octetstring reenc;

	/* decode the LAPDm frame */
	if (ischosen(exp_match.ab)) {
		lf.ab := dec_LapdmFrameAB(enc);
	} else {
		Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, "unsupported frame type");
	}

	/* check if decoder result matches expectation */
	if (not match(lf, exp_match)) {
		Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, log2str(name, ": decoded LAPDm doesn't match"));
	} else {
		log(name, ": matched");
		setverdict(pass);
	}

	/* test if re-encoded frame equals original input */
	reenc := enc_LapdmFrame(lf);
	if (enc != reenc) {
		Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, log2str(name, ": re-encoded LAPDm frame doesn't match"));
	} else {
		setverdict(pass);
	}
}

testcase TC_lapdm_selftest() runs on test_CT {
	f_assert_lapdm('030301'O, tr_LAPDm_UI(0, true, ''O), "ui_s0_empty");
	f_assert_lapdm('0F0301'O, tr_LAPDm_UI(3, true, ''O), "ui_s3_empty");
	f_assert_lapdm('013F01'O, tr_LAPDm_SABM(0, false, true, ''O), "sabm_s0_empty");
	f_assert_lapdm('013F1123420815'O, tr_LAPDm_SABM(0, false, true, '23420815'O), "sabm_s0_l3");
	f_assert_lapdm('03E101'O, tr_LAPDm_RR(0, true, false, 7), "rr_s0_7");
	f_assert_lapdm('03000d063505'O, tr_LAPDm_I(0, true, false, 0, 0, '063505'O), "I/0/0");
	f_assert_lapdm('03e00d063505'O, tr_LAPDm_I(0, true, false, 7, 0, '063505'O), "I/7/0");
}

/***********************************************************************
 * DTX Related (see GSM 05.08, section 8.3)
 ***********************************************************************/

/* XXX These functions must be kept in sync with g_AllChannels defined on test_CT. */
function f_g_chan_is_tchf() runs on ConnHdlr return boolean {
	return (g_chan_nr == valueof(ts_RslChanNr_Bm(1)) or
		g_chan_nr == valueof(ts_RslChanNr_Bm(2)) or
		g_chan_nr == valueof(ts_RslChanNr_Bm(3)) or
		g_chan_nr == valueof(ts_RslChanNr_Bm(4)));
}
function f_g_chan_is_tchh() runs on ConnHdlr return boolean {
	return (g_chan_nr == valueof(ts_RslChanNr_Lm(5,0)) or
		g_chan_nr == valueof(ts_RslChanNr_Lm(5,1)));
}
function f_g_chan_is_sdcch4() runs on ConnHdlr return boolean {
	return (g_chan_nr == valueof(ts_RslChanNr_SDCCH4(0,0)) or
		g_chan_nr == valueof(ts_RslChanNr_SDCCH4(0,1)) or
		g_chan_nr == valueof(ts_RslChanNr_SDCCH4(0,2)) or
		g_chan_nr == valueof(ts_RslChanNr_SDCCH4(0,3)));
}
function f_g_chan_is_sdcch8() runs on ConnHdlr return boolean {
	return (g_chan_nr == valueof(ts_RslChanNr_SDCCH8(6,0)) or
		g_chan_nr == valueof(ts_RslChanNr_SDCCH8(6,1)) or
		g_chan_nr == valueof(ts_RslChanNr_SDCCH8(6,2)) or
		g_chan_nr == valueof(ts_RslChanNr_SDCCH8(6,3)) or
		g_chan_nr == valueof(ts_RslChanNr_SDCCH8(6,4)) or
		g_chan_nr == valueof(ts_RslChanNr_SDCCH8(6,5)) or
		g_chan_nr == valueof(ts_RslChanNr_SDCCH8(6,6)) or
		g_chan_nr == valueof(ts_RslChanNr_SDCCH8(6,7)));
}

function f_test_l2_fill_frames(boolean dtxd) runs on ConnHdlr {
	var L1ctlDlMessage dl;
	var octetstring l2_fill_frame := '0303012B2B2B2B2B2B2B2B2B2B2B2B2B2B2B2B2B2B2B2B'O;
	var octetstring l2_fill_frame_sacch := substr(l2_fill_frame, 0, lengthof(l2_fill_frame) - 2);
	var GsmFrameNumber first_fn;
	var boolean is_first_frame := true;
	var integer nfill_frames_sacch := 0;
	var integer nfill_frames_nonsacch := 0;
	var integer expected_fill_frames := 10000; /* initial value causes test failure if not overridden */
	/* Frames numbers (mod 104) for which a fill frame is expected on TCHF if DTX is enabled. */
	var Integers required_tdma_frames_dtx_tchf := { 52, 53, 54, 55, 56, 57, 58, 59 };
	const integer frame_dtx_tchf_mod := 104;
	/* Frame numbers (mod 104) for which a fill frame is expected at the L1SAP level,
	 * which operates in terms of blocks rather than frames. */
	var Integers required_tdma_blocks_dtx_tchf := { 52, 56 };
	const integer block_dtx_tchf_mod := 26;
	timer T := 5.0;

	f_l1_tune(L1CTL);
	RSL.clear;
	L1CTL.clear;

	/* activate TCHF signalling channel */
	f_est_dchan(false);

	T.start;
	alt {
	[] L1CTL.receive(tr_L1CTL_DATA_IND(g_chan_nr, ?)) -> value dl {
		var GsmFrameNumber fn := dl.dl_info.frame_nr;
		var octetstring l2 := dl.payload.data_ind.payload;

		if (is_first_frame) {
			is_first_frame := false;
			first_fn := dl.dl_info.frame_nr;
		}

		if (dl.dl_info.link_id.c == SACCH) {
			l2 := substr(l2, 2, lengthof(l2) - 2); /* remove L1 header */
			if (not match(l2_fill_frame_sacch, l2)) {
				repeat;
			}
		} else if (not match(l2_fill_frame, l2)) {
			repeat;
		}

		if (dtxd) {
			if (not f_g_chan_is_tchf()) {
				T.stop;
				f_rsl_chan_deact();
				f_L1CTL_DM_REL_REQ(L1CTL, g_chan_nr);
				Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, "Received fill frame on non-TCH/F channel; DTX is only allowed on TCH/F!");
			}
			if (fn > first_fn + frame_dtx_tchf_mod) {
				T.stop;
				f_rsl_chan_deact();
				f_L1CTL_DM_REL_REQ(L1CTL, g_chan_nr);

				/* With DTX enabled we can expect at least 3 fill frames for every 104 frames.
				 * 2 SACCH, 1 TCH/F */
				expected_fill_frames := 3;

				if (nfill_frames_sacch + nfill_frames_nonsacch < expected_fill_frames) {
					log("received only ", nfill_frames_sacch, "+", nfill_frames_nonsacch,
					    " (SACCH+other) out of ", expected_fill_frames, " expected fill frames");
					Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, "Not enough fill frames received");
				} else {
					setverdict(pass);
				}
			} else {
				if (dl.dl_info.link_id.c == SACCH) {
					nfill_frames_sacch := nfill_frames_sacch + 1;
					repeat;
				}
				/* On DTX TCH/F channels, fill frames occur only for specific frame numbers mod 104.
				 * Furthermore, the L1SAP layer gives us frame numbers for the start of a block so
				 * we should only see the subset of frames numbers which correspond to a block boundary.
				 * TCH/F blocks are defined to start at 0,4,8,13,17,21 (modulo 26) */
				for (var integer i := 0; i < lengthof(required_tdma_blocks_dtx_tchf); i := i + 1) {
					if (fn mod frame_dtx_tchf_mod == required_tdma_blocks_dtx_tchf[i]) {
						nfill_frames_nonsacch := nfill_frames_nonsacch + 1;
						repeat;
					}
				}
				log("Received DTX TCH fill frame with bad frame number: ", fn,
				    " (mod ", frame_dtx_tchf_mod, ": ", fn mod frame_dtx_tchf_mod, ")",
				    " (mod ", block_dtx_tchf_mod, ": ", fn mod block_dtx_tchf_mod, ")");
				f_rsl_chan_deact();
				f_L1CTL_DM_REL_REQ(L1CTL, g_chan_nr);
				Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, "Unexpected L2 fill frame received on Um");
			}
		} else {
			if (dl.dl_info.link_id.c == SACCH) {
				nfill_frames_sacch := nfill_frames_sacch + 1;
			} else {
				nfill_frames_nonsacch := nfill_frames_nonsacch + 1;
			}
			if (fn > first_fn + frame_dtx_tchf_mod) {
				T.stop;
				if (f_g_chan_is_tchf()) {
					/* Without DTX we can expect 25 fill frames for every 104 frames.
					 * (24 FACCH + 1 SACCH filling) */
					 expected_fill_frames := 25;
				} else if (f_g_chan_is_tchh()) {
					/* We can expect 2 fill frames for every 104 frames. */
					 expected_fill_frames := 2;
				} else if (f_g_chan_is_sdcch4() or f_g_chan_is_sdcch8()) {
					/* We can expect 5 fill frames for every 104 frames. */
					 expected_fill_frames := 5;
				} else {
					f_rsl_chan_deact();
					f_L1CTL_DM_REL_REQ(L1CTL, g_chan_nr);
					Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, "Unknown channel type");
				}

				f_rsl_chan_deact();
				f_L1CTL_DM_REL_REQ(L1CTL, g_chan_nr);

				if (nfill_frames_sacch + nfill_frames_nonsacch >= expected_fill_frames) {
					setverdict(pass);
				} else {
					log("received only ", nfill_frames_sacch, "+", nfill_frames_nonsacch,
					    " (SACCH+other) out of ", expected_fill_frames, " expected fill frames");
					Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, "Not enough fill frames received");
				}
			} else {
				repeat;
			}
		}
	}
	[] L1CTL.receive { repeat; }
	[] T.timeout {
		f_rsl_chan_deact();
		f_L1CTL_DM_REL_REQ(L1CTL, g_chan_nr);
		Misc_Helpers.f_shutdown(__BFILE__, __LINE__, fail, "Timeout waiting for L2 fill frames on Um");
	}
	}
}

function f_TC_tch_sign_l2_fill_frame(charstring id) runs on ConnHdlr {
	f_test_l2_fill_frames(false);
}

function f_TC_tch_sign_l2_fill_frame_dtxd(charstring id) runs on ConnHdlr {
	f_test_l2_fill_frames(true);
}

function f_tch_sign_l2_fill_frame(boolean dtxd) runs on test_CT {
	var ConnHdlr vc_conn;
	var ConnHdlrPars pars;
	pars.t_guard := 60.0;
	f_init();
	for (var integer i := 0; i < sizeof(g_AllChannels); i := i + 1) {
		pars := valueof(t_Pars(g_AllChannels[i], ts_RSL_ChanMode_SIGN(dtxd)));
		if (dtxd) {
			if (i >= 4) { /* DTX is only allowed on TCH/F */
				break;
			}
			vc_conn := f_start_handler(refers(f_TC_tch_sign_l2_fill_frame_dtxd), pars);
		} else {
			vc_conn := f_start_handler(refers(f_TC_tch_sign_l2_fill_frame), pars);
		}
		vc_conn.done;
	}
}

/* Verify that L2 fill frames are sent on TCH in signaling mode if
 * there is nothing to transmit while DTX is disabled on downlink. */
testcase TC_tch_sign_l2_fill_frame() runs on test_CT {
	f_tch_sign_l2_fill_frame(false);
}

/* Verify that particular L2 fill frames are sent on TCH in signaling mode if
 * there is nothing to transmit while DTX is enabled on downlink. */
testcase TC_tch_sign_l2_fill_frame_dtxd() runs on test_CT {
	f_tch_sign_l2_fill_frame(true);
}

testcase TC_chopped_ipa_ping() runs on test_CT {
	IPA_Testing.f_run_TC_chopped_ipa_ping(mp_rsl_ip, mp_rsl_port, LISTEN_FOR_CLIENT);
}

testcase TC_chopped_ipa_payload() runs on test_CT {
	IPA_Testing.f_run_TC_chopped_ipa_payload(mp_rsl_ip, mp_rsl_port, LISTEN_FOR_CLIENT);
}

/* test generation of RLL ERR IND based on Um errors (TS 48.058 3.9) */
/*	protocol error as per 44.006 */
/*	link layer failure (repetition of I-frame N200 times without ACK */
/*	repetition of SABM or DISC N200 times without ACK */
/*	receptiom of SABM in multi-frame established state */


/* TODO Areas:

* channel activation
** with BS_Power / MS_Power, bypassing power control loop
** on primary vs. secondary TRX
** with timing advance from initial activation on
* mode modify
** encryption
** multirate
* check DEACTIVATE SACCH
** unsupported algorithm
* handover detection
* BS Power Control
* Physical Context
* RF resource ind
* error handling
** IE duplicated?
* PCU interface
** DATA_IND from BTS->PCU
** verification of PCU-originated DATA_REQ arrival on Um/MS side

*/

control {
	execute( TC_chan_act_stress() );
	execute( TC_chan_act_react() );
	execute( TC_chan_deact_not_active() );
	execute( TC_chan_act_wrong_nr() );
	execute( TC_deact_sacch() );
	execute( TC_sacch_filling() );
	execute( TC_sacch_info_mod() );
	execute( TC_sacch_multi() );
	execute( TC_sacch_multi_chg() );
	execute( TC_sacch_chan_act() );
	execute( TC_sacch_chan_act_ho_async() );
	execute( TC_sacch_chan_act_ho_sync() );
	execute( TC_rach_content() );
	execute( TC_rach_count() );
	execute( TC_rach_max_ta() );
	execute( TC_ho_rach() );
	execute( TC_rach_load_idle_thresh0() );
	execute( TC_rach_load_idle_below_thresh() );
	execute( TC_rach_load_count() );
	execute( TC_meas_res_sign_tchf() );
	execute( TC_meas_res_sign_tchh() );
	execute( TC_meas_res_sign_sdcch4() );
	execute( TC_meas_res_sign_sdcch8() );
	execute( TC_meas_res_sign_tchh_toa256() );
	execute( TC_rsl_bs_pwr_static_ass() );
	execute( TC_rsl_bs_pwr_static_power_control() );
	execute( TC_rsl_ms_pwr_ctrl() );
	execute( TC_rsl_ms_pwr_dyn_active() );
	execute( TC_rsl_ms_pwr_dyn_active2() );
	execute( TC_rsl_ms_pwr_dyn_up() );
	execute( TC_rsl_ms_pwr_dyn_down() );
	execute( TC_rsl_ms_pwr_dyn_ass_updown() );
	execute( TC_rsl_ms_pwr_dyn_max() );
	execute( TC_rsl_chan_initial_ms_pwr() );
	execute( TC_rsl_chan_initial_ta() );
	execute( TC_rsl_modify_encr() );
	execute( TC_conn_fail_crit() );
	execute( TC_paging_imsi_80percent() );
	execute( TC_paging_tmsi_80percent() );
	execute( TC_paging_imsi_200percent() );
	execute( TC_paging_tmsi_200percent() );
	execute( TC_rsl_protocol_error() );
	execute( TC_rsl_mand_ie_error() );
	execute( TC_rsl_ie_content_error() );
	execute( TC_si_sched_default() );
	execute( TC_si_sched_1() );
	execute( TC_si_sched_2bis() );
	execute( TC_si_sched_2ter() );
	execute( TC_si_sched_2ter_2bis() );
	execute( TC_si_sched_2quater() );
	execute( TC_si_sched_13() );
	execute( TC_si_sched_13_2bis_2ter_2quater() );
	execute( TC_ipa_dlcx_not_active() );
	execute( TC_ipa_crcx_twice_not_active() );
	execute( TC_ipa_crcx_mdcx_dlcx_not_active() );
	execute( TC_ipa_crcx_mdcx_mdcx_dlcx_not_active() );
	execute( TC_ipa_crcx_sdcch_not_active() );

	if (mp_pcu_socket != "") {
		execute( TC_pcu_act_req() );
		execute( TC_pcu_act_req_wrong_ts() );
		execute( TC_pcu_act_req_wrong_bts() );
		execute( TC_pcu_act_req_wrong_trx() );
		execute( TC_pcu_deact_req() );
		execute( TC_pcu_deact_req_wrong_ts() );
		execute( TC_pcu_ver_si13() );
		if (mp_l1_supports_gprs) {
			execute( TC_pcu_data_req_pdtch() );
			execute( TC_pcu_data_req_ptcch() );
			execute( TC_pcu_data_req_wrong_bts() );
			execute( TC_pcu_data_req_wrong_trx() );
			execute( TC_pcu_data_req_wrong_ts() );
			execute( TC_pcu_data_req_ts_inactive() );
		}
		execute( TC_pcu_ptcch() );
		execute( TC_pcu_data_req_agch() );
		execute( TC_pcu_data_req_pch() );
		execute( TC_pcu_data_req_imm_ass_pch() );
		execute( TC_pcu_rach_content() );
		execute( TC_pcu_ext_rach_content() );
		execute( TC_pcu_data_ind_lqual_cb() );
		execute( TC_pcu_paging_from_rsl() );
		execute( TC_pcu_time_ind() );
		execute( TC_pcu_rts_req() );
		execute( TC_pcu_oml_alert() );
		execute( TC_pcu_rr_suspend() );
		execute( TC_pcu_socket_connect_multi() );
		execute( TC_pcu_socket_reconnect() );
		execute( TC_pcu_socket_noconnect_nosi3gprs() );
		execute( TC_pcu_socket_connect_si3gprs() );
		execute( TC_pcu_socket_disconnect_nosi3gprs() );
		execute( TC_pcu_socket_verify_info_ind() );
		execute( TC_dyn_osmo_pdch_act_deact() );
		execute( TC_dyn_osmo_pdch_double_act() );
		execute( TC_dyn_ipa_pdch_act_deact() );
		execute( TC_dyn_ipa_pdch_act_tchf_act_nack() );

	} else {
		log("PCU socket path not available, skipping PCU tests");
	}

	execute( TC_dyn_osmo_pdch_unsol_deact() );
	execute( TC_dyn_osmo_pdch_tchf_act() );
	execute( TC_dyn_osmo_pdch_tchh_act() );
	execute( TC_dyn_ipa_pdch_tchf_act() );
	execute( TC_dyn_ipa_pdch_tchf_act_pdch_act_nack() );

	execute( TC_rll_est_ind() );
	execute( TC_rll_est_req_DCCH_3() );
	execute( TC_rll_est_req_ACCH_3() );
	execute( TC_rll_rel_ind_DCCH_0() );
	execute( TC_rll_rel_ind_DCCH_3() );
	execute( TC_rll_rel_ind_ACCH_0() );
	execute( TC_rll_rel_ind_ACCH_3() );
	execute( TC_rll_rel_req() );
	execute( TC_rll_unit_data_req_DCCH() );
	execute( TC_rll_unit_data_req_ACCH() );
	execute( TC_rll_unit_data_ind_DCCH() );
	execute( TC_rll_unit_data_ind_ACCH() );

	execute( TC_chan_act_a51() );
	execute( TC_chan_act_a52() );
	execute( TC_chan_act_a53() );
	execute( TC_encr_cmd_a51() );
	execute( TC_encr_cmd_a52() );
	execute( TC_encr_cmd_a53() );

	execute( TC_err_rep_wrong_mdisc() );
	execute( TC_err_rep_wrong_msg_type() );
	execute( TC_err_rep_wrong_sequence() );

	execute( TC_lapdm_selftest() );

	execute( TC_tch_sign_l2_fill_frame() );
	execute( TC_tch_sign_l2_fill_frame_dtxd() );

	execute( TC_chopped_ipa_ping() );
	execute( TC_chopped_ipa_payload() );
}


}
