blob: 62eee7a80d5178907bd797e81117be5750a9bbeb [file] [log] [blame]
Harald Welte68628e82009-03-10 12:17:57 +00001/* OpenBSC interface to quagga VTY */
2/* (C) 2009 by Harald Welte <laforge@gnumonks.org>
3 * All Rights Reserved
4 *
5 * This program is free software; you can redistribute it and/or modify
6 * it under the terms of the GNU General Public License as published by
7 * the Free Software Foundation; either version 2 of the License, or
8 * (at your option) any later version.
9 *
10 * This program is distributed in the hope that it will be useful,
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 * GNU General Public License for more details.
14 *
15 * You should have received a copy of the GNU General Public License along
16 * with this program; if not, write to the Free Software Foundation, Inc.,
17 * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
18 *
19 */
20
21#include <stdlib.h>
22#include <unistd.h>
23#include <sys/types.h>
24
25#include <vty/command.h>
Harald Weltef9daefd2009-08-09 15:13:54 +020026#include <vty/buffer.h>
Harald Welte68628e82009-03-10 12:17:57 +000027#include <vty/vty.h>
28
29#include <arpa/inet.h>
30
Harald Welte1bc77352009-03-10 19:47:51 +000031#include <openbsc/linuxlist.h>
Harald Welte68628e82009-03-10 12:17:57 +000032#include <openbsc/gsm_data.h>
Harald Welte68628e82009-03-10 12:17:57 +000033#include <openbsc/e1_input.h>
Harald Welte1bc77352009-03-10 19:47:51 +000034#include <openbsc/abis_nm.h>
Harald Weltef9daefd2009-08-09 15:13:54 +020035#include <openbsc/gsm_utils.h>
Harald Welteb908cb72009-12-22 13:09:29 +010036#include <openbsc/chan_alloc.h>
Harald Welte8387a492009-12-22 21:43:14 +010037#include <openbsc/meas_rep.h>
Harald Welte40f82892009-05-23 17:31:39 +000038#include <openbsc/db.h>
Harald Welte5013b2a2009-08-07 13:29:14 +020039#include <openbsc/talloc.h>
Harald Welte68628e82009-03-10 12:17:57 +000040
41static struct gsm_network *gsmnet;
42
Harald Welte5013b2a2009-08-07 13:29:14 +020043struct cmd_node net_node = {
44 GSMNET_NODE,
45 "%s(network)#",
46 1,
47};
48
Harald Welte68628e82009-03-10 12:17:57 +000049struct cmd_node bts_node = {
50 BTS_NODE,
51 "%s(bts)#",
52 1,
53};
54
55struct cmd_node trx_node = {
56 TRX_NODE,
57 "%s(trx)#",
58 1,
59};
60
61struct cmd_node ts_node = {
62 TS_NODE,
63 "%s(ts)#",
64 1,
65};
66
67static int dummy_config_write(struct vty *v)
68{
69 return CMD_SUCCESS;
70}
71
72static void net_dump_nmstate(struct vty *vty, struct gsm_nm_state *nms)
73{
Harald Welte1bc77352009-03-10 19:47:51 +000074 vty_out(vty,"Oper '%s', Admin %u, Avail '%s'%s",
75 nm_opstate_name(nms->operational), nms->administrative,
76 nm_avail_name(nms->availability), VTY_NEWLINE);
Harald Welte68628e82009-03-10 12:17:57 +000077}
78
Harald Welteb908cb72009-12-22 13:09:29 +010079static void dump_pchan_load_vty(struct vty *vty, char *prefix,
80 const struct pchan_load *pl)
81{
82 int i;
83
84 for (i = 0; i < ARRAY_SIZE(pl->pchan); i++) {
85 const struct load_counter *lc = &pl->pchan[i];
86 unsigned int percent;
87
88 if (lc->total == 0)
89 continue;
90
91 percent = (lc->used * 100) / lc->total;
92
93 vty_out(vty, "%s%20s: %3u%% (%u/%u)%s", prefix,
94 gsm_pchan_name(i), percent, lc->used, lc->total,
95 VTY_NEWLINE);
96 }
97}
98
Harald Welte68628e82009-03-10 12:17:57 +000099static void net_dump_vty(struct vty *vty, struct gsm_network *net)
100{
Harald Welteb908cb72009-12-22 13:09:29 +0100101 struct pchan_load pl;
102
Harald Welteef235b52009-03-10 12:34:02 +0000103 vty_out(vty, "BSC is on Country Code %u, Network Code %u "
104 "and has %u BTS%s", net->country_code, net->network_code,
105 net->num_bts, VTY_NEWLINE);
Harald Welte1bc77352009-03-10 19:47:51 +0000106 vty_out(vty, " Long network name: '%s'%s",
Harald Welte68628e82009-03-10 12:17:57 +0000107 net->name_long, VTY_NEWLINE);
Harald Welte1bc77352009-03-10 19:47:51 +0000108 vty_out(vty, " Short network name: '%s'%s",
Harald Welte68628e82009-03-10 12:17:57 +0000109 net->name_short, VTY_NEWLINE);
Harald Welte (local)69de3972009-08-12 14:42:23 +0200110 vty_out(vty, " Authentication policy: %s%s",
111 gsm_auth_policy_name(net->auth_policy), VTY_NEWLINE);
Harald Welte1085c092009-11-18 20:33:19 +0100112 vty_out(vty, " Location updating reject cause: %u%s",
113 net->reject_cause, VTY_NEWLINE);
Harald Welte4381cfe2009-08-30 15:47:06 +0900114 vty_out(vty, " Encryption: A5/%u%s", net->a5_encryption,
115 VTY_NEWLINE);
Holger Hans Peter Freytherf7d752f2009-11-16 17:12:38 +0100116 vty_out(vty, " NECI (TCH/H): %u%s", net->neci,
117 VTY_NEWLINE);
Harald Welteeab84a12009-12-13 10:53:12 +0100118 vty_out(vty, " RRLP Mode: %s%s", rrlp_mode_name(net->rrlp.mode),
119 VTY_NEWLINE);
Harald Welte648b6ce2009-12-14 09:00:24 +0100120 vty_out(vty, " MM Info: %s%s", net->send_mm_info ? "On" : "Off",
121 VTY_NEWLINE);
Harald Weltebc814502009-12-19 21:41:52 +0100122 vty_out(vty, " Handover: %s%s", net->handover.active ? "On" : "Off",
123 VTY_NEWLINE);
Harald Welteb908cb72009-12-22 13:09:29 +0100124 network_chan_load(&pl, net);
125 vty_out(vty, " Current Channel Load:%s", VTY_NEWLINE);
126 dump_pchan_load_vty(vty, " ", &pl);
Harald Welte68628e82009-03-10 12:17:57 +0000127}
128
129DEFUN(show_net, show_net_cmd, "show network",
130 SHOW_STR "Display information about a GSM NETWORK\n")
131{
132 struct gsm_network *net = gsmnet;
133 net_dump_vty(vty, net);
134
135 return CMD_SUCCESS;
136}
137
138static void e1isl_dump_vty(struct vty *vty, struct e1inp_sign_link *e1l)
139{
Harald Welteedb37782009-05-01 14:59:07 +0000140 struct e1inp_line *line;
141
142 if (!e1l) {
143 vty_out(vty, " None%s", VTY_NEWLINE);
144 return;
145 }
146
147 line = e1l->ts->line;
148
149 vty_out(vty, " E1 Line %u, Type %s: Timeslot %u, Mode %s%s",
150 line->num, line->driver->name, e1l->ts->num,
Harald Welte1bc77352009-03-10 19:47:51 +0000151 e1inp_signtype_name(e1l->type), VTY_NEWLINE);
Harald Welteedb37782009-05-01 14:59:07 +0000152 vty_out(vty, " E1 TEI %u, SAPI %u%s",
Harald Welte68628e82009-03-10 12:17:57 +0000153 e1l->tei, e1l->sapi, VTY_NEWLINE);
154}
155
156static void bts_dump_vty(struct vty *vty, struct gsm_bts *bts)
157{
Harald Welteb908cb72009-12-22 13:09:29 +0100158 struct pchan_load pl;
159
Holger Hans Peter Freytherc4a49e32009-08-21 14:44:12 +0200160 vty_out(vty, "BTS %u is of %s type in band %s, has CI %u LAC %u, "
Harald Weltefcd24452009-06-20 18:15:19 +0200161 "BSIC %u, TSC %u and %u TRX%s",
162 bts->nr, btstype2str(bts->type), gsm_band_name(bts->band),
Holger Hans Peter Freytherc4a49e32009-08-21 14:44:12 +0200163 bts->cell_identity,
Harald Weltefcd24452009-06-20 18:15:19 +0200164 bts->location_area_code, bts->bsic, bts->tsc,
165 bts->num_trx, VTY_NEWLINE);
Harald Welte1d8dbc42009-12-12 15:38:16 +0100166 vty_out(vty, "MS Max power: %u dBm%s", bts->ms_max_power, VTY_NEWLINE);
Harald Welte73225282009-12-12 18:17:25 +0100167 vty_out(vty, "Minimum Rx Level for Access: %i dBm%s",
Harald Welte1d8dbc42009-12-12 15:38:16 +0100168 rxlev2dbm(bts->si_common.cell_sel_par.rxlev_acc_min),
169 VTY_NEWLINE);
170 vty_out(vty, "Cell Reselection Hysteresis: %u dBm%s",
Harald Welte73225282009-12-12 18:17:25 +0100171 bts->si_common.cell_sel_par.cell_resel_hyst*2, VTY_NEWLINE);
Sylvain Munaut4010f1e2009-12-22 13:43:26 +0100172 vty_out(vty, "RACH TX-Integer: %u%s", bts->si_common.rach_control.tx_integer,
173 VTY_NEWLINE);
174 vty_out(vty, "RACH Max transmissions: %u%s",
175 rach_max_trans_raw2val(bts->si_common.rach_control.max_trans),
176 VTY_NEWLINE);
Harald Welte71355012009-12-21 23:08:18 +0100177 if (bts->si_common.rach_control.cell_bar)
Harald Welte (local)5dececf2009-08-12 13:28:23 +0200178 vty_out(vty, " CELL IS BARRED%s", VTY_NEWLINE);
Harald Welte4cc34222009-05-01 15:12:31 +0000179 if (is_ipaccess_bts(bts))
Harald Welte8175e952009-10-20 00:22:00 +0200180 vty_out(vty, " Unit ID: %u/%u/0, OML Stream ID 0x%02x%s",
Harald Welte4cc34222009-05-01 15:12:31 +0000181 bts->ip_access.site_id, bts->ip_access.bts_id,
Harald Welte8175e952009-10-20 00:22:00 +0200182 bts->oml_tei, VTY_NEWLINE);
Harald Welte68628e82009-03-10 12:17:57 +0000183 vty_out(vty, " NM State: ");
184 net_dump_nmstate(vty, &bts->nm_state);
185 vty_out(vty, " Site Mgr NM State: ");
186 net_dump_nmstate(vty, &bts->site_mgr.nm_state);
187 vty_out(vty, " Paging: FIXME pending requests, %u free slots%s",
188 bts->paging.available_slots, VTY_NEWLINE);
Harald Welte8175e952009-10-20 00:22:00 +0200189 if (!is_ipaccess_bts(bts)) {
190 vty_out(vty, " E1 Signalling Link:%s", VTY_NEWLINE);
191 e1isl_dump_vty(vty, bts->oml_link);
192 }
Harald Welte68628e82009-03-10 12:17:57 +0000193 /* FIXME: oml_link, chan_desc */
Harald Welteb908cb72009-12-22 13:09:29 +0100194 memset(&pl, 0, sizeof(pl));
195 bts_chan_load(&pl, bts);
196 vty_out(vty, " Current Channel Load:%s", VTY_NEWLINE);
197 dump_pchan_load_vty(vty, " ", &pl);
Harald Welte68628e82009-03-10 12:17:57 +0000198}
199
200DEFUN(show_bts, show_bts_cmd, "show bts [number]",
201 SHOW_STR "Display information about a BTS\n"
202 "BTS number")
203{
204 struct gsm_network *net = gsmnet;
205 int bts_nr;
206
207 if (argc != 0) {
208 /* use the BTS number that the user has specified */
209 bts_nr = atoi(argv[0]);
210 if (bts_nr > net->num_bts) {
Harald Welte1bc77352009-03-10 19:47:51 +0000211 vty_out(vty, "%% can't find BTS '%s'%s", argv[0],
Harald Welte68628e82009-03-10 12:17:57 +0000212 VTY_NEWLINE);
213 return CMD_WARNING;
214 }
Harald Weltee441d9c2009-06-21 16:17:15 +0200215 bts_dump_vty(vty, gsm_bts_num(net, bts_nr));
Harald Welte68628e82009-03-10 12:17:57 +0000216 return CMD_SUCCESS;
217 }
218 /* print all BTS's */
219 for (bts_nr = 0; bts_nr < net->num_bts; bts_nr++)
Harald Weltee441d9c2009-06-21 16:17:15 +0200220 bts_dump_vty(vty, gsm_bts_num(net, bts_nr));
Harald Welte68628e82009-03-10 12:17:57 +0000221
222 return CMD_SUCCESS;
223}
224
Harald Welte42581822009-08-08 16:12:58 +0200225/* utility functions */
226static void parse_e1_link(struct gsm_e1_subslot *e1_link, const char *line,
227 const char *ts, const char *ss)
228{
229 e1_link->e1_nr = atoi(line);
230 e1_link->e1_ts = atoi(ts);
231 if (!strcmp(ss, "full"))
232 e1_link->e1_ts_ss = 255;
233 else
234 e1_link->e1_ts_ss = atoi(ss);
235}
236
237static void config_write_e1_link(struct vty *vty, struct gsm_e1_subslot *e1_link,
238 const char *prefix)
239{
240 if (!e1_link->e1_ts)
241 return;
242
243 if (e1_link->e1_ts_ss == 255)
244 vty_out(vty, "%se1 line %u timeslot %u sub-slot full%s",
245 prefix, e1_link->e1_nr, e1_link->e1_ts, VTY_NEWLINE);
246 else
247 vty_out(vty, "%se1 line %u timeslot %u sub-slot %u%s",
248 prefix, e1_link->e1_nr, e1_link->e1_ts,
249 e1_link->e1_ts_ss, VTY_NEWLINE);
250}
251
252
Harald Welte67ce0732009-08-06 19:06:46 +0200253static void config_write_ts_single(struct vty *vty, struct gsm_bts_trx_ts *ts)
254{
Harald Welte42581822009-08-08 16:12:58 +0200255 vty_out(vty, " timeslot %u%s", ts->nr, VTY_NEWLINE);
256 if (ts->pchan != GSM_PCHAN_NONE)
257 vty_out(vty, " phys_chan_config %s%s",
258 gsm_pchan_name(ts->pchan), VTY_NEWLINE);
259 config_write_e1_link(vty, &ts->e1_link, " ");
Harald Welte67ce0732009-08-06 19:06:46 +0200260}
261
262static void config_write_trx_single(struct vty *vty, struct gsm_bts_trx *trx)
263{
264 int i;
265
Harald Welte5013b2a2009-08-07 13:29:14 +0200266 vty_out(vty, " trx %u%s", trx->nr, VTY_NEWLINE);
267 vty_out(vty, " arfcn %u%s", trx->arfcn, VTY_NEWLINE);
268 vty_out(vty, " max_power_red %u%s", trx->max_power_red, VTY_NEWLINE);
Harald Welte42581822009-08-08 16:12:58 +0200269 config_write_e1_link(vty, &trx->rsl_e1_link, " rsl ");
270 vty_out(vty, " rsl e1 tei %u%s", trx->rsl_tei, VTY_NEWLINE);
Harald Welte67ce0732009-08-06 19:06:46 +0200271
272 for (i = 0; i < TRX_NR_TS; i++)
273 config_write_ts_single(vty, &trx->ts[i]);
274}
275
276static void config_write_bts_single(struct vty *vty, struct gsm_bts *bts)
277{
278 struct gsm_bts_trx *trx;
279
Harald Welte5013b2a2009-08-07 13:29:14 +0200280 vty_out(vty, " bts %u%s", bts->nr, VTY_NEWLINE);
281 vty_out(vty, " type %s%s", btstype2str(bts->type), VTY_NEWLINE);
282 vty_out(vty, " band %s%s", gsm_band_name(bts->band), VTY_NEWLINE);
Holger Hans Peter Freytherf926ed62009-11-19 16:38:49 +0100283 vty_out(vty, " cell_identity %u%s", bts->cell_identity, VTY_NEWLINE);
Harald Welte5013b2a2009-08-07 13:29:14 +0200284 vty_out(vty, " location_area_code %u%s", bts->location_area_code,
Harald Welte67ce0732009-08-06 19:06:46 +0200285 VTY_NEWLINE);
Harald Welte5013b2a2009-08-07 13:29:14 +0200286 vty_out(vty, " training_sequence_code %u%s", bts->tsc, VTY_NEWLINE);
287 vty_out(vty, " base_station_id_code %u%s", bts->bsic, VTY_NEWLINE);
Harald Welte (local)0e451d02009-08-13 10:14:26 +0200288 vty_out(vty, " ms max power %u%s", bts->ms_max_power, VTY_NEWLINE);
Harald Welte73225282009-12-12 18:17:25 +0100289 vty_out(vty, " cell reselection hysteresis %u%s",
290 bts->si_common.cell_sel_par.cell_resel_hyst*2, VTY_NEWLINE);
291 vty_out(vty, " rxlev access min %u%s",
292 bts->si_common.cell_sel_par.rxlev_acc_min, VTY_NEWLINE);
Harald Weltea43f7892009-12-01 18:04:30 +0530293 if (bts->si_common.chan_desc.t3212)
Harald Welte (local)efc92312009-08-14 23:09:25 +0200294 vty_out(vty, " periodic location update %u%s",
Harald Weltea43f7892009-12-01 18:04:30 +0530295 bts->si_common.chan_desc.t3212 * 10, VTY_NEWLINE);
Harald Welte7a8fa412009-08-10 13:48:16 +0200296 vty_out(vty, " channel allocator %s%s",
297 bts->chan_alloc_reverse ? "descending" : "ascending",
298 VTY_NEWLINE);
Sylvain Munaut4010f1e2009-12-22 13:43:26 +0100299 vty_out(vty, " rach tx integer %u%s",
300 bts->si_common.rach_control.tx_integer, VTY_NEWLINE);
301 vty_out(vty, " rach max transmission %u%s",
302 rach_max_trans_raw2val(bts->si_common.rach_control.max_trans),
303 VTY_NEWLINE);
Harald Welte71355012009-12-21 23:08:18 +0100304 if (bts->si_common.rach_control.cell_bar)
Harald Welte (local)5dececf2009-08-12 13:28:23 +0200305 vty_out(vty, " cell barred 1%s", VTY_NEWLINE);
Harald Welte8175e952009-10-20 00:22:00 +0200306 if (is_ipaccess_bts(bts)) {
Harald Welte5013b2a2009-08-07 13:29:14 +0200307 vty_out(vty, " ip.access unit_id %u %u%s",
Harald Weltea6fd58e2009-08-07 00:25:23 +0200308 bts->ip_access.site_id, bts->ip_access.bts_id, VTY_NEWLINE);
Harald Welte8175e952009-10-20 00:22:00 +0200309 vty_out(vty, " oml ip.access stream_id %u%s", bts->oml_tei, VTY_NEWLINE);
310 } else {
Harald Welte42581822009-08-08 16:12:58 +0200311 config_write_e1_link(vty, &bts->oml_e1_link, " oml ");
312 vty_out(vty, " oml e1 tei %u%s", bts->oml_tei, VTY_NEWLINE);
313 }
Harald Welte67ce0732009-08-06 19:06:46 +0200314
315 llist_for_each_entry(trx, &bts->trx_list, list)
316 config_write_trx_single(vty, trx);
317}
318
319static int config_write_bts(struct vty *v)
320{
321 struct gsm_bts *bts;
322
323 llist_for_each_entry(bts, &gsmnet->bts_list, list)
324 config_write_bts_single(v, bts);
325
326 return CMD_SUCCESS;
327}
328
Harald Welte5013b2a2009-08-07 13:29:14 +0200329static int config_write_net(struct vty *vty)
330{
331 vty_out(vty, "network%s", VTY_NEWLINE);
Harald Welte42581822009-08-08 16:12:58 +0200332 vty_out(vty, " network country code %u%s", gsmnet->country_code, VTY_NEWLINE);
Harald Welte5013b2a2009-08-07 13:29:14 +0200333 vty_out(vty, " mobile network code %u%s", gsmnet->network_code, VTY_NEWLINE);
Harald Welte42581822009-08-08 16:12:58 +0200334 vty_out(vty, " short name %s%s", gsmnet->name_short, VTY_NEWLINE);
335 vty_out(vty, " long name %s%s", gsmnet->name_long, VTY_NEWLINE);
Harald Welte (local)69de3972009-08-12 14:42:23 +0200336 vty_out(vty, " auth policy %s%s", gsm_auth_policy_name(gsmnet->auth_policy), VTY_NEWLINE);
Harald Welte1085c092009-11-18 20:33:19 +0100337 vty_out(vty, " location updating reject cause %u%s",
338 gsmnet->reject_cause, VTY_NEWLINE);
Harald Welte4381cfe2009-08-30 15:47:06 +0900339 vty_out(vty, " encryption a5 %u%s", gsmnet->a5_encryption, VTY_NEWLINE);
Holger Hans Peter Freytherd54c3372009-11-19 16:37:48 +0100340 vty_out(vty, " neci %u%s", gsmnet->neci, VTY_NEWLINE);
Harald Welteeab84a12009-12-13 10:53:12 +0100341 vty_out(vty, " rrlp mode %s%s", rrlp_mode_name(gsmnet->rrlp.mode),
342 VTY_NEWLINE);
Harald Welte648b6ce2009-12-14 09:00:24 +0100343 vty_out(vty, " mm info %u%s", gsmnet->send_mm_info, VTY_NEWLINE);
Harald Weltebc814502009-12-19 21:41:52 +0100344 vty_out(vty, " handover %u%s", gsmnet->handover.active, VTY_NEWLINE);
Harald Welteb720bd32009-12-21 16:51:50 +0100345 vty_out(vty, " handover window rxlev averaging %u%s",
346 gsmnet->handover.win_rxlev_avg, VTY_NEWLINE);
347 vty_out(vty, " handover window rxqual averaging %u%s",
348 gsmnet->handover.win_rxqual_avg, VTY_NEWLINE);
349 vty_out(vty, " handover window rxlev neighbor averaging %u%s",
350 gsmnet->handover.win_rxlev_avg_neigh, VTY_NEWLINE);
351 vty_out(vty, " handover power budget interval %u%s",
352 gsmnet->handover.pwr_interval, VTY_NEWLINE);
353 vty_out(vty, " handover power budget hysteresis %u%s",
354 gsmnet->handover.pwr_hysteresis, VTY_NEWLINE);
355 vty_out(vty, " handover maximum distance %u%s",
356 gsmnet->handover.max_distance, VTY_NEWLINE);
Holger Hans Peter Freytherc4d88ad2009-11-21 21:18:38 +0100357 vty_out(vty, " timer t3101 %u%s", gsmnet->T3101, VTY_NEWLINE);
Holger Hans Peter Freyther23975e72009-11-21 21:42:26 +0100358 vty_out(vty, " timer t3103 %u%s", gsmnet->T3103, VTY_NEWLINE);
359 vty_out(vty, " timer t3105 %u%s", gsmnet->T3105, VTY_NEWLINE);
360 vty_out(vty, " timer t3107 %u%s", gsmnet->T3107, VTY_NEWLINE);
361 vty_out(vty, " timer t3109 %u%s", gsmnet->T3109, VTY_NEWLINE);
362 vty_out(vty, " timer t3111 %u%s", gsmnet->T3111, VTY_NEWLINE);
363 vty_out(vty, " timer t3113 %u%s", gsmnet->T3113, VTY_NEWLINE);
364 vty_out(vty, " timer t3115 %u%s", gsmnet->T3115, VTY_NEWLINE);
365 vty_out(vty, " timer t3117 %u%s", gsmnet->T3117, VTY_NEWLINE);
366 vty_out(vty, " timer t3119 %u%s", gsmnet->T3119, VTY_NEWLINE);
367 vty_out(vty, " timer t3141 %u%s", gsmnet->T3141, VTY_NEWLINE);
Harald Welte5013b2a2009-08-07 13:29:14 +0200368
369 return CMD_SUCCESS;
370}
Harald Welte67ce0732009-08-06 19:06:46 +0200371
Harald Welte68628e82009-03-10 12:17:57 +0000372static void trx_dump_vty(struct vty *vty, struct gsm_bts_trx *trx)
373{
374 vty_out(vty, "TRX %u of BTS %u is on ARFCN %u%s",
375 trx->nr, trx->bts->nr, trx->arfcn, VTY_NEWLINE);
Harald Weltefcd24452009-06-20 18:15:19 +0200376 vty_out(vty, " RF Nominal Power: %d dBm, reduced by %u dB, "
Harald Welte42581822009-08-08 16:12:58 +0200377 "resulting BS power: %d dBm%s",
Harald Weltefcd24452009-06-20 18:15:19 +0200378 trx->nominal_power, trx->max_power_red,
Harald Welte42581822009-08-08 16:12:58 +0200379 trx->nominal_power - trx->max_power_red, VTY_NEWLINE);
Harald Welte68628e82009-03-10 12:17:57 +0000380 vty_out(vty, " NM State: ");
381 net_dump_nmstate(vty, &trx->nm_state);
382 vty_out(vty, " Baseband Transceiver NM State: ");
383 net_dump_nmstate(vty, &trx->bb_transc.nm_state);
Harald Welte8175e952009-10-20 00:22:00 +0200384 if (is_ipaccess_bts(trx->bts)) {
385 vty_out(vty, " ip.access stream ID: 0x%02x%s",
386 trx->rsl_tei, VTY_NEWLINE);
387 } else {
388 vty_out(vty, " E1 Signalling Link:%s", VTY_NEWLINE);
389 e1isl_dump_vty(vty, trx->rsl_link);
390 }
Harald Welte68628e82009-03-10 12:17:57 +0000391}
392
393DEFUN(show_trx,
394 show_trx_cmd,
395 "show trx [bts_nr] [trx_nr]",
396 SHOW_STR "Display information about a TRX\n")
397{
398 struct gsm_network *net = gsmnet;
399 struct gsm_bts *bts = NULL;
400 struct gsm_bts_trx *trx;
401 int bts_nr, trx_nr;
402
403 if (argc >= 1) {
404 /* use the BTS number that the user has specified */
405 bts_nr = atoi(argv[0]);
406 if (bts_nr >= net->num_bts) {
Harald Welte1bc77352009-03-10 19:47:51 +0000407 vty_out(vty, "%% can't find BTS '%s'%s", argv[0],
Harald Welte68628e82009-03-10 12:17:57 +0000408 VTY_NEWLINE);
409 return CMD_WARNING;
410 }
Harald Weltee441d9c2009-06-21 16:17:15 +0200411 bts = gsm_bts_num(net, bts_nr);
Harald Welte68628e82009-03-10 12:17:57 +0000412 }
413 if (argc >= 2) {
414 trx_nr = atoi(argv[1]);
415 if (trx_nr >= bts->num_trx) {
Harald Welte1bc77352009-03-10 19:47:51 +0000416 vty_out(vty, "%% can't find TRX '%s'%s", argv[1],
Harald Welte68628e82009-03-10 12:17:57 +0000417 VTY_NEWLINE);
418 return CMD_WARNING;
419 }
Harald Weltee441d9c2009-06-21 16:17:15 +0200420 trx = gsm_bts_trx_num(bts, trx_nr);
Harald Welte68628e82009-03-10 12:17:57 +0000421 trx_dump_vty(vty, trx);
422 return CMD_SUCCESS;
423 }
424 if (bts) {
425 /* print all TRX in this BTS */
426 for (trx_nr = 0; trx_nr < bts->num_trx; trx_nr++) {
Harald Weltee441d9c2009-06-21 16:17:15 +0200427 trx = gsm_bts_trx_num(bts, trx_nr);
Harald Welte68628e82009-03-10 12:17:57 +0000428 trx_dump_vty(vty, trx);
429 }
430 return CMD_SUCCESS;
431 }
432
433 for (bts_nr = 0; bts_nr < net->num_bts; bts_nr++) {
Harald Weltee441d9c2009-06-21 16:17:15 +0200434 bts = gsm_bts_num(net, bts_nr);
Harald Welte68628e82009-03-10 12:17:57 +0000435 for (trx_nr = 0; trx_nr < bts->num_trx; trx_nr++) {
Harald Weltee441d9c2009-06-21 16:17:15 +0200436 trx = gsm_bts_trx_num(bts, trx_nr);
Harald Welte68628e82009-03-10 12:17:57 +0000437 trx_dump_vty(vty, trx);
438 }
439 }
440
441 return CMD_SUCCESS;
442}
443
Harald Welte67ce0732009-08-06 19:06:46 +0200444
Harald Welte68628e82009-03-10 12:17:57 +0000445static void ts_dump_vty(struct vty *vty, struct gsm_bts_trx_ts *ts)
446{
Harald Welte68628e82009-03-10 12:17:57 +0000447 vty_out(vty, "Timeslot %u of TRX %u in BTS %u, phys cfg %s%s",
448 ts->nr, ts->trx->nr, ts->trx->bts->nr,
449 gsm_pchan_name(ts->pchan), VTY_NEWLINE);
450 vty_out(vty, " NM State: ");
451 net_dump_nmstate(vty, &ts->nm_state);
Harald Welte2c828992009-12-02 01:56:49 +0530452 if (!is_ipaccess_bts(ts->trx->bts))
Harald Welteef235b52009-03-10 12:34:02 +0000453 vty_out(vty, " E1 Line %u, Timeslot %u, Subslot %u%s",
454 ts->e1_link.e1_nr, ts->e1_link.e1_ts,
455 ts->e1_link.e1_ts_ss, VTY_NEWLINE);
Harald Welte68628e82009-03-10 12:17:57 +0000456}
457
458DEFUN(show_ts,
459 show_ts_cmd,
Harald Welte1bc77352009-03-10 19:47:51 +0000460 "show timeslot [bts_nr] [trx_nr] [ts_nr]",
Harald Welte68628e82009-03-10 12:17:57 +0000461 SHOW_STR "Display information about a TS\n")
462{
463 struct gsm_network *net = gsmnet;
464 struct gsm_bts *bts;
465 struct gsm_bts_trx *trx;
466 struct gsm_bts_trx_ts *ts;
467 int bts_nr, trx_nr, ts_nr;
468
469 if (argc >= 1) {
470 /* use the BTS number that the user has specified */
471 bts_nr = atoi(argv[0]);
472 if (bts_nr >= net->num_bts) {
Harald Welte1bc77352009-03-10 19:47:51 +0000473 vty_out(vty, "%% can't find BTS '%s'%s", argv[0],
Harald Welte68628e82009-03-10 12:17:57 +0000474 VTY_NEWLINE);
475 return CMD_WARNING;
476 }
Harald Weltee441d9c2009-06-21 16:17:15 +0200477 bts = gsm_bts_num(net, bts_nr);
Harald Welte68628e82009-03-10 12:17:57 +0000478 }
479 if (argc >= 2) {
480 trx_nr = atoi(argv[1]);
481 if (trx_nr >= bts->num_trx) {
Harald Welte1bc77352009-03-10 19:47:51 +0000482 vty_out(vty, "%% can't find TRX '%s'%s", argv[1],
Harald Welte68628e82009-03-10 12:17:57 +0000483 VTY_NEWLINE);
484 return CMD_WARNING;
485 }
Harald Weltee441d9c2009-06-21 16:17:15 +0200486 trx = gsm_bts_trx_num(bts, trx_nr);
Harald Welte68628e82009-03-10 12:17:57 +0000487 }
488 if (argc >= 3) {
489 ts_nr = atoi(argv[2]);
490 if (ts_nr >= TRX_NR_TS) {
Harald Welte1bc77352009-03-10 19:47:51 +0000491 vty_out(vty, "%% can't find TS '%s'%s", argv[2],
Harald Welte68628e82009-03-10 12:17:57 +0000492 VTY_NEWLINE);
493 return CMD_WARNING;
494 }
495 ts = &trx->ts[ts_nr];
496 ts_dump_vty(vty, ts);
497 return CMD_SUCCESS;
498 }
499 for (bts_nr = 0; bts_nr < net->num_bts; bts_nr++) {
Harald Weltee441d9c2009-06-21 16:17:15 +0200500 bts = gsm_bts_num(net, bts_nr);
Harald Welte68628e82009-03-10 12:17:57 +0000501 for (trx_nr = 0; trx_nr < bts->num_trx; trx_nr++) {
Harald Weltee441d9c2009-06-21 16:17:15 +0200502 trx = gsm_bts_trx_num(bts, trx_nr);
Harald Welte68628e82009-03-10 12:17:57 +0000503 for (ts_nr = 0; ts_nr < TRX_NR_TS; ts_nr++) {
504 ts = &trx->ts[ts_nr];
505 ts_dump_vty(vty, ts);
506 }
507 }
508 }
509
510 return CMD_SUCCESS;
511}
512
Holger Hans Peter Freythercfa90d42009-08-10 10:17:50 +0200513void subscr_dump_vty(struct vty *vty, struct gsm_subscriber *subscr)
Harald Welte68628e82009-03-10 12:17:57 +0000514{
Harald Weltefcd24452009-06-20 18:15:19 +0200515 vty_out(vty, " ID: %llu, Authorized: %d%s", subscr->id,
Harald Welte40f82892009-05-23 17:31:39 +0000516 subscr->authorized, VTY_NEWLINE);
Harald Welte68628e82009-03-10 12:17:57 +0000517 if (subscr->name)
Harald Welte1bc77352009-03-10 19:47:51 +0000518 vty_out(vty, " Name: '%s'%s", subscr->name, VTY_NEWLINE);
Harald Welte68628e82009-03-10 12:17:57 +0000519 if (subscr->extension)
520 vty_out(vty, " Extension: %s%s", subscr->extension,
521 VTY_NEWLINE);
522 if (subscr->imsi)
523 vty_out(vty, " IMSI: %s%s", subscr->imsi, VTY_NEWLINE);
Holger Hans Peter Freyther22230252009-08-19 12:53:57 +0200524 if (subscr->tmsi != GSM_RESERVED_TMSI)
525 vty_out(vty, " TMSI: %08X%s", subscr->tmsi,
Harald Welte731fd912009-08-15 03:24:51 +0200526 VTY_NEWLINE);
Harald Welte (local)15920de2009-08-14 20:27:16 +0200527 vty_out(vty, " Use count: %u%s", subscr->use_count, VTY_NEWLINE);
Harald Welte68628e82009-03-10 12:17:57 +0000528}
529
Harald Welte8387a492009-12-22 21:43:14 +0100530static void meas_rep_dump_uni_vty(struct vty *vty,
531 struct gsm_meas_rep_unidir *mru,
532 const char *prefix,
533 const char *dir)
534{
535 vty_out(vty, "%s RXL-FULL-%s: %4d dBm, RXL-SUB-%s: %4d dBm ",
536 prefix, dir, rxlev2dbm(mru->full.rx_lev),
537 dir, rxlev2dbm(mru->sub.rx_lev));
538 vty_out(vty, "RXQ-FULL-%s: %d, RXQ-SUB-%s: %d%s",
539 dir, mru->full.rx_qual, dir, mru->sub.rx_qual,
540 VTY_NEWLINE);
541}
542
543static void meas_rep_dump_vty(struct vty *vty, struct gsm_meas_rep *mr,
544 const char *prefix)
545{
546 vty_out(vty, "%sMeasurement Report:%s", prefix, VTY_NEWLINE);
547 vty_out(vty, "%s Flags: %s%s%s%s%s", prefix,
548 mr->flags & MEAS_REP_F_UL_DTX ? "DTXu " : "",
549 mr->flags & MEAS_REP_F_DL_DTX ? "DTXd " : "",
550 mr->flags & MEAS_REP_F_FPC ? "FPC " : "",
551 mr->flags & MEAS_REP_F_DL_VALID ? " " : "DLinval ",
552 VTY_NEWLINE);
553 if (mr->flags & MEAS_REP_F_MS_TO)
554 vty_out(vty, "%s MS Timing Offset: %u%s", prefix,
555 mr->ms_timing_offset, VTY_NEWLINE);
556 if (mr->flags & MEAS_REP_F_MS_L1)
557 vty_out(vty, "%s L1 MS Power: %u dBm, Timing Advance: %u%s",
558 prefix, mr->ms_l1.pwr, mr->ms_l1.ta, VTY_NEWLINE);
559 if (mr->flags & MEAS_REP_F_DL_VALID)
560 meas_rep_dump_uni_vty(vty, &mr->dl, prefix, "dl");
561 meas_rep_dump_uni_vty(vty, &mr->ul, prefix, "ul");
562}
563
Harald Welte68628e82009-03-10 12:17:57 +0000564static void lchan_dump_vty(struct vty *vty, struct gsm_lchan *lchan)
565{
Harald Welte8387a492009-12-22 21:43:14 +0100566 int idx;
567
Harald Welte68628e82009-03-10 12:17:57 +0000568 vty_out(vty, "Lchan %u in Timeslot %u of TRX %u in BTS %u, Type %s%s",
569 lchan->nr, lchan->ts->nr, lchan->ts->trx->nr,
570 lchan->ts->trx->bts->nr, gsm_lchan_name(lchan->type),
571 VTY_NEWLINE);
572 vty_out(vty, " Use Count: %u%s", lchan->use_count, VTY_NEWLINE);
Harald Welte73225282009-12-12 18:17:25 +0100573 vty_out(vty, " BS Power: %u dBm, MS Power: %u dBm%s",
574 lchan->ts->trx->nominal_power - lchan->ts->trx->max_power_red
575 - lchan->bs_power*2,
576 ms_pwr_dbm(lchan->ts->trx->bts->band, lchan->ms_power),
577 VTY_NEWLINE);
Harald Welte68628e82009-03-10 12:17:57 +0000578 if (lchan->subscr) {
579 vty_out(vty, " Subscriber:%s", VTY_NEWLINE);
580 subscr_dump_vty(vty, lchan->subscr);
581 } else
582 vty_out(vty, " No Subscriber%s", VTY_NEWLINE);
Harald Welte2c828992009-12-02 01:56:49 +0530583 if (is_ipaccess_bts(lchan->ts->trx->bts)) {
584 struct in_addr ia;
585 ia.s_addr = lchan->abis_ip.bound_ip;
586 vty_out(vty, " Bound IP: %s Port %u RTP_TYPE2=%u CONN_ID=%u%s",
587 inet_ntoa(ia), lchan->abis_ip.bound_port,
588 lchan->abis_ip.rtp_payload2, lchan->abis_ip.conn_id,
589 VTY_NEWLINE);
590 }
Harald Welte8387a492009-12-22 21:43:14 +0100591
592 /* we want to report the last measurement report */
593 idx = calc_initial_idx(ARRAY_SIZE(lchan->meas_rep),
594 lchan->meas_rep_idx, 1);
595 meas_rep_dump_vty(vty, &lchan->meas_rep[idx], " ");
Harald Welte68628e82009-03-10 12:17:57 +0000596}
597
Harald Welte4bfdfe72009-06-10 23:11:52 +0800598#if 0
599TODO: callref and remote callref of call must be resolved to get gsm_trans object
Harald Welte68628e82009-03-10 12:17:57 +0000600static void call_dump_vty(struct vty *vty, struct gsm_call *call)
601{
602 vty_out(vty, "Call Type %u, State %u, Transaction ID %u%s",
603 call->type, call->state, call->transaction_id, VTY_NEWLINE);
604
605 if (call->local_lchan) {
606 vty_out(vty, "Call Local Channel:%s", VTY_NEWLINE);
607 lchan_dump_vty(vty, call->local_lchan);
608 } else
609 vty_out(vty, "Call has no Local Channel%s", VTY_NEWLINE);
610
611 if (call->remote_lchan) {
612 vty_out(vty, "Call Remote Channel:%s", VTY_NEWLINE);
613 lchan_dump_vty(vty, call->remote_lchan);
614 } else
615 vty_out(vty, "Call has no Remote Channel%s", VTY_NEWLINE);
616
617 if (call->called_subscr) {
618 vty_out(vty, "Called Subscriber:%s", VTY_NEWLINE);
619 subscr_dump_vty(vty, call->called_subscr);
620 } else
621 vty_out(vty, "Call has no Called Subscriber%s", VTY_NEWLINE);
622}
Harald Welte4bfdfe72009-06-10 23:11:52 +0800623#endif
Harald Welte68628e82009-03-10 12:17:57 +0000624
625DEFUN(show_lchan,
626 show_lchan_cmd,
627 "show lchan [bts_nr] [trx_nr] [ts_nr] [lchan_nr]",
628 SHOW_STR "Display information about a logical channel\n")
629{
630 struct gsm_network *net = gsmnet;
631 struct gsm_bts *bts;
632 struct gsm_bts_trx *trx;
633 struct gsm_bts_trx_ts *ts;
634 struct gsm_lchan *lchan;
635 int bts_nr, trx_nr, ts_nr, lchan_nr;
636
637 if (argc >= 1) {
638 /* use the BTS number that the user has specified */
639 bts_nr = atoi(argv[0]);
640 if (bts_nr >= net->num_bts) {
641 vty_out(vty, "%% can't find BTS %s%s", argv[0],
642 VTY_NEWLINE);
643 return CMD_WARNING;
644 }
Harald Weltee441d9c2009-06-21 16:17:15 +0200645 bts = gsm_bts_num(net, bts_nr);
Harald Welte68628e82009-03-10 12:17:57 +0000646 }
647 if (argc >= 2) {
648 trx_nr = atoi(argv[1]);
649 if (trx_nr >= bts->num_trx) {
650 vty_out(vty, "%% can't find TRX %s%s", argv[1],
651 VTY_NEWLINE);
652 return CMD_WARNING;
653 }
Harald Weltee441d9c2009-06-21 16:17:15 +0200654 trx = gsm_bts_trx_num(bts, trx_nr);
Harald Welte68628e82009-03-10 12:17:57 +0000655 }
656 if (argc >= 3) {
657 ts_nr = atoi(argv[2]);
658 if (ts_nr >= TRX_NR_TS) {
659 vty_out(vty, "%% can't find TS %s%s", argv[2],
660 VTY_NEWLINE);
661 return CMD_WARNING;
662 }
663 ts = &trx->ts[ts_nr];
664 }
665 if (argc >= 4) {
666 lchan_nr = atoi(argv[3]);
667 if (lchan_nr >= TS_MAX_LCHAN) {
668 vty_out(vty, "%% can't find LCHAN %s%s", argv[3],
669 VTY_NEWLINE);
670 return CMD_WARNING;
671 }
672 lchan = &ts->lchan[lchan_nr];
673 lchan_dump_vty(vty, lchan);
674 return CMD_SUCCESS;
675 }
676 for (bts_nr = 0; bts_nr < net->num_bts; bts_nr++) {
Harald Weltee441d9c2009-06-21 16:17:15 +0200677 bts = gsm_bts_num(net, bts_nr);
Harald Welte68628e82009-03-10 12:17:57 +0000678 for (trx_nr = 0; trx_nr < bts->num_trx; trx_nr++) {
Harald Weltee441d9c2009-06-21 16:17:15 +0200679 trx = gsm_bts_trx_num(bts, trx_nr);
Harald Welte68628e82009-03-10 12:17:57 +0000680 for (ts_nr = 0; ts_nr < TRX_NR_TS; ts_nr++) {
681 ts = &trx->ts[ts_nr];
682 for (lchan_nr = 0; lchan_nr < TS_MAX_LCHAN;
683 lchan_nr++) {
684 lchan = &ts->lchan[lchan_nr];
Harald Welteef235b52009-03-10 12:34:02 +0000685 if (lchan->type == GSM_LCHAN_NONE)
686 continue;
Harald Welte68628e82009-03-10 12:17:57 +0000687 lchan_dump_vty(vty, lchan);
688 }
689 }
690 }
691 }
692
693 return CMD_SUCCESS;
694}
695
Harald Welte1bc77352009-03-10 19:47:51 +0000696static void e1drv_dump_vty(struct vty *vty, struct e1inp_driver *drv)
697{
698 vty_out(vty, "E1 Input Driver %s%s", drv->name, VTY_NEWLINE);
699}
700
701DEFUN(show_e1drv,
702 show_e1drv_cmd,
703 "show e1_driver",
704 SHOW_STR "Display information about available E1 drivers\n")
705{
706 struct e1inp_driver *drv;
707
708 llist_for_each_entry(drv, &e1inp_driver_list, list)
709 e1drv_dump_vty(vty, drv);
710
711 return CMD_SUCCESS;
712}
713
Harald Welte68628e82009-03-10 12:17:57 +0000714static void e1line_dump_vty(struct vty *vty, struct e1inp_line *line)
715{
716 vty_out(vty, "E1 Line Number %u, Name %s, Driver %s%s",
717 line->num, line->name ? line->name : "",
718 line->driver->name, VTY_NEWLINE);
719}
720
721DEFUN(show_e1line,
722 show_e1line_cmd,
723 "show e1_line [line_nr]",
724 SHOW_STR "Display information about a E1 line\n")
725{
Harald Welte1bc77352009-03-10 19:47:51 +0000726 struct e1inp_line *line;
727
728 if (argc >= 1) {
729 int num = atoi(argv[0]);
730 llist_for_each_entry(line, &e1inp_line_list, list) {
731 if (line->num == num) {
732 e1line_dump_vty(vty, line);
733 return CMD_SUCCESS;
734 }
735 }
736 return CMD_WARNING;
737 }
738
739 llist_for_each_entry(line, &e1inp_line_list, list)
740 e1line_dump_vty(vty, line);
741
742 return CMD_SUCCESS;
Harald Welte68628e82009-03-10 12:17:57 +0000743}
744
745static void e1ts_dump_vty(struct vty *vty, struct e1inp_ts *ts)
746{
Harald Welte42581822009-08-08 16:12:58 +0200747 if (ts->type == E1INP_TS_TYPE_NONE)
748 return;
Harald Welte1bc77352009-03-10 19:47:51 +0000749 vty_out(vty, "E1 Timeslot %2u of Line %u is Type %s%s",
750 ts->num, ts->line->num, e1inp_tstype_name(ts->type),
751 VTY_NEWLINE);
Harald Welte68628e82009-03-10 12:17:57 +0000752}
753
754DEFUN(show_e1ts,
755 show_e1ts_cmd,
756 "show e1_timeslot [line_nr] [ts_nr]",
757 SHOW_STR "Display information about a E1 timeslot\n")
758{
Harald Welte986c3d72009-11-17 06:12:16 +0100759 struct e1inp_line *line = NULL;
Harald Welte1bc77352009-03-10 19:47:51 +0000760 struct e1inp_ts *ts;
761 int ts_nr;
Harald Welte68628e82009-03-10 12:17:57 +0000762
Harald Welte1bc77352009-03-10 19:47:51 +0000763 if (argc == 0) {
764 llist_for_each_entry(line, &e1inp_line_list, list) {
765 for (ts_nr = 0; ts_nr < NUM_E1_TS; ts_nr++) {
766 ts = &line->ts[ts_nr];
767 e1ts_dump_vty(vty, ts);
768 }
769 }
770 return CMD_SUCCESS;
771 }
772 if (argc >= 1) {
773 int num = atoi(argv[0]);
774 llist_for_each_entry(line, &e1inp_line_list, list) {
775 if (line->num == num)
776 break;
777 }
778 if (!line || line->num != num) {
779 vty_out(vty, "E1 line %s is invalid%s",
780 argv[0], VTY_NEWLINE);
781 return CMD_WARNING;
782 }
783 }
784 if (argc >= 2) {
785 ts_nr = atoi(argv[1]);
786 if (ts_nr > NUM_E1_TS) {
787 vty_out(vty, "E1 timeslot %s is invalid%s",
788 argv[1], VTY_NEWLINE);
789 return CMD_WARNING;
790 }
791 ts = &line->ts[ts_nr];
792 e1ts_dump_vty(vty, ts);
793 return CMD_SUCCESS;
794 } else {
795 for (ts_nr = 0; ts_nr < NUM_E1_TS; ts_nr++) {
796 ts = &line->ts[ts_nr];
797 e1ts_dump_vty(vty, ts);
798 }
799 return CMD_SUCCESS;
800 }
801 return CMD_SUCCESS;
Harald Welte68628e82009-03-10 12:17:57 +0000802}
803
Harald Weltebe4b7302009-05-23 16:59:33 +0000804static void paging_dump_vty(struct vty *vty, struct gsm_paging_request *pag)
Harald Weltef5025b62009-03-28 16:55:11 +0000805{
806 vty_out(vty, "Paging on BTS %u%s", pag->bts->nr, VTY_NEWLINE);
807 subscr_dump_vty(vty, pag->subscr);
808}
809
Harald Weltebe4b7302009-05-23 16:59:33 +0000810static void bts_paging_dump_vty(struct vty *vty, struct gsm_bts *bts)
Harald Weltef5025b62009-03-28 16:55:11 +0000811{
812 struct gsm_paging_request *pag;
813
814 llist_for_each_entry(pag, &bts->paging.pending_requests, entry)
815 paging_dump_vty(vty, pag);
816}
817
818DEFUN(show_paging,
819 show_paging_cmd,
820 "show paging [bts_nr]",
Harald Weltebe4b7302009-05-23 16:59:33 +0000821 SHOW_STR "Display information about paging reuqests of a BTS\n")
Harald Weltef5025b62009-03-28 16:55:11 +0000822{
823 struct gsm_network *net = gsmnet;
824 struct gsm_bts *bts;
825 int bts_nr;
826
827 if (argc >= 1) {
828 /* use the BTS number that the user has specified */
829 bts_nr = atoi(argv[0]);
830 if (bts_nr >= net->num_bts) {
831 vty_out(vty, "%% can't find BTS %s%s", argv[0],
832 VTY_NEWLINE);
833 return CMD_WARNING;
834 }
Harald Weltee441d9c2009-06-21 16:17:15 +0200835 bts = gsm_bts_num(net, bts_nr);
Harald Weltef5025b62009-03-28 16:55:11 +0000836 bts_paging_dump_vty(vty, bts);
837
838 return CMD_SUCCESS;
839 }
840 for (bts_nr = 0; bts_nr < net->num_bts; bts_nr++) {
Harald Weltee441d9c2009-06-21 16:17:15 +0200841 bts = gsm_bts_num(net, bts_nr);
Harald Weltef5025b62009-03-28 16:55:11 +0000842 bts_paging_dump_vty(vty, bts);
843 }
844
845 return CMD_SUCCESS;
846}
847
Harald Welte24ff6ee2009-12-22 00:41:05 +0100848DEFUN(show_stats,
849 show_stats_cmd,
850 "show statistics",
851 SHOW_STR "Display network statistics\n")
852{
853 struct gsm_network *net = gsmnet;
854
Harald Weltee2b8ece2009-12-22 21:47:48 +0100855 vty_out(vty, "Channel Requests : %lu total, %lu no channel%s",
Harald Welteffa55a42009-12-22 19:07:32 +0100856 counter_get(net->stats.chreq.total),
857 counter_get(net->stats.chreq.no_channel), VTY_NEWLINE);
Harald Weltee2b8ece2009-12-22 21:47:48 +0100858 vty_out(vty, "Location Update : %lu attach, %lu normal, %lu periodic%s",
Harald Welteffa55a42009-12-22 19:07:32 +0100859 counter_get(net->stats.loc_upd_type.attach),
860 counter_get(net->stats.loc_upd_type.normal),
861 counter_get(net->stats.loc_upd_type.periodic), VTY_NEWLINE);
Harald Weltee2b8ece2009-12-22 21:47:48 +0100862 vty_out(vty, "IMSI Detach Indications : %lu%s",
Harald Welteffa55a42009-12-22 19:07:32 +0100863 counter_get(net->stats.loc_upd_type.detach), VTY_NEWLINE);
Harald Welte24ff6ee2009-12-22 00:41:05 +0100864 vty_out(vty, "Location Update Response: %lu accept, %lu reject%s",
Harald Welteffa55a42009-12-22 19:07:32 +0100865 counter_get(net->stats.loc_upd_resp.accept),
866 counter_get(net->stats.loc_upd_resp.reject), VTY_NEWLINE);
Harald Weltee2b8ece2009-12-22 21:47:48 +0100867 vty_out(vty, "Paging : %lu attempted, %lu complete, %lu expired%s",
Harald Welteffa55a42009-12-22 19:07:32 +0100868 counter_get(net->stats.paging.attempted),
869 counter_get(net->stats.paging.completed),
870 counter_get(net->stats.paging.expired), VTY_NEWLINE);
Harald Weltee2b8ece2009-12-22 21:47:48 +0100871 vty_out(vty, "Handover : %lu attempted, %lu no_channel, %lu timeout, "
Harald Welteffa55a42009-12-22 19:07:32 +0100872 "%lu completed, %lu failed%s",
873 counter_get(net->stats.handover.attempted),
874 counter_get(net->stats.handover.no_channel),
875 counter_get(net->stats.handover.timeout),
876 counter_get(net->stats.handover.completed),
877 counter_get(net->stats.handover.failed), VTY_NEWLINE);
Harald Weltee2b8ece2009-12-22 21:47:48 +0100878 vty_out(vty, "SMS MO : %lu submitted, %lu no receiver%s",
Harald Welteffa55a42009-12-22 19:07:32 +0100879 counter_get(net->stats.sms.submitted),
880 counter_get(net->stats.sms.no_receiver), VTY_NEWLINE);
Harald Weltee2b8ece2009-12-22 21:47:48 +0100881 vty_out(vty, "SMS MT : %lu delivered, %lu no memory, %lu other error%s",
Harald Welteffa55a42009-12-22 19:07:32 +0100882 counter_get(net->stats.sms.delivered),
883 counter_get(net->stats.sms.rp_err_mem),
884 counter_get(net->stats.sms.rp_err_other), VTY_NEWLINE);
Harald Welte24ff6ee2009-12-22 00:41:05 +0100885 return CMD_SUCCESS;
886}
887
Harald Welte5013b2a2009-08-07 13:29:14 +0200888DEFUN(cfg_net,
889 cfg_net_cmd,
890 "network",
891 "Configure the GSM network")
892{
893 vty->index = gsmnet;
894 vty->node = GSMNET_NODE;
895
896 return CMD_SUCCESS;
897}
898
899
900DEFUN(cfg_net_ncc,
901 cfg_net_ncc_cmd,
902 "network country code <1-999>",
903 "Set the GSM network country code")
904{
905 gsmnet->country_code = atoi(argv[0]);
906
907 return CMD_SUCCESS;
908}
909
910DEFUN(cfg_net_mnc,
911 cfg_net_mnc_cmd,
912 "mobile network code <1-999>",
913 "Set the GSM mobile network code")
914{
915 gsmnet->network_code = atoi(argv[0]);
916
917 return CMD_SUCCESS;
918}
919
920DEFUN(cfg_net_name_short,
921 cfg_net_name_short_cmd,
922 "short name NAME",
923 "Set the short GSM network name")
924{
925 if (gsmnet->name_short)
926 talloc_free(gsmnet->name_short);
927
928 gsmnet->name_short = talloc_strdup(gsmnet, argv[0]);
929
930 return CMD_SUCCESS;
931}
932
933DEFUN(cfg_net_name_long,
934 cfg_net_name_long_cmd,
935 "long name NAME",
936 "Set the long GSM network name")
937{
938 if (gsmnet->name_long)
939 talloc_free(gsmnet->name_long);
940
941 gsmnet->name_long = talloc_strdup(gsmnet, argv[0]);
942
943 return CMD_SUCCESS;
944}
Harald Welte40f82892009-05-23 17:31:39 +0000945
Harald Welte (local)69de3972009-08-12 14:42:23 +0200946DEFUN(cfg_net_auth_policy,
947 cfg_net_auth_policy_cmd,
948 "auth policy (closed|accept-all|token)",
949 "Set the GSM network authentication policy\n")
950{
951 enum gsm_auth_policy policy = gsm_auth_policy_parse(argv[0]);
952
953 gsmnet->auth_policy = policy;
954
955 return CMD_SUCCESS;
956}
957
Harald Welte1085c092009-11-18 20:33:19 +0100958DEFUN(cfg_net_reject_cause,
959 cfg_net_reject_cause_cmd,
960 "location updating reject cause <2-111>",
961 "Set the reject cause of location updating reject\n")
962{
963 gsmnet->reject_cause = atoi(argv[0]);
964
965 return CMD_SUCCESS;
966}
967
Harald Welte4381cfe2009-08-30 15:47:06 +0900968DEFUN(cfg_net_encryption,
969 cfg_net_encryption_cmd,
970 "encryption a5 (0|1|2)",
971 "Enable or disable encryption (A5) for this network\n")
972{
Andreas.Eversberg1059deb2009-11-17 09:55:26 +0100973 gsmnet->a5_encryption= atoi(argv[0]);
Harald Welte4381cfe2009-08-30 15:47:06 +0900974
975 return CMD_SUCCESS;
976}
977
Holger Hans Peter Freytherf7d752f2009-11-16 17:12:38 +0100978DEFUN(cfg_net_neci,
979 cfg_net_neci_cmd,
980 "neci (0|1)",
981 "Set if NECI of cell selection is to be set")
982{
983 gsmnet->neci = atoi(argv[0]);
984 return CMD_SUCCESS;
985}
986
Harald Welteeab84a12009-12-13 10:53:12 +0100987DEFUN(cfg_net_rrlp_mode, cfg_net_rrlp_mode_cmd,
988 "rrlp mode (none|ms-based|ms-preferred|ass-preferred)",
989 "Set the Radio Resource Location Protocol Mode")
990{
991 gsmnet->rrlp.mode = rrlp_mode_parse(argv[0]);
992
993 return CMD_SUCCESS;
994}
995
Harald Welte648b6ce2009-12-14 09:00:24 +0100996DEFUN(cfg_net_mm_info, cfg_net_mm_info_cmd,
997 "mm info (0|1)",
998 "Whether to send MM INFO after LOC UPD ACCEPT")
999{
1000 gsmnet->send_mm_info = atoi(argv[0]);
1001
1002 return CMD_SUCCESS;
1003}
1004
Harald Weltebc814502009-12-19 21:41:52 +01001005DEFUN(cfg_net_handover, cfg_net_handover_cmd,
1006 "handover (0|1)",
1007 "Whether or not to use in-call handover")
1008{
Harald Weltefe03f0d2009-12-20 13:51:01 +01001009 if (ipacc_rtp_direct) {
1010 vty_out(vty, "%% Cannot enable handover unless RTP Proxy mode "
1011 "is enabled by using the -P command line option%s",
1012 VTY_NEWLINE);
1013 return CMD_WARNING;
1014 }
Harald Weltebc814502009-12-19 21:41:52 +01001015 gsmnet->handover.active = atoi(argv[0]);
1016
1017 return CMD_SUCCESS;
1018}
1019
Harald Welteb720bd32009-12-21 16:51:50 +01001020DEFUN(cfg_net_ho_win_rxlev_avg, cfg_net_ho_win_rxlev_avg_cmd,
1021 "handover window rxlev averaging <1-10>",
1022 "How many RxLev measurements are used for averaging")
1023{
1024 gsmnet->handover.win_rxlev_avg = atoi(argv[0]);
1025 return CMD_SUCCESS;
1026}
1027
1028DEFUN(cfg_net_ho_win_rxqual_avg, cfg_net_ho_win_rxqual_avg_cmd,
1029 "handover window rxqual averaging <1-10>",
1030 "How many RxQual measurements are used for averaging")
1031{
1032 gsmnet->handover.win_rxqual_avg = atoi(argv[0]);
1033 return CMD_SUCCESS;
1034}
1035
1036DEFUN(cfg_net_ho_win_rxlev_neigh_avg, cfg_net_ho_win_rxlev_avg_neigh_cmd,
1037 "handover window rxlev neighbor averaging <1-10>",
1038 "How many RxQual measurements are used for averaging")
1039{
1040 gsmnet->handover.win_rxlev_avg_neigh = atoi(argv[0]);
1041 return CMD_SUCCESS;
1042}
1043
1044DEFUN(cfg_net_ho_pwr_interval, cfg_net_ho_pwr_interval_cmd,
1045 "handover power budget interval <1-99>",
1046 "How often to check if we have a better cell (SACCH frames)")
1047{
1048 gsmnet->handover.pwr_interval = atoi(argv[0]);
1049 return CMD_SUCCESS;
1050}
1051
1052DEFUN(cfg_net_ho_pwr_hysteresis, cfg_net_ho_pwr_hysteresis_cmd,
1053 "handover power budget hysteresis <0-999>",
1054 "How many dB does a neighbor to be stronger to become a HO candidate")
1055{
1056 gsmnet->handover.pwr_hysteresis = atoi(argv[0]);
1057 return CMD_SUCCESS;
1058}
1059
1060DEFUN(cfg_net_ho_max_distance, cfg_net_ho_max_distance_cmd,
1061 "handover maximum distance <0-9999>",
1062 "How big is the maximum timing advance before HO is forced")
1063{
1064 gsmnet->handover.max_distance = atoi(argv[0]);
1065 return CMD_SUCCESS;
1066}
Harald Weltebc814502009-12-19 21:41:52 +01001067
Holger Hans Peter Freytherc8021062009-12-22 08:27:21 +01001068#define DECLARE_TIMER(number, doc) \
Holger Hans Peter Freytherc4d88ad2009-11-21 21:18:38 +01001069 DEFUN(cfg_net_T##number, \
1070 cfg_net_T##number##_cmd, \
1071 "timer t" #number " <0-65535>", \
Holger Hans Peter Freytherc8021062009-12-22 08:27:21 +01001072 doc) \
Holger Hans Peter Freytherc4d88ad2009-11-21 21:18:38 +01001073{ \
1074 int value = atoi(argv[0]); \
1075 \
1076 if (value < 0 || value > 65535) { \
1077 vty_out(vty, "Timer value %s out of range.%s", \
1078 argv[0], VTY_NEWLINE); \
1079 return CMD_WARNING; \
1080 } \
1081 \
1082 gsmnet->T##number = value; \
1083 return CMD_SUCCESS; \
1084}
1085
Holger Hans Peter Freytherc8021062009-12-22 08:27:21 +01001086DECLARE_TIMER(3101, "Set the timeout value for IMMEDIATE ASSIGNMENT.")
1087DECLARE_TIMER(3103, "Set the timeout value for HANDOVER.")
1088DECLARE_TIMER(3105, "Currently not used.")
1089DECLARE_TIMER(3107, "Currently not used.")
1090DECLARE_TIMER(3109, "Currently not used.")
1091DECLARE_TIMER(3111, "Currently not used.")
1092DECLARE_TIMER(3113, "Set the time to try paging a subscriber.")
1093DECLARE_TIMER(3115, "Currently not used.")
1094DECLARE_TIMER(3117, "Currently not used.")
1095DECLARE_TIMER(3119, "Currently not used.")
1096DECLARE_TIMER(3141, "Currently not used.")
Holger Hans Peter Freytherc4d88ad2009-11-21 21:18:38 +01001097
1098
Harald Welte5258fc42009-03-28 19:07:53 +00001099/* per-BTS configuration */
1100DEFUN(cfg_bts,
1101 cfg_bts_cmd,
1102 "bts BTS_NR",
1103 "Select a BTS to configure\n")
1104{
1105 int bts_nr = atoi(argv[0]);
1106 struct gsm_bts *bts;
1107
Harald Weltee441d9c2009-06-21 16:17:15 +02001108 if (bts_nr > gsmnet->num_bts) {
1109 vty_out(vty, "%% The next unused BTS number is %u%s",
1110 gsmnet->num_bts, VTY_NEWLINE);
Harald Welte5258fc42009-03-28 19:07:53 +00001111 return CMD_WARNING;
Harald Weltee441d9c2009-06-21 16:17:15 +02001112 } else if (bts_nr == gsmnet->num_bts) {
1113 /* allocate a new one */
1114 bts = gsm_bts_alloc(gsmnet, GSM_BTS_TYPE_UNKNOWN,
1115 HARDCODED_TSC, HARDCODED_BSIC);
1116 } else
1117 bts = gsm_bts_num(gsmnet, bts_nr);
1118
1119 if (!bts)
1120 return CMD_WARNING;
Harald Welte5258fc42009-03-28 19:07:53 +00001121
1122 vty->index = bts;
1123 vty->node = BTS_NODE;
1124
1125 return CMD_SUCCESS;
1126}
1127
1128DEFUN(cfg_bts_type,
1129 cfg_bts_type_cmd,
1130 "type TYPE",
1131 "Set the BTS type\n")
1132{
1133 struct gsm_bts *bts = vty->index;
1134
Harald Weltea6fd58e2009-08-07 00:25:23 +02001135 bts->type = parse_btstype(argv[0]);
1136
Harald Welte8175e952009-10-20 00:22:00 +02001137 if (is_ipaccess_bts(bts)) {
1138 /* Set the default OML Stream ID to 0xff */
1139 bts->oml_tei = 0xff;
1140 }
1141
Harald Welte5258fc42009-03-28 19:07:53 +00001142 return CMD_SUCCESS;
1143}
1144
Harald Weltefcd24452009-06-20 18:15:19 +02001145DEFUN(cfg_bts_band,
1146 cfg_bts_band_cmd,
1147 "band BAND",
1148 "Set the frequency band of this BTS\n")
1149{
1150 struct gsm_bts *bts = vty->index;
Harald Welte42581822009-08-08 16:12:58 +02001151 int band = gsm_band_parse(argv[0]);
Harald Weltefcd24452009-06-20 18:15:19 +02001152
1153 if (band < 0) {
1154 vty_out(vty, "%% BAND %d is not a valid GSM band%s",
1155 band, VTY_NEWLINE);
1156 return CMD_WARNING;
1157 }
1158
1159 bts->band = band;
1160
1161 return CMD_SUCCESS;
1162}
1163
Holger Hans Peter Freytherc4a49e32009-08-21 14:44:12 +02001164DEFUN(cfg_bts_ci,
1165 cfg_bts_ci_cmd,
1166 "cell_identity <0-65535>",
1167 "Set the Cell identity of this BTS\n")
1168{
1169 struct gsm_bts *bts = vty->index;
1170 int ci = atoi(argv[0]);
1171
1172 if (ci < 0 || ci > 0xffff) {
1173 vty_out(vty, "%% CI %d is not in the valid range (0-65535)%s",
1174 ci, VTY_NEWLINE);
1175 return CMD_WARNING;
1176 }
1177 bts->cell_identity = ci;
1178
1179 return CMD_SUCCESS;
1180}
1181
Harald Welte5258fc42009-03-28 19:07:53 +00001182DEFUN(cfg_bts_lac,
1183 cfg_bts_lac_cmd,
Holger Hans Peter Freyther0b7f4b32009-09-29 14:02:33 +02001184 "location_area_code <0-65535>",
Harald Welte5258fc42009-03-28 19:07:53 +00001185 "Set the Location Area Code (LAC) of this BTS\n")
1186{
1187 struct gsm_bts *bts = vty->index;
1188 int lac = atoi(argv[0]);
1189
Holger Hans Peter Freyther0b7f4b32009-09-29 14:02:33 +02001190 if (lac < 0 || lac > 0xffff) {
1191 vty_out(vty, "%% LAC %d is not in the valid range (0-65535)%s",
Harald Welte5258fc42009-03-28 19:07:53 +00001192 lac, VTY_NEWLINE);
1193 return CMD_WARNING;
1194 }
Holger Hans Peter Freythere48b9562009-10-01 04:07:15 +02001195
1196 if (lac == GSM_LAC_RESERVED_DETACHED || lac == GSM_LAC_RESERVED_ALL_BTS) {
1197 vty_out(vty, "%% LAC %d is reserved by GSM 04.08%s",
1198 lac, VTY_NEWLINE);
1199 return CMD_WARNING;
1200 }
1201
Harald Welte5258fc42009-03-28 19:07:53 +00001202 bts->location_area_code = lac;
1203
1204 return CMD_SUCCESS;
1205}
1206
Harald Weltea43f7892009-12-01 18:04:30 +05301207
Harald Welte5258fc42009-03-28 19:07:53 +00001208DEFUN(cfg_bts_tsc,
1209 cfg_bts_tsc_cmd,
1210 "training_sequence_code <0-255>",
1211 "Set the Training Sequence Code (TSC) of this BTS\n")
1212{
1213 struct gsm_bts *bts = vty->index;
1214 int tsc = atoi(argv[0]);
1215
1216 if (tsc < 0 || tsc > 0xff) {
1217 vty_out(vty, "%% TSC %d is not in the valid range (0-255)%s",
1218 tsc, VTY_NEWLINE);
1219 return CMD_WARNING;
1220 }
1221 bts->tsc = tsc;
1222
1223 return CMD_SUCCESS;
1224}
1225
Harald Welte78f2f502009-05-23 16:56:52 +00001226DEFUN(cfg_bts_bsic,
1227 cfg_bts_bsic_cmd,
1228 "base_station_id_code <0-63>",
1229 "Set the Base Station Identity Code (BSIC) of this BTS\n")
1230{
1231 struct gsm_bts *bts = vty->index;
1232 int bsic = atoi(argv[0]);
1233
1234 if (bsic < 0 || bsic > 0x3f) {
Harald Welte42581822009-08-08 16:12:58 +02001235 vty_out(vty, "%% BSIC %d is not in the valid range (0-255)%s",
Harald Welte78f2f502009-05-23 16:56:52 +00001236 bsic, VTY_NEWLINE);
1237 return CMD_WARNING;
1238 }
1239 bts->bsic = bsic;
1240
1241 return CMD_SUCCESS;
1242}
1243
1244
Harald Welte4cc34222009-05-01 15:12:31 +00001245DEFUN(cfg_bts_unit_id,
1246 cfg_bts_unit_id_cmd,
Harald Welte07dc73d2009-08-07 13:27:09 +02001247 "ip.access unit_id <0-65534> <0-255>",
1248 "Set the ip.access BTS Unit ID of this BTS\n")
Harald Welte4cc34222009-05-01 15:12:31 +00001249{
1250 struct gsm_bts *bts = vty->index;
1251 int site_id = atoi(argv[0]);
1252 int bts_id = atoi(argv[1]);
1253
Harald Welte07dc73d2009-08-07 13:27:09 +02001254 if (!is_ipaccess_bts(bts)) {
1255 vty_out(vty, "%% BTS is not of ip.access type%s", VTY_NEWLINE);
1256 return CMD_WARNING;
1257 }
1258
Harald Welte4cc34222009-05-01 15:12:31 +00001259 bts->ip_access.site_id = site_id;
1260 bts->ip_access.bts_id = bts_id;
1261
1262 return CMD_SUCCESS;
1263}
1264
Harald Welte8175e952009-10-20 00:22:00 +02001265DEFUN(cfg_bts_stream_id,
1266 cfg_bts_stream_id_cmd,
1267 "oml ip.access stream_id <0-255>",
1268 "Set the ip.access Stream ID of the OML link of this BTS\n")
1269{
1270 struct gsm_bts *bts = vty->index;
1271 int stream_id = atoi(argv[0]);
1272
1273 if (!is_ipaccess_bts(bts)) {
1274 vty_out(vty, "%% BTS is not of ip.access type%s", VTY_NEWLINE);
1275 return CMD_WARNING;
1276 }
1277
1278 bts->oml_tei = stream_id;
1279
1280 return CMD_SUCCESS;
1281}
1282
1283
Harald Welte42581822009-08-08 16:12:58 +02001284DEFUN(cfg_bts_oml_e1,
1285 cfg_bts_oml_e1_cmd,
1286 "oml e1 line E1_LINE timeslot <1-31> sub-slot (0|1|2|3|full)",
1287 "E1 interface to be used for OML\n")
1288{
1289 struct gsm_bts *bts = vty->index;
1290
1291 parse_e1_link(&bts->oml_e1_link, argv[0], argv[1], argv[2]);
1292
1293 return CMD_SUCCESS;
1294}
1295
1296
1297DEFUN(cfg_bts_oml_e1_tei,
1298 cfg_bts_oml_e1_tei_cmd,
1299 "oml e1 tei <0-63>",
1300 "Set the TEI to be used for OML")
1301{
1302 struct gsm_bts *bts = vty->index;
1303
1304 bts->oml_tei = atoi(argv[0]);
1305
1306 return CMD_SUCCESS;
1307}
1308
Harald Welte7a8fa412009-08-10 13:48:16 +02001309DEFUN(cfg_bts_challoc, cfg_bts_challoc_cmd,
1310 "channel allocator (ascending|descending)",
1311 "Should the channel allocator allocate in reverse TRX order?")
1312{
1313 struct gsm_bts *bts = vty->index;
1314
1315 if (!strcmp(argv[0], "ascending"))
1316 bts->chan_alloc_reverse = 0;
1317 else
1318 bts->chan_alloc_reverse = 1;
1319
1320 return CMD_SUCCESS;
1321}
1322
Sylvain Munaut4010f1e2009-12-22 13:43:26 +01001323DEFUN(cfg_bts_rach_tx_integer,
1324 cfg_bts_rach_tx_integer_cmd,
1325 "rach tx integer <0-15>",
1326 "Set the raw tx integer value in RACH Control parameters IE")
1327{
1328 struct gsm_bts *bts = vty->index;
1329 bts->si_common.rach_control.tx_integer = atoi(argv[0]) & 0xf;
1330 return CMD_SUCCESS;
1331}
1332
1333DEFUN(cfg_bts_rach_max_trans,
1334 cfg_bts_rach_max_trans_cmd,
1335 "rach max transmission (1|2|4|7)",
1336 "Set the maximum number of RACH burst transmissions")
1337{
1338 struct gsm_bts *bts = vty->index;
1339 bts->si_common.rach_control.max_trans = rach_max_trans_val2raw(atoi(argv[0]));
1340 return CMD_SUCCESS;
1341}
1342
Harald Welte (local)5dececf2009-08-12 13:28:23 +02001343DEFUN(cfg_bts_cell_barred, cfg_bts_cell_barred_cmd,
1344 "cell barred (0|1)",
1345 "Should this cell be barred from access?")
1346{
1347 struct gsm_bts *bts = vty->index;
1348
Harald Welte71355012009-12-21 23:08:18 +01001349 bts->si_common.rach_control.cell_bar = atoi(argv[0]);
Harald Welte (local)5dececf2009-08-12 13:28:23 +02001350
1351 return CMD_SUCCESS;
1352}
1353
Harald Welte (local)0e451d02009-08-13 10:14:26 +02001354DEFUN(cfg_bts_ms_max_power, cfg_bts_ms_max_power_cmd,
1355 "ms max power <0-40>",
1356 "Maximum transmit power of the MS")
1357{
1358 struct gsm_bts *bts = vty->index;
1359
1360 bts->ms_max_power = atoi(argv[0]);
1361
1362 return CMD_SUCCESS;
1363}
1364
Harald Welte73225282009-12-12 18:17:25 +01001365DEFUN(cfg_bts_cell_resel_hyst, cfg_bts_cell_resel_hyst_cmd,
1366 "cell reselection hysteresis <0-14>",
1367 "Cell Re-Selection Hysteresis in dB")
1368{
1369 struct gsm_bts *bts = vty->index;
1370
1371 bts->si_common.cell_sel_par.cell_resel_hyst = atoi(argv[0])/2;
1372
1373 return CMD_SUCCESS;
1374}
1375
1376DEFUN(cfg_bts_rxlev_acc_min, cfg_bts_rxlev_acc_min_cmd,
1377 "rxlev access min <0-63>",
1378 "Minimum RxLev needed for cell access (better than -110dBm)")
1379{
1380 struct gsm_bts *bts = vty->index;
1381
1382 bts->si_common.cell_sel_par.rxlev_acc_min = atoi(argv[0]);
1383
1384 return CMD_SUCCESS;
1385}
1386
Harald Welte (local)efc92312009-08-14 23:09:25 +02001387DEFUN(cfg_bts_per_loc_upd, cfg_bts_per_loc_upd_cmd,
1388 "periodic location update <0-1530>",
1389 "Periodic Location Updating Interval in Minutes")
1390{
1391 struct gsm_bts *bts = vty->index;
1392
Harald Weltea43f7892009-12-01 18:04:30 +05301393 bts->si_common.chan_desc.t3212 = atoi(argv[0]) / 10;
Harald Welte (local)efc92312009-08-14 23:09:25 +02001394
1395 return CMD_SUCCESS;
1396}
1397
Harald Welte7a8fa412009-08-10 13:48:16 +02001398
Harald Welte5258fc42009-03-28 19:07:53 +00001399/* per TRX configuration */
1400DEFUN(cfg_trx,
1401 cfg_trx_cmd,
1402 "trx TRX_NR",
1403 "Select a TRX to configure")
1404{
1405 int trx_nr = atoi(argv[0]);
1406 struct gsm_bts *bts = vty->index;
1407 struct gsm_bts_trx *trx;
1408
Harald Weltee441d9c2009-06-21 16:17:15 +02001409 if (trx_nr > bts->num_trx) {
1410 vty_out(vty, "%% The next unused TRX number in this BTS is %u%s",
1411 bts->num_trx, VTY_NEWLINE);
Harald Welte5258fc42009-03-28 19:07:53 +00001412 return CMD_WARNING;
Harald Weltee441d9c2009-06-21 16:17:15 +02001413 } else if (trx_nr == bts->num_trx) {
1414 /* we need to allocate a new one */
1415 trx = gsm_bts_trx_alloc(bts);
1416 } else
1417 trx = gsm_bts_trx_num(bts, trx_nr);
1418
1419 if (!trx)
1420 return CMD_WARNING;
Harald Welte5258fc42009-03-28 19:07:53 +00001421
1422 vty->index = trx;
1423 vty->node = TRX_NODE;
1424
1425 return CMD_SUCCESS;
1426}
1427
1428DEFUN(cfg_trx_arfcn,
1429 cfg_trx_arfcn_cmd,
1430 "arfcn <1-1024>",
1431 "Set the ARFCN for this TRX\n")
1432{
1433 int arfcn = atoi(argv[0]);
1434 struct gsm_bts_trx *trx = vty->index;
1435
1436 /* FIXME: check if this ARFCN is supported by this TRX */
1437
1438 trx->arfcn = arfcn;
1439
1440 /* FIXME: patch ARFCN into SYSTEM INFORMATION */
1441 /* FIXME: use OML layer to update the ARFCN */
1442 /* FIXME: use RSL layer to update SYSTEM INFORMATION */
1443
1444 return CMD_SUCCESS;
1445}
1446
Harald Weltefcd24452009-06-20 18:15:19 +02001447DEFUN(cfg_trx_max_power_red,
1448 cfg_trx_max_power_red_cmd,
1449 "max_power_red <0-100>",
1450 "Reduction of maximum BS RF Power in dB\n")
1451{
1452 int maxpwr_r = atoi(argv[0]);
1453 struct gsm_bts_trx *trx = vty->index;
Harald Welte61a83b22009-11-18 09:20:22 +01001454 int upper_limit = 24; /* default 12.21 max power red. */
Harald Weltefcd24452009-06-20 18:15:19 +02001455
1456 /* FIXME: check if our BTS type supports more than 12 */
1457 if (maxpwr_r < 0 || maxpwr_r > upper_limit) {
1458 vty_out(vty, "%% Power %d dB is not in the valid range%s",
1459 maxpwr_r, VTY_NEWLINE);
1460 return CMD_WARNING;
1461 }
1462 if (maxpwr_r & 1) {
1463 vty_out(vty, "%% Power %d dB is not an even value%s",
1464 maxpwr_r, VTY_NEWLINE);
1465 return CMD_WARNING;
1466 }
1467
1468 trx->max_power_red = maxpwr_r;
1469
1470 /* FIXME: make sure we update this using OML */
1471
1472 return CMD_SUCCESS;
1473}
1474
Harald Welte42581822009-08-08 16:12:58 +02001475DEFUN(cfg_trx_rsl_e1,
1476 cfg_trx_rsl_e1_cmd,
1477 "rsl e1 line E1_LINE timeslot <1-31> sub-slot (0|1|2|3|full)",
1478 "E1 interface to be used for RSL\n")
1479{
1480 struct gsm_bts_trx *trx = vty->index;
1481
1482 parse_e1_link(&trx->rsl_e1_link, argv[0], argv[1], argv[2]);
1483
1484 return CMD_SUCCESS;
1485}
1486
1487DEFUN(cfg_trx_rsl_e1_tei,
1488 cfg_trx_rsl_e1_tei_cmd,
1489 "rsl e1 tei <0-63>",
1490 "Set the TEI to be used for RSL")
1491{
1492 struct gsm_bts_trx *trx = vty->index;
1493
1494 trx->rsl_tei = atoi(argv[0]);
1495
1496 return CMD_SUCCESS;
1497}
1498
Holger Hans Peter Freyther2d501ea2009-11-11 11:54:24 +01001499DEFUN(cfg_trx_rf_locked,
1500 cfg_trx_rf_locked_cmd,
1501 "rf_locked (0|1)",
1502 "Turn off RF of the TRX.\n")
1503{
1504 int locked = atoi(argv[0]);
1505 struct gsm_bts_trx *trx = vty->index;
1506
1507 gsm_trx_lock_rf(trx, locked);
1508 return CMD_SUCCESS;
1509}
Harald Welte42581822009-08-08 16:12:58 +02001510
Harald Welte5258fc42009-03-28 19:07:53 +00001511/* per TS configuration */
1512DEFUN(cfg_ts,
1513 cfg_ts_cmd,
Harald Welte42581822009-08-08 16:12:58 +02001514 "timeslot <0-7>",
Harald Welte5258fc42009-03-28 19:07:53 +00001515 "Select a Timeslot to configure")
1516{
1517 int ts_nr = atoi(argv[0]);
1518 struct gsm_bts_trx *trx = vty->index;
1519 struct gsm_bts_trx_ts *ts;
1520
1521 if (ts_nr >= TRX_NR_TS) {
1522 vty_out(vty, "%% A GSM TRX only has %u Timeslots per TRX%s",
1523 TRX_NR_TS, VTY_NEWLINE);
1524 return CMD_WARNING;
1525 }
1526
1527 ts = &trx->ts[ts_nr];
1528
1529 vty->index = ts;
1530 vty->node = TS_NODE;
1531
1532 return CMD_SUCCESS;
1533}
1534
Harald Weltea6fd58e2009-08-07 00:25:23 +02001535DEFUN(cfg_ts_pchan,
1536 cfg_ts_pchan_cmd,
1537 "phys_chan_config PCHAN",
1538 "Physical Channel configuration (TCH/SDCCH/...)")
1539{
1540 struct gsm_bts_trx_ts *ts = vty->index;
1541 int pchanc;
1542
1543 pchanc = gsm_pchan_parse(argv[0]);
1544 if (pchanc < 0)
1545 return CMD_WARNING;
1546
1547 ts->pchan = pchanc;
1548
1549 return CMD_SUCCESS;
1550}
1551
1552DEFUN(cfg_ts_e1_subslot,
1553 cfg_ts_e1_subslot_cmd,
Harald Welte42581822009-08-08 16:12:58 +02001554 "e1 line E1_LINE timeslot <1-31> sub-slot (0|1|2|3|full)",
Harald Weltea6fd58e2009-08-07 00:25:23 +02001555 "E1 sub-slot connected to this on-air timeslot")
1556{
1557 struct gsm_bts_trx_ts *ts = vty->index;
1558
Harald Welte42581822009-08-08 16:12:58 +02001559 parse_e1_link(&ts->e1_link, argv[0], argv[1], argv[2]);
Harald Weltea6fd58e2009-08-07 00:25:23 +02001560
1561 return CMD_SUCCESS;
1562}
Harald Welte5258fc42009-03-28 19:07:53 +00001563
Harald Welte68628e82009-03-10 12:17:57 +00001564int bsc_vty_init(struct gsm_network *net)
1565{
1566 gsmnet = net;
1567
1568 cmd_init(1);
1569 vty_init();
1570
1571 install_element(VIEW_NODE, &show_net_cmd);
1572 install_element(VIEW_NODE, &show_bts_cmd);
1573 install_element(VIEW_NODE, &show_trx_cmd);
1574 install_element(VIEW_NODE, &show_ts_cmd);
1575 install_element(VIEW_NODE, &show_lchan_cmd);
Harald Welte1bc77352009-03-10 19:47:51 +00001576
1577 install_element(VIEW_NODE, &show_e1drv_cmd);
Harald Welte68628e82009-03-10 12:17:57 +00001578 install_element(VIEW_NODE, &show_e1line_cmd);
1579 install_element(VIEW_NODE, &show_e1ts_cmd);
1580
Harald Weltef5025b62009-03-28 16:55:11 +00001581 install_element(VIEW_NODE, &show_paging_cmd);
Harald Welte24ff6ee2009-12-22 00:41:05 +01001582 install_element(VIEW_NODE, &show_stats_cmd);
Harald Welte5258fc42009-03-28 19:07:53 +00001583
Harald Welte5013b2a2009-08-07 13:29:14 +02001584 install_element(CONFIG_NODE, &cfg_net_cmd);
1585 install_node(&net_node, config_write_net);
1586 install_default(GSMNET_NODE);
Harald Welte42581822009-08-08 16:12:58 +02001587 install_element(GSMNET_NODE, &cfg_net_ncc_cmd);
Harald Welte5013b2a2009-08-07 13:29:14 +02001588 install_element(GSMNET_NODE, &cfg_net_mnc_cmd);
1589 install_element(GSMNET_NODE, &cfg_net_name_short_cmd);
1590 install_element(GSMNET_NODE, &cfg_net_name_long_cmd);
Harald Welte (local)69de3972009-08-12 14:42:23 +02001591 install_element(GSMNET_NODE, &cfg_net_auth_policy_cmd);
Harald Welte1085c092009-11-18 20:33:19 +01001592 install_element(GSMNET_NODE, &cfg_net_reject_cause_cmd);
Harald Welte4381cfe2009-08-30 15:47:06 +09001593 install_element(GSMNET_NODE, &cfg_net_encryption_cmd);
Holger Hans Peter Freytherf7d752f2009-11-16 17:12:38 +01001594 install_element(GSMNET_NODE, &cfg_net_neci_cmd);
Harald Welteeab84a12009-12-13 10:53:12 +01001595 install_element(GSMNET_NODE, &cfg_net_rrlp_mode_cmd);
Harald Welte3d23db42009-12-14 17:49:15 +01001596 install_element(GSMNET_NODE, &cfg_net_mm_info_cmd);
Harald Weltebc814502009-12-19 21:41:52 +01001597 install_element(GSMNET_NODE, &cfg_net_handover_cmd);
Harald Welteb720bd32009-12-21 16:51:50 +01001598 install_element(GSMNET_NODE, &cfg_net_ho_win_rxlev_avg_cmd);
1599 install_element(GSMNET_NODE, &cfg_net_ho_win_rxqual_avg_cmd);
1600 install_element(GSMNET_NODE, &cfg_net_ho_win_rxlev_avg_neigh_cmd);
1601 install_element(GSMNET_NODE, &cfg_net_ho_pwr_interval_cmd);
1602 install_element(GSMNET_NODE, &cfg_net_ho_pwr_hysteresis_cmd);
1603 install_element(GSMNET_NODE, &cfg_net_ho_max_distance_cmd);
Holger Hans Peter Freytherc4d88ad2009-11-21 21:18:38 +01001604 install_element(GSMNET_NODE, &cfg_net_T3101_cmd);
Holger Hans Peter Freyther23975e72009-11-21 21:42:26 +01001605 install_element(GSMNET_NODE, &cfg_net_T3103_cmd);
1606 install_element(GSMNET_NODE, &cfg_net_T3105_cmd);
1607 install_element(GSMNET_NODE, &cfg_net_T3107_cmd);
1608 install_element(GSMNET_NODE, &cfg_net_T3109_cmd);
1609 install_element(GSMNET_NODE, &cfg_net_T3111_cmd);
1610 install_element(GSMNET_NODE, &cfg_net_T3113_cmd);
1611 install_element(GSMNET_NODE, &cfg_net_T3115_cmd);
1612 install_element(GSMNET_NODE, &cfg_net_T3117_cmd);
1613 install_element(GSMNET_NODE, &cfg_net_T3119_cmd);
1614 install_element(GSMNET_NODE, &cfg_net_T3141_cmd);
Harald Welte5013b2a2009-08-07 13:29:14 +02001615
1616 install_element(GSMNET_NODE, &cfg_bts_cmd);
Harald Welte67ce0732009-08-06 19:06:46 +02001617 install_node(&bts_node, config_write_bts);
Harald Welte68628e82009-03-10 12:17:57 +00001618 install_default(BTS_NODE);
Harald Welte5258fc42009-03-28 19:07:53 +00001619 install_element(BTS_NODE, &cfg_bts_type_cmd);
Harald Weltefcd24452009-06-20 18:15:19 +02001620 install_element(BTS_NODE, &cfg_bts_band_cmd);
Holger Hans Peter Freytherc4a49e32009-08-21 14:44:12 +02001621 install_element(BTS_NODE, &cfg_bts_ci_cmd);
Harald Welte5258fc42009-03-28 19:07:53 +00001622 install_element(BTS_NODE, &cfg_bts_lac_cmd);
1623 install_element(BTS_NODE, &cfg_bts_tsc_cmd);
Harald Welte42581822009-08-08 16:12:58 +02001624 install_element(BTS_NODE, &cfg_bts_bsic_cmd);
Harald Welte4cc34222009-05-01 15:12:31 +00001625 install_element(BTS_NODE, &cfg_bts_unit_id_cmd);
Harald Welte8175e952009-10-20 00:22:00 +02001626 install_element(BTS_NODE, &cfg_bts_stream_id_cmd);
Harald Welte42581822009-08-08 16:12:58 +02001627 install_element(BTS_NODE, &cfg_bts_oml_e1_cmd);
1628 install_element(BTS_NODE, &cfg_bts_oml_e1_tei_cmd);
Harald Welte7a8fa412009-08-10 13:48:16 +02001629 install_element(BTS_NODE, &cfg_bts_challoc_cmd);
Sylvain Munaut4010f1e2009-12-22 13:43:26 +01001630 install_element(BTS_NODE, &cfg_bts_rach_tx_integer_cmd);
1631 install_element(BTS_NODE, &cfg_bts_rach_max_trans_cmd);
Harald Welte (local)5dececf2009-08-12 13:28:23 +02001632 install_element(BTS_NODE, &cfg_bts_cell_barred_cmd);
Harald Welte (local)0e451d02009-08-13 10:14:26 +02001633 install_element(BTS_NODE, &cfg_bts_ms_max_power_cmd);
Harald Welte (local)efc92312009-08-14 23:09:25 +02001634 install_element(BTS_NODE, &cfg_bts_per_loc_upd_cmd);
Harald Welte73225282009-12-12 18:17:25 +01001635 install_element(BTS_NODE, &cfg_bts_cell_resel_hyst_cmd);
1636 install_element(BTS_NODE, &cfg_bts_rxlev_acc_min_cmd);
Harald Welte7a8fa412009-08-10 13:48:16 +02001637
Harald Welte68628e82009-03-10 12:17:57 +00001638
Harald Welte5258fc42009-03-28 19:07:53 +00001639 install_element(BTS_NODE, &cfg_trx_cmd);
Harald Welte68628e82009-03-10 12:17:57 +00001640 install_node(&trx_node, dummy_config_write);
Harald Welte68628e82009-03-10 12:17:57 +00001641 install_default(TRX_NODE);
Harald Welte5258fc42009-03-28 19:07:53 +00001642 install_element(TRX_NODE, &cfg_trx_arfcn_cmd);
Harald Welte879dc972009-06-20 22:36:12 +02001643 install_element(TRX_NODE, &cfg_trx_max_power_red_cmd);
Harald Welte42581822009-08-08 16:12:58 +02001644 install_element(TRX_NODE, &cfg_trx_rsl_e1_cmd);
1645 install_element(TRX_NODE, &cfg_trx_rsl_e1_tei_cmd);
Holger Hans Peter Freyther2d501ea2009-11-11 11:54:24 +01001646 install_element(TRX_NODE, &cfg_trx_rf_locked_cmd);
Harald Welte68628e82009-03-10 12:17:57 +00001647
Harald Welte5258fc42009-03-28 19:07:53 +00001648 install_element(TRX_NODE, &cfg_ts_cmd);
Harald Welte68628e82009-03-10 12:17:57 +00001649 install_node(&ts_node, dummy_config_write);
Harald Welte68628e82009-03-10 12:17:57 +00001650 install_default(TS_NODE);
Harald Weltea6fd58e2009-08-07 00:25:23 +02001651 install_element(TS_NODE, &cfg_ts_pchan_cmd);
1652 install_element(TS_NODE, &cfg_ts_e1_subslot_cmd);
Harald Welte68628e82009-03-10 12:17:57 +00001653
Holger Hans Peter Freythercfa90d42009-08-10 10:17:50 +02001654 bsc_vty_init_extra(net);
Harald Welte40f82892009-05-23 17:31:39 +00001655
Harald Welte68628e82009-03-10 12:17:57 +00001656 return 0;
1657}