aboutsummaryrefslogtreecommitdiffstats
path: root/remsim/RSPRO_Server.ttcn
blob: bb11689de8055636194279f7bda19a4f494c7062 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
module RSPRO_Server {

/* Utility functions implementing an RSRPO server.
 * (C) 2019 by Harald Welte <laforge@gnumonks.org>
 * All rights reserved.
 *
 * Released under the terms of GNU General Public License, Version 2 or
 * (at your option) any later version.
 *
 * SPDX-License-Identifier: GPL-2.0-or-later
 */


import from IPL4asp_Types all;
import from RSPRO all;
import from RSPRO_Types all;
import from IPA_Types all;
import from IPA_Emulation all;


type record RSPRO_Server {
	IPA_Emulation_CT	vc_IPA,
	IPA_CCM_Parameters	ccm_pars,
	charstring		id,
	ComponentIdentity	rspro_id//,

	//ClientSlot		rspro_client_slot optional,
	//BankId			rspro_bank_id optional,
	//SlotNumber		rspro_bank_nslots optional
};

const integer NUM_SERVER := 2;

type component rspro_server_CT {
	var RSPRO_Server	g_rspro_srv[NUM_SERVER];
	port IPA_RSPRO_PT	RSPRO_SRV[NUM_SERVER];
	timer			g_rspro_srv_Tguard := 30.0;
};

private altstep as_rspro_srv_Tguard() runs on rspro_server_CT {
[] g_rspro_srv_Tguard.timeout {
	setverdict(fail, "RSPRO Server global guard timer timeout");
	mtc.stop;
	}
}

altstep as_ignore_id_ack(integer i) runs on rspro_server_CT {
	[] RSPRO_SRV[i].receive(tr_ASP_IPA_EV(ASP_IPA_EVENT_ID_ACK)) { repeat; }
	[] RSPRO_SRV[i].receive(tr_ASP_IPA_EV(ASP_IPA_EVENT_ID_RESP)) { repeat; }
}


function f_rspro_srv_exp_connect(integer i)
runs on rspro_server_CT
{
	timer T := 20.0;
	T.start;
	alt {
	[] RSPRO_SRV[i].receive(tr_ASP_IPA_EV(ASP_IPA_EVENT_UP)) { }
	[] T.timeout {
		setverdict(fail, "Timeout waiting for ASP_IPA_EVENT_UP");
		mtc.stop;
		}
	}
}

function f_rspro_srv_init(integer i, charstring bind_host, integer bind_port,
			  ComponentIdentity rspro_id, boolean exp_connect := true)
runs on rspro_server_CT
{
	g_rspro_srv[i].id := "RSPRO_SRV" & int2str(i);
	g_rspro_srv[i].vc_IPA := IPA_Emulation_CT.create(g_rspro_srv[i].id);
	g_rspro_srv[i].ccm_pars := c_IPA_default_ccm_pars;
	g_rspro_srv[i].ccm_pars.name := "Osmocom TTCN-3 RSPRO server simulator";
	g_rspro_srv[i].rspro_id := rspro_id;

	activate(as_rspro_srv_Tguard());
	g_rspro_srv_Tguard.start;

	map(g_rspro_srv[i].vc_IPA:IPA_PORT, system:IPA_CODEC_PT);
	connect(g_rspro_srv[i].vc_IPA:IPA_RSPRO_PORT, self:RSPRO_SRV[i]);

	g_rspro_srv[i].vc_IPA.start(IPA_Emulation.main_server(bind_host, bind_port));

	activate(as_ignore_id_ack(i));

	if (exp_connect) {
		f_rspro_srv_exp_connect(i);
	}
}

function f_rspro_srv_fini(integer i)
runs on rspro_server_CT
{
	g_rspro_srv[i].vc_IPA.stop;
	disconnect(g_rspro_srv[i].vc_IPA:IPA_RSPRO_PORT, self:RSPRO_SRV[i]);
	unmap(g_rspro_srv[i].vc_IPA:IPA_PORT, system:IPA_CODEC_PT);
}


function f_rspro_srv_restart(integer i, charstring bind_host, integer bind_port)
runs on rspro_server_CT
{
	g_rspro_srv[i].vc_IPA.stop;
	g_rspro_srv[i].vc_IPA.start(IPA_Emulation.main_server(bind_host, bind_port));
}


function f_rspro_srv_exp(template RsproPDU exp, integer i := 0, float tout := 10.0)
runs on rspro_server_CT return RsproPDU
{
	var RsproPDU pdu;

	timer T := tout;
	T.start;
	alt {
	[] RSPRO_SRV[i].receive(exp) -> value pdu {
		setverdict(pass);
		}
	[] RSPRO_SRV[i].receive(RsproPDU:?) -> value pdu {
		setverdict(fail, "Received unexpected RPSRO", pdu, " instead of ", exp);
		mtc.stop;
		}
	[] as_ignore_id_ack(i) { repeat; }
	[] RSPRO_SRV[i].receive {
		setverdict(fail, "Received unexpected != RPSRO");
		mtc.stop;
		}
	[] T.timeout {
		setverdict(fail, "Timeout waiting for ", exp);
		mtc.stop;
		}
	}
	return pdu;
}

function f_rspro_srv_create_slotmap(ClientSlot cslot, BankSlot bslot,
				    template ResultCode exp_res := ok, integer i := 0)
runs on rspro_server_CT
{
	RSPRO_SRV[i].send(ts_RSPRO_CreateMappingReq(cslot, bslot));
	f_rspro_srv_exp(tr_RSPRO_CreateMappingRes(exp_res), i);
}

function f_rspro_srv_remove_slotmap(ClientSlot cslot, BankSlot bslot,
				    template ResultCode exp_res := ok, integer i := 0)
runs on rspro_server_CT
{
	RSPRO_SRV[i].send(ts_RSPRO_RemoveMappingReq(cslot, bslot));
	f_rspro_srv_exp(tr_RSPRO_RemoveMappingRes(exp_res), i);
}

function f_rspro_config_client_bank(template (value) BankSlot bank_slot,
				    template (value) IpPort bank_iport,
				    template ResultCode exp_res := ok, integer i := 0)
runs on rspro_server_CT {
	RSPRO_SRV[i].send(ts_RSPRO_ConfigClientBankReq(bank_slot, bank_iport));
	f_rspro_srv_exp(tr_RSPRO_ConfigClientBankRes(exp_res));
}

function f_rspro_srv_reset_state(template ResultCode exp_res := ok, integer i := 0)
runs on rspro_server_CT
{
	RSPRO_SRV[i].send(ts_RSPRO_ResetStateReq);
	f_rspro_srv_exp(tr_RSPRO_ResetStateRes(exp_res));
}

altstep as_connectBankReq(template ComponentIdentity comp_id := tr_CompId(remsimBankd, ?,
									  "remsim-bankd", ?),
			  template BankId bid := ?,
			  template SlotNumber nslots := ?,
			  ResultCode res := ok, integer i := 0)
runs on rspro_server_CT {
	[] RSPRO_SRV[i].receive(tr_RSPRO_ConnectBankReq(comp_id, bid, nslots)) {
		RSPRO_SRV[i].send(ts_RSPRO_ConnectBankRes(g_rspro_srv[i].rspro_id, res));
		}
}

altstep as_connectClientReq(template ComponentIdentity comp_id := tr_CompId(remsimClient, ?,
									  "remsim-client", ?),
			  template ClientSlot cslot := *,
			  ResultCode res := ok, integer i := 0)
runs on rspro_server_CT {
	[] RSPRO_SRV[i].receive(tr_RSPRO_ConnectClientReq(comp_id, cslot)) {
		RSPRO_SRV[i].send(ts_RSPRO_ConnectClientRes(g_rspro_srv[i].rspro_id, res));
		}
}



}