Patrick Welche <prlw1@cam.ac.uk>
[netbsd-mini2440.git] / usr.sbin / lmcconfig / lmcconfig.c
bloba2ef82ec0aecc399fc78e302e89a2b8516bc2569
1 /*-
2 * $NetBSD: lmcconfig.c,v 1.10 2006/05/25 00:16:48 christos Exp $
4 * First author: Michael Graff.
5 * Copyright (c) 1997-2000 Lan Media Corp.
6 * All rights reserved.
8 * Second author: Andrew Stanley-Jones.
9 * Copyright (c) 2000-2002 SBE Corp.
10 * All rights reserved.
12 * Third author: David Boggs.
13 * Copyright (c) 2002-2006 David Boggs.
14 * All rights reserved.
16 * BSD License:
18 * Redistribution and use in source and binary forms, with or without
19 * modification, are permitted provided that the following conditions
20 * are met:
21 * 1. Redistributions of source code must retain the above copyright
22 * notice, this list of conditions and the following disclaimer.
23 * 2. Redistributions in binary form must reproduce the above copyright
24 * notice, this list of conditions and the following disclaimer in the
25 * documentation and/or other materials provided with the distribution.
27 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
28 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
29 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
30 * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
31 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
32 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
33 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
34 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
35 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
36 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
37 * SUCH DAMAGE.
39 * GNU General Public License:
41 * This program is free software; you can redistribute it and/or modify it
42 * under the terms of the GNU General Public License as published by the Free
43 * Software Foundation; either version 2 of the License, or (at your option)
44 * any later version.
46 * This program is distributed in the hope that it will be useful, but WITHOUT
47 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
48 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
49 * more details.
51 * You should have received a copy of the GNU General Public License along with
52 * this program; if not, write to the Free Software Foundation, Inc., 59
53 * Temple Place - Suite 330, Boston, MA 02111-1307, USA.
55 * Description:
57 * This program configures the Unix/Linux device driver
58 * for LMC wide area network interface cards.
59 * A complete man page for this program exists.
60 * This is a total rewrite of the program 'lmcctl' by
61 * Michael Graff, Rob Braun and Andrew Stanley-Jones.
63 * If Netgraph is present (FreeBSD only):
64 * cc -o lmcconfig -l netgraph -D NETGRAPH lmcconfig.c
65 * If Netgraph is NOT present:
66 * cc -o lmcconfig lmcconfig.c
69 #include <errno.h>
70 #include <stdio.h>
71 #include <stdlib.h>
72 #include <string.h>
73 #include <time.h>
74 #include <unistd.h>
75 #if defined(NETGRAPH)
76 # include <netgraph.h>
77 #endif
78 #include <sys/cdefs.h>
79 #include <sys/ioctl.h>
80 #include <sys/param.h>
81 #include <sys/socket.h>
82 #include <sys/types.h>
83 #include <sys/time.h>
84 #include <net/if.h>
85 /* and finally... */
86 # include "if_lmc.h"
88 /* procedure prototypes */
90 void usage(void);
92 void call_driver(unsigned long, struct iohdr *);
94 u_int32_t read_pci_config(u_int8_t);
95 void write_pci_config(u_int8_t, u_int32_t);
96 u_int32_t read_csr(u_int8_t);
97 void write_csr(u_int8_t, u_int32_t);
98 u_int16_t read_srom(u_int8_t);
99 void write_srom(u_int8_t, u_int16_t);
100 u_int8_t read_bios_rom(u_int32_t);
101 void write_bios_rom(u_int32_t, u_int8_t);
102 u_int16_t read_mii(u_int8_t);
103 void write_mii(u_int8_t, u_int16_t);
104 u_int8_t read_framer(u_int16_t);
105 void write_framer(u_int16_t, u_int8_t);
107 void write_synth(struct synth);
108 void write_dac(u_int16_t);
110 void reset_xilinx(void);
111 void load_xilinx_from_rom(void);
112 void load_xilinx_from_file(char *, int);
114 void ioctl_snmp_send(u_int32_t);
115 void ioctl_snmp_loop(u_int32_t);
116 void ioctl_reset_cntrs(void);
117 void ioctl_read_config(void);
118 void ioctl_write_config(void);
119 void ioctl_read_status(void);
121 void print_card_name(void);
122 void print_card_type(void);
123 void print_status(void);
124 void print_tx_speed(void);
125 void print_debug(void);
126 void print_line_prot(void);
127 void print_crc_len(void);
128 void print_loop_back(int);
129 void print_tx_clk_src(void);
130 void print_format(void);
131 void print_dte_dce(void);
132 void print_synth_freq(void);
133 void synth_freq(unsigned long);
134 void print_cable_len(void);
135 void print_cable_type(void);
136 void print_time_slots(void);
137 void print_scrambler(void);
138 double vga_dbs(u_int8_t);
139 void print_rx_gain_max(void);
140 void print_tx_lbo(void);
141 void print_tx_pulse(int);
142 void print_ssi_sigs(void);
143 void print_hssi_sigs(void);
144 void print_events(void);
145 void print_summary(void);
147 const char *print_t3_bop(int);
148 void print_t3_snmp(void);
149 void print_t3_dsu(void);
150 void t3_cmd(int, char **);
152 const char *print_t1_bop(int);
153 void print_t1_test_pattern(int);
154 void print_t1_far_report(int);
155 void print_t1_snmp(void);
156 void print_t1_dsu(void);
157 void t1_cmd(int, char **);
159 unsigned char read_hex(FILE *);
160 void load_xilinx(char *);
162 u_int32_t crc32(u_int8_t *, int);
163 u_int8_t crc8(u_int16_t *, int);
165 void main_cmd(int, char **);
166 /* int main(int, char **); */
168 /* program global variables */
170 char * progname; /* name of this program */
171 const char * ifname; /* interface name */
172 int fdcs; /* ifnet File Desc or ng Ctl Socket */
173 struct status status; /* card status (read only) */
174 struct config config; /* card configuration (read/write) */
175 int netgraph = 0; /* non-zero if netgraph present */
176 int summary = 0; /* print summary at end */
177 int update = 0; /* update driver config */
178 int verbose = 0; /* verbose output */
179 unsigned int waittime = 0; /* time in seconds between status prints */
180 u_int8_t checksum; /* gate array ucode file checksum */
182 void usage()
184 fprintf(stderr, "Usage: %s interface [-abBcCdDeEfgGhiLmMpPsStTuUvVwxXyY?]\n", progname);
185 fprintf(stderr, "or\n");
186 fprintf(stderr, "Usage: %s interface -1 [-aABcdeEfFgiIlLpPstTuUvxX]\n", progname);
187 fprintf(stderr, "or\n");
188 fprintf(stderr, "Usage: %s interface -3 [-aABcdefFlLsSvV]\n\n", progname);
189 fprintf(stderr, "\tInterface is the interface name, e.g. '%s'\n", ifname);
190 #if defined(NETGRAPH)
191 fprintf(stderr, "\tIf interface name ends with ':' then use netgraph\n");
192 #endif
193 fprintf(stderr, "\t-1 following parameters apply to T1E1 cards\n");
194 fprintf(stderr, "\t-3 following parameters apply to T3 cards\n");
195 fprintf(stderr, "\t-a <number> Set Tx clock source, where:\n");
196 fprintf(stderr, "\t 1:modem Tx clk 2:xtal osc 3:modem Rx Clk 4:ext conn\n");
197 fprintf(stderr, "\t-b Read and print bios rom addrs 0-255\n");
198 fprintf(stderr, "\t-B Write bios rom with address pattern\n");
199 fprintf(stderr, "\t-c Set 16-bit CRC (default)\n");
200 fprintf(stderr, "\t-C Set 32-bit CRC\n");
201 fprintf(stderr, "\t-d Clear driver DEBUG flag\n");
202 fprintf(stderr, "\t-D Set driver DEBUG flag (more log msgs)\n");
203 fprintf(stderr, "\t-e Set DTE mode (default)\n");
204 fprintf(stderr, "\t-E Set DCE mode\n");
205 fprintf(stderr, "\t-f <number> Set synth osc freq in bits/sec\n");
206 fprintf(stderr, "\t-g Load gate array from ROM\n");
207 fprintf(stderr, "\t-G <filename> Load gate array from file\n");
208 fprintf(stderr, "\t-h Help: this usage message\n");
209 fprintf(stderr, "\t-i Interface name (eg, lmc0)\n");
210 fprintf(stderr, "\t-L <number> Set loopback, where:\n");
211 fprintf(stderr, "\t 1:none 2:payload 3:line 4:other 5: inward\n");
212 fprintf(stderr, "\t 6:dual 16:Tulip 17:pins 18:LA/LL 19:LB/RL\n");
213 fprintf(stderr, "\t-m Read and print MII regs\n");
214 fprintf(stderr, "\t-M <addr> <data> Write MII reg\n");
215 fprintf(stderr, "\t-p Read and print PCI config regs\n");
216 fprintf(stderr, "\t-P <addr> <data> Write PCI config reg\n");
217 fprintf(stderr, "\t-s Read and print Tulip SROM\n");
218 fprintf(stderr, "\t-S <number> Initialize Tulip SROM\n");
219 fprintf(stderr, "\t-t Read and print Tulip Control/Status regs\n");
220 fprintf(stderr, "\t-T <addr> <data> Write Tulip Control/status reg\n");
221 fprintf(stderr, "\t-u Reset event counters\n");
222 fprintf(stderr, "\t-U Reset gate array\n");
223 fprintf(stderr, "\t-v Set verbose printout mode\n");
224 fprintf(stderr, "\t-V Print card configuration\n");
225 fprintf(stderr, "\t-w <number> Seconds between status prints\n");
226 fprintf(stderr, "\t-x <number> Set line protocol where:\n");
227 fprintf(stderr, "\t 1:RAW-IP 2:PPP 3:C-HDLC 4:FRM-RLY 5:RAW-ETH\n");
228 fprintf(stderr, "\t-X <number> Set line package where:\n");
229 fprintf(stderr, "\t 1:RAW-IP 2:SPPP 3:P2P 4:GEN-HDLC 5:SYNC-PPP\n");
230 fprintf(stderr, "\t-y Disable SPPP keep-alive packets\n");
231 fprintf(stderr, "\t-Y Enable SPPP keep-alive packets\n");
233 fprintf(stderr, "The -1 switch precedes T1/E1 commands.\n");
234 fprintf(stderr, "\t-a <y|b|a> Stop sending Yellow|Blue|AIS signal\n");
235 fprintf(stderr, "\t-A <y|b|a> Start sending Yellow|Blue}AIS signal\n");
236 fprintf(stderr, "\t-B <number> Send BOP msg 25 times\n");
237 fprintf(stderr, "\t-c <number> Set cable length in meters\n");
238 fprintf(stderr, "\t-d Print status of T1 DSU/CSU\n");
239 fprintf(stderr, "\t-e <number> Set framing format, where:\n");
240 fprintf(stderr, "\t 27:T1-ESF 9:T1-SF 0:E1-FAS 8:E1-FAS+CRC\n");
241 fprintf(stderr, "\t 16:E1-FAS+CAS 24:E1-FAS+CRC+CAS 32:E1-NO-FRAMING\n");
242 fprintf(stderr, "\t-E <32-bit hex number> 1 activates a channel and 0 deactivates it.\n");
243 fprintf(stderr, "\t Use this to config a link in fractional T1/E1 mode\n");
244 fprintf(stderr, "\t-f Read and print Framer/LIU registers\n");
245 fprintf(stderr, "\t-F <addr> <data> Write Framer/LIU register\n");
246 fprintf(stderr, "\t-g <number> Set receiver gain, where:\n");
247 fprintf(stderr, "\t 0:short range 1:medium range\n");
248 fprintf(stderr, "\t 2:long range 3:extended range\n");
249 fprintf(stderr, "\t 4:auto-set based on cable length\n");
250 fprintf(stderr, "\t-i Send 'CSU Loop Down' inband msg\n");
251 fprintf(stderr, "\t-I Send 'CSU Loop Up' inband msg\n");
252 fprintf(stderr, "\t-l Send 'Line Loop Down' BOP msg\n");
253 fprintf(stderr, "\t-L Send 'Line Loop Up' BOP msg\n");
254 fprintf(stderr, "\t-p Send 'Payload Loop Down' BOP msg\n");
255 fprintf(stderr, "\t-P Send 'Payload Loop Up' BOP msg\n");
256 fprintf(stderr, "\t-s Print status of T1 DSU/CSU\n");
257 fprintf(stderr, "\t-t Stop sending test pattern\n");
258 fprintf(stderr, "\t-T <number> Start sending test pattern, where:\n");
259 fprintf(stderr, "\t 0:unframed 2^11 1:unframed 2^15\n");
260 fprintf(stderr, "\t 2:unframed 2^20 3:unframed 2^23\n");
261 fprintf(stderr, "\t 4:unframed 2^11 w/ZS 5:unframed 2^15 w/ZS\n");
262 fprintf(stderr, "\t 6:unframed QRSS 7:unframed 2^23 w/ZS\n");
263 fprintf(stderr, "\t 8: framed 2^11 9: framed 2^15\n");
264 fprintf(stderr, "\t 10: framed 2^20 11: framed 2^23\n");
265 fprintf(stderr, "\t 12: framed 2^11 w/ZS 13: framed 2^15 w/ZS\n");
266 fprintf(stderr, "\t 14: framed QRSS 15: framed 2^23 w/ZS\n");
267 fprintf(stderr, "\t-u <number> Set transmitter pulse shape, where:\n");
268 fprintf(stderr, "\t 0:T1-DSX 0-40m 1:T1-DSX 40-80m\n");
269 fprintf(stderr, "\t 2:T1-DSX 80-120m 3:T1-DSX 120-160m\n");
270 fprintf(stderr, "\t 4:T1-DSX 160-200m 5:E1-G.703 75ohm coax\n");
271 fprintf(stderr, "\t 6:E1-G.703 120ohm TP 7:T1-CSU Long range\n");
272 fprintf(stderr, "\t 8:auto-set based on cable length (T1 only)\n");
273 fprintf(stderr, "\t-U <number> Set line build out where:\n");
274 fprintf(stderr, "\t 0:0dB 1:7.5dB 2:15dB 3:22.5dB\n");
275 fprintf(stderr, "\t 4:auto-set based on cable length\n");
276 fprintf(stderr, "\t-x Disable Transmitter outputs\n");
277 fprintf(stderr, "\t-X Enable Transmitter outputs\n");
279 fprintf(stderr, "The -3 switch precedes T3 commands.\n");
280 fprintf(stderr, "\t-a <y|b|a|i> Stop sending Yellow|Blue|AIS|Idle signal\n");
281 fprintf(stderr, "\t-A <y|b|a|i> Start sending Yellow|Blue|AIS|Idle signal\n");
282 fprintf(stderr, "\t-B <bopcode> Send BOP msg 10 times\n");
283 fprintf(stderr, "\t-c <number> Set cable length in meters\n");
284 fprintf(stderr, "\t-d Print status of T3 DSU/CSU\n");
285 fprintf(stderr, "\t-e <number> Set T3 frame format, where:\n");
286 fprintf(stderr, "\t 100:C-Bit Parity 101:M13\n");
287 fprintf(stderr, "\t-f Read and print Framer registers\n");
288 fprintf(stderr, "\t-F <addr> <data> Write Framer register\n");
289 fprintf(stderr, "\t-l Send 'Line Loop Down' BOP msg\n");
290 fprintf(stderr, "\t-L Send 'Line Loop Up' BOP msg\n");
291 fprintf(stderr, "\t-s Print status of T3 DSU/CSU\n");
292 fprintf(stderr, "\t-S <number> Set DS3 scrambler mode, where:\n");
293 fprintf(stderr, "\t 1:OFF 2:DigitalLink|Kentrox 3:Larse\n");
294 fprintf(stderr, "\t-V <number> Write to T3 VCXO freq control DAC\n");
297 void call_driver(unsigned long cmd, struct iohdr *iohdr)
299 strncpy(iohdr->ifname, ifname, sizeof(iohdr->ifname));
300 iohdr->cookie = NGM_LMC_COOKIE;
301 iohdr->iohdr = iohdr;
303 /* Exchange data with a running device driver. */
304 #if defined(NETGRAPH)
305 if (netgraph)
307 NgSendMsg(fdcs, ifname, NGM_LMC_COOKIE, cmd, iohdr, IOCPARM_LEN(cmd));
308 if (cmd & IOC_OUT)
310 int replen = sizeof(struct ng_mesg) + IOCPARM_LEN(cmd);
311 char rep[replen]; /* storage for the reply */
312 struct ng_mesg *reply = (struct ng_mesg *)rep;
313 int rl = NgRecvMsg(fdcs, reply, replen, NULL);
314 if (rl == replen)
315 bcopy(&reply->data, iohdr, IOCPARM_LEN(cmd));
316 else
318 fprintf(stderr, "%s: NgRecvMsg returned %d bytes, expected %d\n",
319 progname, rl, replen);
320 exit(1);
324 else
325 #endif
327 if (ioctl(fdcs, cmd, (caddr_t)iohdr) < 0)
329 fprintf(stderr, "%s: ioctl() returned error code %d: %s\n",
330 progname, errno, strerror(errno));
331 exit(1);
335 if (iohdr->cookie != NGM_LMC_COOKIE)
337 fprintf(stderr, "%s: cookie is 0x%08X; expected 0x%08X\n",
338 progname, iohdr->cookie, NGM_LMC_COOKIE);
339 fprintf(stderr, "%s: recompile this program!\n", progname);
340 exit(1);
344 u_int32_t read_pci_config(u_int8_t addr)
346 struct ioctl ioc;
348 ioc.iohdr.direction = DIR_IOWR;
349 ioc.iohdr.length = sizeof(struct ioctl);
350 ioc.cmd = IOCTL_RW_PCI;
351 ioc.address = addr;
353 call_driver(LMCIOCREAD, &ioc.iohdr);
355 return ioc.data;
358 void write_pci_config(u_int8_t addr, u_int32_t data)
360 struct ioctl ioc;
362 ioc.iohdr.direction = DIR_IOW;
363 ioc.iohdr.length = sizeof(struct ioctl);
364 ioc.cmd = IOCTL_RW_PCI;
365 ioc.address = addr;
366 ioc.data = data;
368 call_driver(LMCIOCWRITE, &ioc.iohdr);
371 u_int32_t read_csr(u_int8_t addr)
373 struct ioctl ioc;
375 ioc.iohdr.direction = DIR_IOWR;
376 ioc.iohdr.length = sizeof(struct ioctl);
377 ioc.cmd = IOCTL_RW_CSR;
378 ioc.address = addr;
380 call_driver(LMCIOCREAD, &ioc.iohdr);
382 return ioc.data;
385 void write_csr(u_int8_t addr, u_int32_t data)
387 struct ioctl ioc;
389 ioc.iohdr.direction = DIR_IOW;
390 ioc.iohdr.length = sizeof(struct ioctl);
391 ioc.cmd = IOCTL_RW_CSR;
392 ioc.address = addr;
393 ioc.data = data;
395 call_driver(LMCIOCWRITE, &ioc.iohdr);
398 u_int16_t read_srom(u_int8_t addr)
400 struct ioctl ioc;
402 ioc.iohdr.direction = DIR_IOWR;
403 ioc.iohdr.length = sizeof(struct ioctl);
404 ioc.cmd = IOCTL_RW_SROM;
405 ioc.address = addr;
407 call_driver(LMCIOCREAD, &ioc.iohdr);
409 return ioc.data;
412 void write_srom(u_int8_t addr, u_int16_t data)
414 struct ioctl ioc;
416 ioc.iohdr.direction = DIR_IOW;
417 ioc.iohdr.length = sizeof(struct ioctl);
418 ioc.cmd = IOCTL_RW_SROM;
419 ioc.address = addr;
420 ioc.data = data;
422 call_driver(LMCIOCWRITE, &ioc.iohdr);
425 u_int8_t read_bios_rom(u_int32_t addr)
427 struct ioctl ioc;
429 ioc.iohdr.direction = DIR_IOWR;
430 ioc.iohdr.length = sizeof(struct ioctl);
431 ioc.cmd = IOCTL_RW_BIOS;
432 ioc.address = addr;
434 call_driver(LMCIOCREAD, &ioc.iohdr);
436 return ioc.data;
439 void write_bios_rom(u_int32_t addr, u_int8_t data)
441 struct ioctl ioc;
443 ioc.iohdr.direction = DIR_IOW;
444 ioc.iohdr.length = sizeof(struct ioctl);
445 ioc.cmd = IOCTL_RW_BIOS;
446 ioc.address = addr;
447 ioc.data = data;
449 call_driver(LMCIOCWRITE, &ioc.iohdr);
452 u_int16_t read_mii(u_int8_t addr)
454 struct ioctl ioc;
456 ioc.iohdr.direction = DIR_IOWR;
457 ioc.iohdr.length = sizeof(struct ioctl);
458 ioc.cmd = IOCTL_RW_MII;
459 ioc.address = addr;
461 call_driver(LMCIOCREAD, &ioc.iohdr);
463 return ioc.data;
466 void write_mii(u_int8_t addr, u_int16_t data)
468 struct ioctl ioc;
470 ioc.iohdr.direction = DIR_IOW;
471 ioc.iohdr.length = sizeof(struct ioctl);
472 ioc.cmd = IOCTL_RW_MII;
473 ioc.address = addr;
474 ioc.data = data;
476 call_driver(LMCIOCWRITE, &ioc.iohdr);
479 u_int8_t read_framer(u_int16_t addr)
481 struct ioctl ioc;
483 ioc.iohdr.direction = DIR_IOWR;
484 ioc.iohdr.length = sizeof(struct ioctl);
485 ioc.cmd = IOCTL_RW_FRAME;
486 ioc.address = addr;
488 call_driver(LMCIOCREAD, &ioc.iohdr);
490 return ioc.data;
493 void write_framer(u_int16_t addr, u_int8_t data)
495 struct ioctl ioc;
497 ioc.iohdr.direction = DIR_IOW;
498 ioc.iohdr.length = sizeof(struct ioctl);
499 ioc.cmd = IOCTL_RW_FRAME;
500 ioc.address = addr;
501 ioc.data = data;
503 call_driver(LMCIOCWRITE, &ioc.iohdr);
506 void write_synth(struct synth synth)
508 struct ioctl ioc;
510 ioc.iohdr.direction = DIR_IOW;
511 ioc.iohdr.length = sizeof(struct ioctl);
512 ioc.cmd = IOCTL_WO_SYNTH;
513 bcopy(&synth, &ioc.data, sizeof(synth));
515 call_driver(LMCIOCWRITE, &ioc.iohdr);
518 void write_dac(u_int16_t data)
520 struct ioctl ioc;
522 ioc.iohdr.direction = DIR_IOW;
523 ioc.iohdr.length = sizeof(struct ioctl);
524 ioc.cmd = IOCTL_WO_DAC;
525 ioc.data = data;
527 call_driver(LMCIOCWRITE, &ioc.iohdr);
530 void reset_xilinx()
532 struct ioctl ioc;
534 ioc.iohdr.direction = DIR_IOWR;
535 ioc.iohdr.length = sizeof(struct ioctl);
536 ioc.cmd = IOCTL_XILINX_RESET;
538 call_driver(LMCIOCTL, &ioc.iohdr);
541 void load_xilinx_from_rom()
543 struct ioctl ioc;
545 ioc.iohdr.direction = DIR_IOWR;
546 ioc.iohdr.length = sizeof(struct ioctl);
547 ioc.cmd = IOCTL_XILINX_ROM;
549 call_driver(LMCIOCTL, &ioc.iohdr);
552 void load_xilinx_from_file(char *ucode, int len)
554 struct ioctl ioc;
556 ioc.iohdr.direction = DIR_IOWR;
557 ioc.iohdr.length = sizeof(struct ioctl);
558 ioc.cmd = IOCTL_XILINX_FILE;
559 ioc.data = len;
560 ioc.ucode = ucode;
562 call_driver(LMCIOCTL, &ioc.iohdr);
565 void ioctl_snmp_send(u_int32_t sendval)
567 struct ioctl ioc;
569 ioc.iohdr.direction = DIR_IOWR;
570 ioc.iohdr.length = sizeof(struct ioctl);
571 ioc.cmd = IOCTL_SNMP_SEND;
572 ioc.data = sendval;
574 call_driver(LMCIOCTL, &ioc.iohdr);
577 void ioctl_snmp_loop(u_int32_t loop)
579 struct ioctl ioc;
581 ioc.iohdr.direction = DIR_IOWR;
582 ioc.iohdr.length = sizeof(struct ioctl);
583 ioc.cmd = IOCTL_SNMP_LOOP;
584 ioc.data = loop;
586 call_driver(LMCIOCTL, &ioc.iohdr);
589 void ioctl_reset_cntrs()
591 struct ioctl ioc;
593 ioc.iohdr.direction = DIR_IOWR;
594 ioc.iohdr.length = sizeof(struct ioctl);
595 ioc.cmd = IOCTL_RESET_CNTRS;
597 call_driver(LMCIOCTL, &ioc.iohdr);
600 void ioctl_read_config()
602 config.iohdr.direction = DIR_IOWR;
603 config.iohdr.length = sizeof(struct config);
605 call_driver(LMCIOCGCFG, &config.iohdr);
608 void ioctl_write_config()
610 config.iohdr.direction = DIR_IOW;
611 config.iohdr.length = sizeof(struct config);
613 call_driver(LMCIOCSCFG, &config.iohdr);
616 void ioctl_read_status()
618 status.iohdr.direction = DIR_IOWR;
619 status.iohdr.length = sizeof(struct status);
621 call_driver(LMCIOCGSTAT, &status.iohdr);
624 void print_card_name()
626 printf("Card name:\t\t%s\n", ifname);
629 void print_card_type()
631 printf("Card type:\t\t");
632 switch(status.card_type)
634 case CSID_LMC_HSSI:
635 printf("HSSI (lmc5200)\n");
636 break;
637 case CSID_LMC_T3:
638 printf("T3 (lmc5245)\n");
639 break;
640 case CSID_LMC_SSI:
641 printf("SSI (lmc1000)\n");
642 break;
643 case CSID_LMC_T1E1:
644 printf("T1E1 (lmc1200)\n");
645 break;
646 case CSID_LMC_HSSIc:
647 printf("HSSI (lmc5200C)\n");
648 break;
649 default:
650 printf("Unknown card_type: %d\n", status.card_type);
651 break;
655 void print_status()
657 const char *status_string;
659 if (status.link_state == STATE_UP)
660 status_string = "Up";
661 else if (status.link_state == STATE_DOWN)
662 status_string = "Down";
663 else if (status.link_state == STATE_TEST)
664 status_string = "Test";
665 else
666 status_string = "Unknown";
667 printf("Link status:\t\t%s\n", status_string);
670 void print_tx_speed()
672 printf("Tx Speed:\t\t%u\n", status.tx_speed);
675 void print_debug()
677 if (config.debug != 0)
678 printf("Debug:\t\t\t%s\n", "On");
681 void print_line_prot()
683 const char *on = "On", *off = "Off";
685 printf("Line Prot/Pkg:\t\t");
686 switch (status.proto)
688 case 0:
689 printf("NotSet/");
690 break;
691 case PROTO_IP_HDLC:
692 printf("IP-in-HDLC/");
693 break;
694 case PROTO_PPP:
695 printf("PPP/");
696 break;
697 case PROTO_C_HDLC:
698 printf("Cisco-HDLC/");
699 break;
700 case PROTO_FRM_RLY:
701 printf("Frame-Relay/");
702 break;
703 case PROTO_ETH_HDLC:
704 printf("Ether-in-HDLC/");
705 break;
706 case PROTO_X25:
707 printf("X25+LAPB/");
708 break;
709 default:
710 printf("Unknown proto: %d/", status.proto);
711 break;
714 switch (status.stack)
716 case 0:
717 printf("NotSet\n");
718 break;
719 case STACK_RAWIP:
720 printf("Driver\n");
721 break;
722 case STACK_SPPP:
723 printf("SPPP\n");
724 break;
725 case STACK_P2P:
726 printf("P2P\n");
727 break;
728 case STACK_GEN_HDLC:
729 printf("GenHDLC\n");
730 break;
731 case STACK_SYNC_PPP:
732 printf("SyncPPP\n");
733 break;
734 case STACK_NETGRAPH:
735 printf("Netgraph\n");
736 break;
737 default:
738 printf("Unknown stack: %d\n", status.stack);
739 break;
742 if ((status.stack == STACK_SPPP) ||
743 (status.stack == STACK_SYNC_PPP) ||
744 ((status.stack == STACK_GEN_HDLC) && (status.proto == PROTO_PPP)))
745 printf("Keep-alive pkts:\t%s\n", status.keep_alive ? on : off);
748 void print_crc_len()
750 printf("CRC length:\t\t");
751 if (config.crc_len == CFG_CRC_0)
752 printf("no CRC\n");
753 else if (config.crc_len == CFG_CRC_16)
754 printf("16 bits\n");
755 else if (config.crc_len == CFG_CRC_32)
756 printf("32 bits\n");
757 else
758 printf("bad crc_len: %d\n", config.crc_len);
761 void print_loop_back(int skip_none)
763 if ((config.loop_back == CFG_LOOP_NONE) && skip_none)
764 return;
766 printf("Loopback:\t\t");
767 switch (config.loop_back)
769 case CFG_LOOP_NONE:
770 printf("None\n");
771 break;
772 case CFG_LOOP_PAYLOAD:
773 printf("Outward thru framer (payload loop)\n");
774 break;
775 case CFG_LOOP_LINE:
776 printf("Outward thru line interface (line loop)\n");
777 break;
778 case CFG_LOOP_OTHER:
779 printf("Inward thru line interface\n");
780 break;
781 case CFG_LOOP_INWARD:
782 printf("Inward thru framer\n");
783 break;
784 case CFG_LOOP_DUAL:
785 printf("Inward & outward (dual loop)\n");
786 break;
787 case CFG_LOOP_TULIP:
788 printf("Inward thru Tulip chip\n");
789 break;
790 case CFG_LOOP_PINS:
791 printf("Inward thru drvrs/rcvrs\n");
792 break;
793 case CFG_LOOP_LL:
794 printf("LA/LL asserted\n");
795 break;
796 case CFG_LOOP_RL:
797 printf("LB/RL asserted\n");
798 break;
799 default:
800 printf("Unknown loop_back: %d\n", config.loop_back);
801 break;
805 void print_tx_clk_src()
807 printf("Tx Clk src:\t\t");
808 switch (config.tx_clk_src)
810 case CFG_CLKMUX_ST:
811 printf("Modem Tx Clk\n");
812 break;
813 case CFG_CLKMUX_INT:
814 printf("Crystal osc\n");
815 break;
816 case CFG_CLKMUX_RT:
817 printf("Modem Rx Clk (loop timed)\n");
818 break;
819 case CFG_CLKMUX_EXT:
820 printf("External connector\n");
821 break;
822 default:
823 printf("Unknown tx_clk_src: %d\n", config.tx_clk_src);
824 break;
828 void print_format()
830 printf("Format-Frame/Code:\t");
831 switch (config.format)
833 case CFG_FORMAT_T1SF:
834 printf("T1-SF/AMI\n");
835 break;
836 case CFG_FORMAT_T1ESF:
837 printf("T1-ESF/B8ZS\n");
838 break;
839 case CFG_FORMAT_E1FAS:
840 printf("E1-FAS/HDB3\n");
841 break;
842 case CFG_FORMAT_E1FASCRC:
843 printf("E1-FAS+CRC/HDB3\n");
844 break;
845 case CFG_FORMAT_E1FASCAS:
846 printf("E1-FAS+CAS/HDB3\n");
847 break;
848 case CFG_FORMAT_E1FASCRCCAS:
849 printf("E1-FAS+CRC+CAS/HDB3\n");
850 break;
851 case CFG_FORMAT_E1NONE:
852 printf("E1-NOFRAMING/HDB3\n");
853 break;
854 case CFG_FORMAT_T3CPAR:
855 printf("T3-CParity/B3ZS\n");
856 break;
857 case CFG_FORMAT_T3M13:
858 printf("T3-M13/B3ZS\n");
859 break;
860 default:
861 printf("Unknown format: %d\n", config.format);
862 break;
866 void print_dte_dce()
868 printf("DTE or DCE:\t\t");
869 switch(config.dte_dce)
871 case CFG_DTE:
872 printf("DTE (receiving TxClk)\n");
873 break;
874 case CFG_DCE:
875 printf("DCE (driving TxClk)\n");
876 break;
877 default:
878 printf("Unknown dte_dce: %d\n", config.dte_dce);
879 break;
883 void print_synth_freq()
885 double Fref = 20e6;
886 double Fout, Fvco;
888 /* decode the synthesizer params */
889 Fvco = (Fref * (config.synth.n<<(3*config.synth.v)))/config.synth.m;
890 Fout = Fvco / (1<<(config.synth.x+config.synth.r+config.synth.prescale));
892 printf("Synth freq:\t\t%.0f\n", Fout);
895 void synth_freq(unsigned long target)
897 unsigned int n, m, v, x, r;
898 double Fout, Fvco, Ftarg;
899 double newdiff, olddiff;
900 double bestF=0.0, bestV=0.0;
901 unsigned prescale = (target < 50000) ? 9:4;
903 Ftarg = target<<prescale;
904 for (n=3; n<=127; n++)
905 for (m=3; m<=127; m++)
906 for (v=0; v<=1; v++)
907 for (x=0; x<=3; x++)
908 for (r=0; r<=3; r++)
910 Fvco = (SYNTH_FREF * (n<<(3*v)))/m;
911 if (Fvco < SYNTH_FMIN || Fvco > SYNTH_FMAX) continue;
912 Fout = Fvco / (1<<(x+r));
913 if (Fout >= Ftarg)
914 newdiff = Fout - Ftarg;
915 else
916 newdiff = Ftarg - Fout;
917 if (bestF >= Ftarg)
918 olddiff = bestF - Ftarg;
919 else
920 olddiff = Ftarg - bestF;
921 if ((newdiff < olddiff) ||
922 ((newdiff == olddiff) && (Fvco < bestV)))
924 config.synth.n = n;
925 config.synth.m = m;
926 config.synth.v = v;
927 config.synth.x = x;
928 config.synth.r = r;
929 config.synth.prescale = prescale;
930 bestF = Fout;
931 bestV = Fvco;
934 #if 0
935 printf("Fbest=%.0f, Ftarg=%u, Fout=%.0f\n", bestF>>prescale, target, bestF);
936 printf("N=%u, M=%u, V=%u, X=%u, R=%u\n", config.synth.n,
937 config.synth.m, config.synth.v, config.synth.x, config.synth.r);
938 #endif
941 void print_cable_len()
943 printf("Cable length:\t\t%d meters\n", config.cable_len);
946 void print_cable_type()
948 printf("Cable type:\t\t");
949 if (status.cable_type > 7)
950 printf("Unknown cable_type: %d\n", status.cable_type);
951 else
952 printf("%s\n", ssi_cables[status.cable_type]);
955 void print_time_slots()
957 printf("TimeSlot [31-0]:\t0x%08X\n", status.time_slots);
960 void print_scrambler()
962 printf("Scrambler:\t\t");
963 if (config.scrambler == CFG_SCRAM_OFF)
964 printf("off\n");
965 else if (config.scrambler == CFG_SCRAM_DL_KEN)
966 printf("DigLink/Kentrox: X^43+1\n");
967 else if (config.scrambler == CFG_SCRAM_LARS)
968 printf("Larse: X^20+X^17+1 w/28ZS\n");
969 else
970 printf("Unknown scrambler: %d\n", config.scrambler);
973 double vga_dbs(u_int8_t vga)
975 if (vga < 0x0F) return 0.0;
976 else if ((vga >= 0x0F) && (vga <= 0x1B)) return 0.0 + 0.77 * (vga - 0x0F);
977 else if ((vga >= 0x1C) && (vga <= 0x33)) return 10.0 + 1.25 * (vga - 0x1C);
978 else if ((vga >= 0x34) && (vga <= 0x39)) return 40.0 + 1.67 * (vga - 0x34);
979 else if ((vga >= 0x3A) && (vga <= 0x3F)) return 50.0 + 2.80 * (vga - 0x3A);
980 else /* if (vga > 0x3F) */ return 64.0;
983 void print_rx_gain_max()
985 if (config.rx_gain_max != CFG_GAIN_AUTO)
987 printf("Rx gain max:\t\t");
988 printf("up to %02.1f dB\n", vga_dbs(config.rx_gain_max));
992 void print_tx_lbo()
994 u_int8_t saved_lbo = config.tx_lbo;
996 printf("LBO = ");
997 if (config.tx_lbo == CFG_LBO_AUTO)
999 config.tx_lbo = read_framer(Bt8370_TLIU_CR) & 0x30;
1000 printf("auto-set to ");
1003 switch (config.tx_lbo)
1005 case CFG_LBO_0DB:
1006 printf("0 dB\n");
1007 break;
1008 case CFG_LBO_7DB:
1009 printf("7.5 dB\n");
1010 break;
1011 case CFG_LBO_15DB:
1012 printf("15 dB\n");
1013 break;
1014 case CFG_LBO_22DB:
1015 printf("22.5 dB\n");
1016 break;
1017 default:
1018 printf("Unknown tx_lbo: %d\n", config.tx_lbo);
1019 break;
1022 if (saved_lbo == CFG_LBO_AUTO)
1023 config.tx_lbo = saved_lbo;
1026 void print_tx_pulse(int skip_auto)
1028 u_int8_t saved_pulse = config.tx_pulse;
1030 if ((config.tx_pulse == CFG_PULSE_AUTO) && skip_auto)
1031 return;
1033 printf("Tx pulse shape:\t\t");
1034 if (config.tx_pulse == CFG_PULSE_AUTO)
1036 config.tx_pulse = read_framer(Bt8370_TLIU_CR) & 0x0E;
1037 printf("auto-set to ");
1040 switch (config.tx_pulse)
1042 case CFG_PULSE_T1DSX0:
1043 printf("T1-DSX: 0 to 40 meters\n");
1044 break;
1045 case CFG_PULSE_T1DSX1:
1046 printf("T1-DSX: 40 to 80 meters\n");
1047 break;
1048 case CFG_PULSE_T1DSX2:
1049 printf("T1-DSX: 80 to 120 meters\n");
1050 break;
1051 case CFG_PULSE_T1DSX3:
1052 printf("T1-DSX: 120 to 160 meters\n");
1053 break;
1054 case CFG_PULSE_T1DSX4:
1055 printf("T1-DSX: 160 to 200 meters\n");
1056 break;
1057 case CFG_PULSE_E1COAX:
1058 printf("E1: Twin Coax\n");
1059 break;
1060 case CFG_PULSE_E1TWIST:
1061 printf("E1: Twisted Pairs\n");
1062 break;
1063 case CFG_PULSE_T1CSU:
1064 printf("T1-CSU; ");
1065 print_tx_lbo();
1066 break;
1067 default:
1068 printf("Unknown tx_pulse: %d\n", config.tx_pulse);
1069 break;
1072 if (saved_pulse == CFG_PULSE_AUTO)
1073 config.tx_pulse = saved_pulse;
1076 void print_ssi_sigs()
1078 u_int32_t mii16 = status.snmp.ssi.sigs;
1079 const char *on = "On", *off = "Off";
1081 printf("Modem signals:\t\tDTR=%s DSR=%s RTS=%s CTS=%s\n",
1082 (mii16 & MII16_SSI_DTR) ? on : off,
1083 (mii16 & MII16_SSI_DSR) ? on : off,
1084 (mii16 & MII16_SSI_RTS) ? on : off,
1085 (mii16 & MII16_SSI_CTS) ? on : off);
1086 printf("Modem signals:\t\tDCD=%s RI=%s LL=%s RL=%s TM=%s\n",
1087 (mii16 & MII16_SSI_DCD) ? on : off,
1088 (mii16 & MII16_SSI_RI) ? on : off,
1089 (mii16 & MII16_SSI_LL) ? on : off,
1090 (mii16 & MII16_SSI_RL) ? on : off,
1091 (mii16 & MII16_SSI_TM) ? on : off);
1094 void print_hssi_sigs()
1096 u_int32_t mii16 = status.snmp.hssi.sigs;
1097 const char *on = "On", *off = "Off";
1099 printf("Modem signals:\t\tTA=%s CA=%s\n",
1100 (mii16 & MII16_HSSI_TA) ? on : off,
1101 (mii16 & MII16_HSSI_CA) ? on : off);
1102 printf("Modem signals:\t\tLA=%s LB=%s LC=%s TM=%s\n",
1103 (mii16 & MII16_HSSI_LA) ? on : off,
1104 (mii16 & MII16_HSSI_LB) ? on : off,
1105 (mii16 & MII16_HSSI_LC) ? on : off,
1106 (mii16 & MII16_HSSI_TM) ? on : off);
1109 void print_events()
1111 const char *timestr;
1112 struct timeval tv;
1113 time_t tv_sec;
1115 (void)gettimeofday(&tv, NULL);
1116 tv_sec = tv.tv_sec;
1117 timestr = ctime(&tv_sec);
1118 printf("Current time:\t\t%s", timestr);
1120 if (status.cntrs.reset_time.tv_sec < 1000)
1121 timestr = "Never\n";
1122 else
1124 tv_sec = status.cntrs.reset_time.tv_sec;
1125 timestr = ctime(&tv_sec);
1127 printf("Cntrs reset:\t\t%s", timestr);
1129 if (status.cntrs.ibytes) printf("Rx bytes:\t\t%llu\n", (unsigned long long)status.cntrs.ibytes);
1130 if (status.cntrs.obytes) printf("Tx bytes:\t\t%llu\n", (unsigned long long)status.cntrs.obytes);
1131 if (status.cntrs.ipackets) printf("Rx packets:\t\t%llu\n", (unsigned long long)status.cntrs.ipackets);
1132 if (status.cntrs.opackets) printf("Tx packets:\t\t%llu\n", (unsigned long long)status.cntrs.opackets);
1133 if (status.cntrs.ierrors) printf("Rx errors:\t\t%u\n", status.cntrs.ierrors);
1134 if (status.cntrs.oerrors) printf("Tx errors:\t\t%u\n", status.cntrs.oerrors);
1135 if (status.cntrs.idrops) printf("Rx drops:\t\t%u\n", status.cntrs.idrops);
1136 if (status.cntrs.missed) printf("Rx missed:\t\t%u\n", status.cntrs.missed);
1137 if (status.cntrs.odrops) printf("Tx drops:\t\t%u\n", status.cntrs.odrops);
1138 if (status.cntrs.fifo_over) printf("Rx fifo overruns:\t%u\n", status.cntrs.fifo_over);
1139 if (status.cntrs.overruns) printf("Rx overruns:\t\t%u\n", status.cntrs.overruns);
1140 if (status.cntrs.fifo_under) printf("Tx fifo underruns:\t%u\n", status.cntrs.fifo_under);
1141 if (status.cntrs.underruns) printf("Rx underruns:\t\t%u\n", status.cntrs.underruns);
1142 if (status.cntrs.fdl_pkts) printf("Rx FDL pkts:\t\t%u\n", status.cntrs.fdl_pkts);
1143 if (status.cntrs.crc_errs) printf("Rx CRC:\t\t\t%u\n", status.cntrs.crc_errs);
1144 if (status.cntrs.lcv_errs) printf("Rx line code:\t\t%u\n", status.cntrs.lcv_errs);
1145 if (status.cntrs.frm_errs) printf("Rx F-bits:\t\t%u\n", status.cntrs.frm_errs);
1146 if (status.cntrs.febe_errs) printf("Rx FEBE:\t\t%u\n", status.cntrs.febe_errs);
1147 if (status.cntrs.par_errs) printf("Rx P-parity:\t\t%u\n", status.cntrs.par_errs);
1148 if (status.cntrs.cpar_errs) printf("Rx C-parity:\t\t%u\n", status.cntrs.cpar_errs);
1149 if (status.cntrs.mfrm_errs) printf("Rx M-bits:\t\t%u\n", status.cntrs.mfrm_errs);
1150 if (config.debug)
1151 { /* These events are hard to explain and may worry users, */
1152 if (status.cntrs.rxbuf) printf("Rx no buffs:\t\t%u\n", status.cntrs.rxbuf);
1153 if (status.cntrs.txdma) printf("Tx no descs:\t\t%u\n", status.cntrs.txdma);
1154 if (status.cntrs.lck_watch) printf("Lock watch:\t\t%u\n", status.cntrs.lck_watch);
1155 if (status.cntrs.lck_intr) printf("Lock intr:\t\t%u\n", status.cntrs.lck_intr);
1156 if (status.cntrs.spare1) printf("Spare1:\t\t\t%u\n", status.cntrs.spare1);
1157 if (status.cntrs.spare2) printf("Spare2:\t\t\t%u\n", status.cntrs.spare2);
1158 if (status.cntrs.spare3) printf("Spare3:\t\t\t%u\n", status.cntrs.spare3);
1159 if (status.cntrs.spare4) printf("Spare4:\t\t\t%u\n", status.cntrs.spare4);
1163 void print_summary()
1165 switch(status.card_type)
1167 case CSID_LMC_HSSI:
1169 print_card_name();
1170 print_card_type();
1171 print_debug();
1172 print_status();
1173 print_tx_speed();
1174 print_line_prot();
1175 print_crc_len();
1176 print_loop_back(1);
1177 print_tx_clk_src();
1178 print_hssi_sigs();
1179 print_events();
1180 break;
1182 case CSID_LMC_T3:
1184 print_card_name();
1185 print_card_type();
1186 print_debug();
1187 print_status();
1188 print_tx_speed();
1189 print_line_prot();
1190 print_crc_len();
1191 print_loop_back(1);
1192 print_format();
1193 print_cable_len();
1194 print_scrambler();
1195 print_events();
1196 break;
1198 case CSID_LMC_SSI:
1200 print_card_name();
1201 print_card_type();
1202 print_debug();
1203 print_status();
1204 print_tx_speed();
1205 print_line_prot();
1206 print_crc_len();
1207 print_loop_back(1);
1208 print_dte_dce();
1209 print_synth_freq();
1210 print_cable_type();
1211 print_ssi_sigs();
1212 print_events();
1213 break;
1215 case CSID_LMC_T1E1:
1217 print_card_name();
1218 print_card_type();
1219 print_debug();
1220 print_status();
1221 print_tx_speed();
1222 print_line_prot();
1223 print_crc_len();
1224 print_loop_back(1);
1225 print_tx_clk_src();
1226 print_format();
1227 print_time_slots();
1228 print_cable_len();
1229 print_tx_pulse(1);
1230 print_rx_gain_max();
1231 print_events();
1232 break;
1234 case CSID_LMC_HSSIc:
1236 print_card_name();
1237 print_card_type();
1238 print_debug();
1239 print_status();
1240 print_line_prot();
1241 print_tx_speed();
1242 print_crc_len();
1243 print_loop_back(1);
1244 print_tx_clk_src();
1245 print_dte_dce();
1246 print_synth_freq();
1247 print_hssi_sigs();
1248 print_events();
1249 break;
1251 default:
1253 printf("%s: Unknown card type: %d\n", ifname, status.card_type);
1254 break;
1259 const char *print_t3_bop(int bop_code)
1261 switch(bop_code)
1263 case 0x00:
1264 return "far end LOF";
1265 case 0x0E:
1266 return "far end LOS";
1267 case 0x16:
1268 return "far end AIS";
1269 case 0x1A:
1270 return "far end IDL";
1271 case 0x07:
1272 return "Line Loopback activate";
1273 case 0x1C:
1274 return "Line Loopback deactivate";
1275 case 0x1B:
1276 return "Entire DS3 line";
1277 default:
1278 return "Unknown BOP code";
1282 void print_t3_snmp()
1284 printf("SNMP performance data:\n");
1285 printf(" LCV=%d", status.snmp.t3.lcv);
1286 printf(" LOS=%d", (status.snmp.t3.line & TLINE_LOS) ? 1 : 0);
1287 printf(" PCV=%d", status.snmp.t3.pcv);
1288 printf(" CCV=%d", status.snmp.t3.ccv);
1289 printf(" AIS=%d", (status.snmp.t3.line & TLINE_RX_AIS) ? 1 : 0);
1290 printf(" SEF=%d", (status.snmp.t3.line & T1LINE_SEF) ? 1 : 0);
1291 printf(" OOF=%d", (status.snmp.t3.line & TLINE_LOF) ? 1 : 0);
1292 printf(" FEBE=%d", status.snmp.t3.febe);
1293 printf(" RAI=%d", (status.snmp.t3.line & TLINE_RX_RAI) ? 1 : 0);
1294 printf("\n");
1297 void print_t3_dsu()
1299 const char *no = "No", *yes = "Yes";
1300 u_int16_t mii16 = read_mii(16);
1301 u_int8_t ctl1 = read_framer(T3CSR_CTL1);
1302 u_int8_t ctl8 = read_framer(T3CSR_CTL8);
1303 u_int8_t stat9 = read_framer(T3CSR_STAT9);
1304 u_int8_t ctl12 = read_framer(T3CSR_CTL12);
1305 u_int8_t stat16 = read_framer(T3CSR_STAT16);
1307 printf("Framing: \t\t%s\n", ctl1 & CTL1_M13MODE ? "M13" : "CPAR");
1308 print_tx_speed();
1309 if ((mii16 & MII16_DS3_SCRAM)==0)
1310 printf("Scrambler: \t\toff\n");
1311 else if (mii16 & MII16_DS3_POLY)
1312 printf("Scrambler: \t\tX^20+X^17+1\n");
1313 else
1314 printf("Scrambler: \t\tX^43+1\n");
1315 printf("Cable length \t\t%s\n", mii16 & MII16_DS3_ZERO ? "Short" : "Long");
1316 printf("Line loop: \t\t%s\n", mii16 & MII16_DS3_LNLBK ? yes : no);
1317 printf("Payload loop: \t\t%s\n", ctl12 & CTL12_RTPLOOP ? yes : no);
1318 printf("Frame loop: \t\t%s\n", ctl1 & CTL1_3LOOP ? yes : no);
1319 printf("Host loop: \t\t%s\n", mii16 & MII16_DS3_TRLBK ? yes : no);
1320 printf("Transmit RAI: \t\t%s\n", ctl1 & CTL1_XTX ? no : yes);
1321 printf("Receive RAI: \t\t%s\n", stat16 & STAT16_XERR ? yes : no);
1322 printf("Transmit AIS: \t\t%s\n", ctl1 & CTL1_TXAIS ? yes : no);
1323 printf("Receive AIS: \t\t%s\n", stat16 & STAT16_RAIS ? yes : no);
1324 printf("Transmit IDLE: \t\t%s\n", ctl1 & CTL1_TXIDL ? yes : no);
1325 printf("Receive IDLE: \t\t%s\n", stat16 & STAT16_RIDL ? yes : no);
1326 printf("Transmit BLUE: \t\t%s\n", ctl8 & CTL8_TBLU ? yes : no);
1327 printf("Receive BLUE: \t\t%s\n", stat9 & STAT9_RBLU ? yes : no);
1328 printf("Loss of Signal:\t\t%s\n", stat16 & STAT16_RLOS ? yes : no);
1329 printf("Loss of Frame: \t\t%s\n", stat16 & STAT16_ROOF ? yes : no);
1330 printf("Sev Err Frms: \t\t%s\n", stat16 & STAT16_SEF ? yes : no);
1331 printf("Code errors: \t\t%d\n", read_framer(T3CSR_CVLO) + (read_framer(T3CSR_CVHI)<<8));
1332 printf("C-Par errors: \t\t%d\n", read_framer(T3CSR_CERR));
1333 printf("P-Par errors: \t\t%d\n", read_framer(T3CSR_PERR));
1334 printf("F-Bit errors: \t\t%d\n", read_framer(T3CSR_FERR));
1335 printf("M-Bit errors: \t\t%d\n", read_framer(T3CSR_MERR));
1336 printf("FarEndBitErrs: \t\t%d\n", read_framer(T3CSR_FEBE));
1337 printf("Last Tx FEAC msg:\t0x%02X (%s)\n",
1338 read_framer(T3CSR_TX_FEAC) & 0x3F,
1339 print_t3_bop(read_framer(T3CSR_TX_FEAC) & 0x3F));
1340 printf("Last dbl FEAC msg:\t0x%02X (%s)\n",
1341 read_framer(T3CSR_DBL_FEAC) & 0x3F,
1342 print_t3_bop(read_framer(T3CSR_DBL_FEAC) & 0x3F));
1343 printf("Last Rx FEAC msg:\t0x%02X (%s)\n",
1344 read_framer(T3CSR_RX_FEAC) & 0x3F,
1345 print_t3_bop(read_framer(T3CSR_RX_FEAC) & 0x3F));
1346 print_t3_snmp();
1349 void t3_cmd(int argc, char **argv)
1351 int ch;
1352 const char *optstring = "a:A:B:c:de:fF:lLsS:V:";
1354 while ((ch = getopt(argc, argv, optstring)) != -1)
1356 switch (ch)
1358 case 'a': /* stop alarms */
1360 switch (optarg[0])
1362 case 'a': /* Stop sending AIS Signal */
1364 write_mii(16,
1365 read_mii(16) & ~MII16_DS3_FRAME);
1366 write_framer(T3CSR_CTL1,
1367 read_framer(T3CSR_CTL1) & ~CTL1_TXAIS);
1368 if (verbose) printf("Stop sending Alarm Indication Signal (AIS)\n");
1369 break;
1371 case 'b': /* Stop sending Blue signal */
1373 write_mii(16,
1374 read_mii(16) & ~MII16_DS3_FRAME);
1375 write_framer(T3CSR_CTL8,
1376 read_framer(T3CSR_CTL8) & ~CTL8_TBLU);
1377 if (verbose) printf("Stop sending Blue signal\n");
1378 break;
1380 case 'i': /* Stop sending IDLE signal */
1382 write_framer(T3CSR_CTL1,
1383 read_framer(T3CSR_CTL1) & ~CTL1_TXIDL);
1384 if (verbose) printf("Stop sending IDLE signal\n");
1385 break;
1387 case 'y': /* Stop sending Yellow alarm */
1389 write_framer(T3CSR_CTL1,
1390 read_framer(T3CSR_CTL1) | CTL1_XTX);
1391 if (verbose) printf("Stop sending Yellow alarm\n");
1392 break;
1394 default:
1395 printf("Unknown alarm: %c\n", optarg[0]);
1396 break;
1398 break;
1400 case 'A': /* start alarms */
1402 switch (optarg[0])
1404 case 'a': /* Start sending AIS Signal */
1406 write_mii(16,
1407 read_mii(16) | MII16_DS3_FRAME);
1408 write_framer(T3CSR_CTL1,
1409 read_framer(T3CSR_CTL1) | CTL1_TXAIS);
1410 if (verbose) printf("Sending AIS signal (framed 1010..)\n");
1411 break;
1413 case 'b': /* Start sending Blue signal */
1415 write_mii(16,
1416 read_mii(16) | MII16_DS3_FRAME);
1417 write_framer(T3CSR_CTL8,
1418 read_framer(T3CSR_CTL8) | CTL8_TBLU);
1419 if (verbose) printf("Sending Blue signal (unframed all 1s)\n");
1420 break;
1422 case 'i': /* Start sending IDLE signal */
1424 write_framer(T3CSR_CTL1,
1425 read_framer(T3CSR_CTL1) | CTL1_TXIDL);
1426 if (verbose) printf("Sending IDLE signal (framed 1100..)\n");
1427 break;
1429 case 'y': /* Start sending Yellow alarm */
1431 write_framer(T3CSR_CTL1,
1432 read_framer(T3CSR_CTL1) & ~CTL1_XTX);
1433 if (verbose) printf("Sending Yellow alarm (X-bits=0)\n");
1434 break;
1436 default:
1437 printf("Unknown alarm: %c\n", optarg[0]);
1438 break;
1440 break;
1442 case 'B': /* send BOP msg */
1444 u_int8_t bop = (u_int8_t)strtoul(optarg, NULL, 0);
1445 write_framer(T3CSR_TX_FEAC, 0xC0 + bop);
1446 if (verbose) printf("Sent '0x%02X' BOP msg 10 times\n", bop);
1447 break;
1449 case 'c': /* set cable length */
1451 config.cable_len = strtoul(optarg, NULL, 0);
1452 if (verbose) print_cable_len();
1453 update = 1;
1454 break;
1456 case 'd': /* DSU status */
1457 case 's': /* deprecated */
1459 print_t3_dsu();
1460 break;
1462 case 'e': /* set framimg format */
1464 config.format = strtoul(optarg, NULL, 0);
1465 if (verbose) print_format();
1466 update = 1;
1467 break;
1469 case 'f': /* read and print framer regs */
1471 int i;
1472 printf("TXC03401 regs:\n");
1473 printf(" 0 1 2 3 4 5 6 7");
1474 for (i=0; i<21; i++)
1476 if (i%8 == 0) printf("\n%02X: ", i);
1477 printf("%02X ", read_framer(i));
1479 printf("\n\n");
1480 break;
1482 case 'F': /* write framer reg */
1484 u_int32_t addr = strtoul(optarg, NULL, 0);
1485 u_int32_t data = strtoul(argv[optind++], NULL, 0);
1486 write_framer(addr, data);
1487 if (verbose)
1489 data = read_framer(addr);
1490 printf("Write framer register: addr = 0x%02X data = 0x%02X\n", addr, data);
1492 break;
1494 case 'l': /* send DS3 line loopback deactivate BOP cmd */
1496 ioctl_snmp_send(TSEND_RESET);
1497 if (verbose) printf("Sent 'DS3 Line Loopback deactivate' BOP cmd\n");
1498 break;
1500 case 'L': /* send DS3 line loopback activate BOP cmd */
1502 ioctl_snmp_send(TSEND_LINE);
1503 if (verbose) printf("Sent 'DS3 Line Loopback activate' BOP cmd\n");
1504 break;
1506 case 'S': /* set scrambler */
1508 config.scrambler = strtoul(optarg, NULL, 0);
1509 if (verbose) print_scrambler();
1510 update = 1;
1511 break;
1513 case 'V': /* set T3 freq control DAC */
1515 u_int32_t dac = strtoul(optarg, NULL, 0);
1516 write_dac(dac);
1517 if (verbose) printf("VCXO DAC value is %d\n", dac);
1518 break;
1520 default:
1522 printf("Unknown command char: %c\n", ch);
1523 exit(1);
1524 } /* case */
1525 } /* switch */
1526 } /* while */
1527 } /* proc */
1529 const char *print_t1_bop(int bop_code)
1531 switch(bop_code)
1533 case 0x00:
1534 return "Yellow Alarm (far end LOF)";
1535 case 0x07:
1536 return "Line Loop up";
1537 case 0x1C:
1538 return "Line Loop down";
1539 case 0x0A:
1540 return "Payload Loop up";
1541 case 0x19:
1542 return "Payload Loop down";
1543 case 0x09:
1544 return "Network Loop up";
1545 case 0x12:
1546 return "Network Loop down";
1547 default:
1548 return "Unknown BOP code";
1552 void print_t1_test_pattern(int patt)
1554 printf("Test Pattern:\t\t");
1555 switch (patt)
1557 case 0:
1558 printf("unframed X^11+X^9+1\n");
1559 break;
1560 case 1:
1561 printf("unframed X^15+X^14+1\n");
1562 break;
1563 case 2:
1564 printf("unframed X^20+X^17+1\n");
1565 break;
1566 case 3:
1567 printf("unframed X^23+X^18+1\n");
1568 break;
1569 case 4:
1570 printf("unframed X^11+X^9+1 w/7ZS\n");
1571 break;
1572 case 5:
1573 printf("unframed X^15+X^14+1 w/7ZS\n");
1574 break;
1575 case 6:
1576 printf("unframed X^20+X^17+1 w/14ZS (QRSS)\n");
1577 break;
1578 case 7:
1579 printf("unframed X^23+X^18+1 w/14ZS\n");
1580 break;
1581 case 8:
1582 printf("framed X^11+X^9+1\n");
1583 break;
1584 case 9:
1585 printf("framed X^15+X^14+1\n");
1586 break;
1587 case 10:
1588 printf("framed X^20+X^17+1\n");
1589 break;
1590 case 11:
1591 printf("framed X^23+X^18+1\n");
1592 break;
1593 case 12:;
1594 printf("framed X^11+X^9+1 w/7ZS\n");
1595 break;
1596 case 13:
1597 printf("framed X^15+X^14+1 w/7ZS\n");
1598 break;
1599 case 14:
1600 printf("framed X^20+X^17+1 w/14ZS (QRSS)\n");
1601 break;
1602 case 15:
1603 printf("framed X^23+X^18+1 w/14ZS\n");
1604 break;
1608 void print_t1_far_report(int idx)
1610 u_int16_t far = status.snmp.t1.prm[idx];
1612 printf(" SEQ=%d ", (far & T1PRM_SEQ)>>8);
1613 if (far & T1PRM_G1) printf("CRC=1");
1614 else if (far & T1PRM_G2) printf("CRC=1 to 5");
1615 else if (far & T1PRM_G3) printf("CRC=5 to 10");
1616 else if (far & T1PRM_G4) printf("CRC=10 to 100");
1617 else if (far & T1PRM_G5) printf("CRC=100 to 319");
1618 else if (far & T1PRM_G6) printf("CRC>=320");
1619 else printf("CRC=0");
1620 printf(" SE=%d", (far & T1PRM_SE) ? 1 : 0);
1621 printf(" FE=%d", (far & T1PRM_FE) ? 1 : 0);
1622 printf(" LV=%d", (far & T1PRM_LV) ? 1 : 0);
1623 printf(" SL=%d", (far & T1PRM_SL) ? 1 : 0);
1624 printf(" LB=%d", (far & T1PRM_LB) ? 1 : 0);
1625 printf("\n");
1628 void print_t1_snmp()
1630 printf("SNMP Near-end performance data:\n");
1631 printf(" LCV=%d", status.snmp.t1.lcv);
1632 printf(" LOS=%d", (status.snmp.t1.line & TLINE_LOS) ? 1 : 0);
1633 printf(" FE=%d", status.snmp.t1.fe);
1634 printf(" CRC=%d", status.snmp.t1.crc);
1635 printf(" AIS=%d", (status.snmp.t1.line & TLINE_RX_AIS) ? 1 : 0);
1636 printf(" SEF=%d", (status.snmp.t1.line & T1LINE_SEF) ? 1 : 0);
1637 printf(" OOF=%d", (status.snmp.t1.line & TLINE_LOF) ? 1 : 0);
1638 printf(" RAI=%d",(status.snmp.t1.line & TLINE_RX_RAI) ? 1 : 0);
1639 printf("\n");
1640 if (config.format == CFG_FORMAT_T1ESF)
1642 printf("ANSI Far-end performance reports:\n");
1643 print_t1_far_report(0);
1644 print_t1_far_report(1);
1645 print_t1_far_report(2);
1646 print_t1_far_report(3);
1650 void print_t1_dsu()
1652 const char *no = "No", *yes = "Yes";
1653 u_int16_t mii16 = read_mii(16);
1654 u_int8_t isr0 = read_framer(Bt8370_ISR0);
1655 u_int8_t loop = read_framer(Bt8370_LOOP);
1656 u_int8_t vga_max = read_framer(Bt8370_VGA_MAX) & 0x3F;
1657 u_int8_t alm1 = read_framer(Bt8370_ALM1);
1658 u_int8_t alm3 = read_framer(Bt8370_ALM3);
1659 u_int8_t talm = read_framer(Bt8370_TALM);
1660 u_int8_t tpatt = read_framer(Bt8370_TPATT);
1661 u_int8_t tpulse = read_framer(Bt8370_TLIU_CR);
1662 u_int8_t vga;
1663 u_int8_t bop;
1664 u_int8_t saved_pulse, saved_lbo;
1666 /* d/c write required before read */
1667 write_framer(Bt8370_VGA, 0);
1668 vga = read_framer(Bt8370_VGA) & 0x3F;
1670 print_format();
1671 print_time_slots();
1672 print_tx_clk_src();
1673 print_tx_speed();
1675 saved_pulse = config.tx_pulse;
1676 config.tx_pulse = tpulse & 0x0E;
1677 saved_lbo = config.tx_lbo;
1678 config.tx_lbo = tpulse & 0x30;
1679 print_tx_pulse(0);
1680 config.tx_pulse = saved_pulse;
1681 config.tx_lbo = saved_lbo;
1683 printf("Tx outputs: \t\t%sabled\n", (mii16 & MII16_T1_XOE) ? "En" : "Dis");
1684 printf("Line impedance:\t\t%s ohms\n", (mii16 & MII16_T1_Z) ? "120" : "100");
1685 printf("Max line loss: \t\t%4.1f dB\n", vga_dbs(vga_max));
1686 printf("Cur line loss: \t\t%4.1f dB\n", vga_dbs(vga));
1687 printf("Invert data: \t\t%s\n", (mii16 & MII16_T1_INVERT) ? yes : no);
1688 printf("Line loop: \t\t%s\n", (loop & LOOP_LINE) ? yes : no);
1689 printf("Payload loop: \t\t%s\n", (loop & LOOP_PAYLOAD) ? yes : no);
1690 printf("Framer loop: \t\t%s\n", (loop & LOOP_FRAMER) ? yes : no);
1691 printf("Analog loop: \t\t%s\n", (loop & LOOP_ANALOG) ? yes : no);
1692 printf("Tx AIS: \t\t%s\n", ((talm & TALM_TAIS) ||
1693 ((talm & TALM_AUTO_AIS) && (alm1 & ALM1_RLOS))) ? yes : no);
1694 printf("Rx AIS: \t\t%s\n", (alm1 & ALM1_RAIS) ? yes : no);
1695 if (((config.format & 1)==0) && (config.format != CFG_FORMAT_E1NONE))
1697 printf("Tx RAI: \t\t%s\n", ((talm & TALM_TYEL) ||
1698 ((talm & TALM_AUTO_YEL) && (alm3 & ALM3_FRED))) ? yes : no);
1699 printf("Rx RAI: \t\t%s\n", (alm1 & ALM1_RYEL) ? yes : no);
1701 if (config.format == CFG_FORMAT_T1ESF)
1703 printf("Tx BOP RAI: \t\t%s\n", (alm1 & ALM1_RLOF) ? yes : no);
1704 printf("Rx BOP RAI: \t\t%s\n", (alm1 & ALM1_RMYEL) ? yes : no);
1706 if ((config.format & 0x11) == 0x10) /* E1CAS */
1708 printf("Rx TS16 AIS: \t\t%s\n", (alm3 & ALM3_RMAIS) ? yes : no);
1709 printf("Tx TS16 RAI; \t\t%s\n",
1710 ((talm & TALM_AUTO_MYEL) && (alm3 & ALM3_SRED)) ? yes : no);
1712 printf("Rx LOS analog: \t\t%s\n", (alm1 & ALM1_RALOS) ? yes : no);
1713 printf("Rx LOS digital:\t\t%s\n", (alm1 & ALM1_RLOS) ? yes : no);
1714 printf("Rx LOF: \t\t%s\n", (alm1 & ALM1_RLOF) ? yes : no);
1715 printf("Tx QRS: \t\t%s\n", (tpatt & 0x10) ? yes : no);
1716 printf("Rx QRS: \t\t%s\n", (isr0 & 0x10) ? yes : no);
1717 printf("LCV errors: \t\t%d\n",
1718 read_framer(Bt8370_LCV_LO) + (read_framer(Bt8370_LCV_HI)<<8));
1719 if (config.format != CFG_FORMAT_E1NONE)
1721 if ((config.format & 1)==0) printf("Far End Block Errors:\t%d\n",
1722 read_framer(Bt8370_FEBE_LO) + (read_framer(Bt8370_FEBE_HI)<<8));
1723 printf("CRC errors: \t\t%d\n",
1724 read_framer(Bt8370_CRC_LO) + (read_framer(Bt8370_CRC_HI)<<8));
1725 printf("Frame errors: \t\t%d\n",
1726 read_framer(Bt8370_FERR_LO) + (read_framer(Bt8370_FERR_HI)<<8));
1727 printf("Sev Err Frms: \t\t%d\n", read_framer(Bt8370_AERR) & 0x03);
1728 printf("Change of Frm align:\t%d\n", (read_framer(Bt8370_AERR) & 0x0C)>>2);
1729 printf("Loss of Frame events:\t%d\n", (read_framer(Bt8370_AERR) & 0xF0)>>4);
1731 if (config.format == CFG_FORMAT_T1ESF)
1733 if ((bop = read_framer(Bt8370_TBOP)))
1734 printf("Last Tx BOP msg:\t0x%02X (%s)\n", bop, print_t1_bop(bop));
1735 if ((bop = read_framer(Bt8370_RBOP)))
1736 printf("Last Rx BOP msg:\t0x%02X (%s)\n", bop, print_t1_bop(bop&0x3F));
1738 print_t1_snmp();
1741 void t1_cmd(int argc, char **argv)
1743 int ch;
1744 const char *optstring = "a:A:B:c:de:E:fF:g:iIlLpPstT:u:U:xX";
1746 while ((ch = getopt(argc, argv, optstring)) != -1)
1748 switch (ch)
1750 case 'a': /* stop alarms */
1752 switch (optarg[0])
1754 case 'y': /* Stop sending Yellow Alarm */
1756 if ((config.format == CFG_FORMAT_T1SF) ||
1757 (config.format == CFG_FORMAT_E1NONE))
1758 printf("No Yellow alarm for this frame format\n");
1759 else if (config.format == CFG_FORMAT_T1ESF)
1760 write_framer(Bt8370_BOP, 0xE0); /* rbop 25, tbop off */
1761 else
1763 u_int8_t talm = read_framer(Bt8370_TALM);
1764 write_framer(Bt8370_TALM, talm & ~TALM_TYEL);
1766 if (verbose) printf("Stop sending Yellow alarm\n");
1767 break;
1769 case 'a': /* Stop sending AIS */
1770 case 'b': /* Stop sending Blue Alarm */
1772 u_int8_t talm = read_framer(Bt8370_TALM);
1773 write_framer(Bt8370_TALM, talm & ~TALM_TAIS);
1774 if (verbose) printf("Stop sending AIS/Blue signal\n");
1775 break;
1777 default:
1778 printf("Unknown alarm: %c\n", optarg[0]);
1780 break;
1782 case 'A': /* start alarms */
1784 switch (optarg[0])
1786 case 'y': /* Start sending Yellow Alarm */
1788 if ((config.format == CFG_FORMAT_T1SF) ||
1789 (config.format == CFG_FORMAT_E1NONE))
1790 printf("No Yellow alarm for this frame format\n");
1791 else if (config.format == CFG_FORMAT_T1ESF)
1793 write_framer(Bt8370_BOP, 0x0F); /* rbop off, tbop cont */
1794 write_framer(Bt8370_TBOP, T1BOP_OOF);
1796 else
1798 u_int8_t talm = read_framer(Bt8370_TALM);
1799 write_framer(Bt8370_TALM, talm | TALM_TYEL);
1801 if (verbose) printf("Sending Yellow alarm\n");
1802 break;
1804 case 'a': /* Start sending AIS */
1805 case 'b': /* Start sending Blue Alarm */
1807 u_int8_t talm = read_framer(Bt8370_TALM);
1808 write_framer(Bt8370_TALM, talm | TALM_TAIS);
1809 if (verbose) printf("Sending AIS/Blue signal\n");
1810 break;
1812 default:
1813 printf("Unknown alarm: %c\n", optarg[0]);
1815 break;
1817 case 'B': /* send BOP msg */
1819 u_int8_t bop = (u_int8_t)strtoul(optarg, NULL, 0);
1820 if (config.format == CFG_FORMAT_T1ESF)
1822 write_framer(Bt8370_BOP, 0x0B); /* rbop off, tbop 25 */
1823 write_framer(Bt8370_TBOP, bop); /* start sending BOP msg */
1824 sleep(1); /* sending 25 BOP msgs takes about 100 ms. */
1825 write_framer(Bt8370_BOP, 0xE0); /* rbop 25, tbop off */
1826 if (verbose) printf("Sent '0x%02X' BOP msg 25 times\n", bop);
1828 else
1829 printf("BOP msgs only work in T1-ESF format\n");
1830 break;
1832 case 'c': /* set cable length */
1834 config.cable_len = strtoul(optarg, NULL, 0);
1835 if (verbose) print_cable_len();
1836 update = 1;
1837 break;
1839 case 'd': /* DSU status */
1840 case 's': /* deprecated */
1842 print_t1_dsu();
1843 break;
1845 case 'e': /* set framimg format */
1847 config.format = strtoul(optarg, NULL, 0);
1848 if (verbose) print_format();
1849 update = 1;
1850 break;
1852 case 'E': /* set time slots */
1854 config.time_slots = strtoul(optarg, NULL, 16);
1855 if (verbose) print_time_slots();
1856 update = 1;
1857 break;
1859 case 'f': /* read and print framer regs */
1861 int i;
1862 printf("Bt8370 regs:\n");
1863 printf(" 0 1 2 3 4 5 6 7 8 9 A B C D E F");
1864 for (i=0; i<512; i++)
1866 if (i%16 == 0) printf("\n%03X: ", i);
1867 printf("%02X ", read_framer(i));
1869 printf("\n\n");
1870 break;
1872 case 'F': /* write framer reg */
1874 u_int32_t addr = strtoul(optarg, NULL, 0);
1875 u_int32_t data = strtoul(argv[optind++], NULL, 0);
1876 write_framer(addr, data);
1877 if (verbose)
1879 data = read_framer(addr);
1880 printf("Write framer register: addr = 0x%02X data = 0x%02X\n", addr, data);
1882 break;
1884 case 'g': /* set receiver gain */
1886 config.rx_gain_max = strtoul(optarg, NULL, 0);
1887 if (verbose) print_rx_gain_max();
1888 update = 1;
1889 break;
1891 case 'i': /* send CSU loopback deactivate inband cmd */
1893 if (config.format == CFG_FORMAT_T1SF)
1895 if (verbose) printf("Sending 'CSU loop down' inband cmd for 10 secs...");
1896 ioctl_snmp_send(TSEND_RESET);
1897 sleep(10);
1898 ioctl_snmp_send(TSEND_NORMAL);
1899 if (verbose) printf("done\n");
1901 else
1902 printf("Inband loopback cmds only work in T1-SF format");
1903 break;
1905 case 'I': /* send CSU loopback activate inband cmd */
1907 if (config.format == CFG_FORMAT_T1SF)
1909 if (verbose) printf("Sending 'CSU loop up' inband cmd for 10 secs...");
1910 ioctl_snmp_send(TSEND_LINE);
1911 sleep(10);
1912 ioctl_snmp_send(TSEND_NORMAL);
1913 if (verbose) printf("done\n");
1915 else
1916 printf("Inband loopback cmds only work in T1-SF format");
1917 break;
1919 case 'l': /* send line loopback deactivate BOP msg */
1921 if (config.format == CFG_FORMAT_T1ESF)
1923 ioctl_snmp_send(TSEND_RESET);
1924 if (verbose) printf("Sent 'Line Loop Down' BOP cmd\n");
1926 else
1927 printf("BOP msgs only work in T1-ESF format\n");
1928 break;
1930 case 'L': /* send line loopback activate BOP msg */
1932 if (config.format == CFG_FORMAT_T1ESF)
1934 ioctl_snmp_send(TSEND_LINE);
1935 if (verbose) printf("Sent 'Line Loop Up' BOP cmd\n");
1937 else
1938 printf("BOP msgs only work in T1-ESF format\n");
1939 break;
1941 case 'p': /* send payload loopback deactivate BOP msg */
1943 if (config.format == CFG_FORMAT_T1ESF)
1945 ioctl_snmp_send(TSEND_RESET);
1946 if (verbose) printf("Sent 'Payload Loop Down' BOP cmd\n");
1948 else
1949 printf("BOP msgs only work in T1-ESF format\n");
1950 break;
1952 case 'P': /* send payload loopback activate BOP msg */
1954 if (config.format == CFG_FORMAT_T1ESF)
1956 ioctl_snmp_send(TSEND_PAYLOAD);
1957 if (verbose) printf("Sent 'Payload Loop Up' BOP cmd\n");
1959 else
1960 printf("BOP msgs only work in T1-ESF format\n");
1961 break;
1963 case 't': /* stop sending test pattern */
1965 ioctl_snmp_send(TSEND_NORMAL);
1966 if (verbose) printf("Stop sending test pattern\n");
1967 break;
1969 case 'T': /* start sending test pattern */
1971 u_int8_t patt = (u_int8_t)strtoul(optarg, NULL, 0);
1972 write_framer(Bt8370_TPATT, 0x10 + patt);
1973 write_framer(Bt8370_RPATT, 0x30 + patt);
1974 if (verbose) print_t1_test_pattern(patt);
1975 break;
1977 case 'u': /* set transmit pulse shape */
1979 config.tx_pulse = strtoul(optarg, NULL, 0);
1980 if (verbose) print_tx_pulse(0);
1981 update = 1;
1982 break;
1984 case 'U': /* set tx line build-out */
1986 if (config.tx_pulse == CFG_PULSE_T1CSU)
1988 config.tx_lbo = strtoul(optarg, NULL, 0);
1989 if (verbose) print_tx_pulse(0);
1990 update = 1;
1992 else
1993 printf("LBO only meaningful if Tx Pulse is T1CSU\n");
1994 break;
1996 case 'x': /* disable transmitter outputs */
1998 write_mii(16, read_mii(16) & ~MII16_T1_XOE);
1999 if (verbose) printf("Transmitter outputs disabled\n");
2000 break;
2002 case 'X': /* enable transmitter outputs */
2004 write_mii(16, read_mii(16) | MII16_T1_XOE);
2005 if (verbose) printf("Transmitter outputs enabled\n");
2006 break;
2008 default:
2010 printf("Unknown command char: %c\n", ch);
2011 exit(1);
2012 } /* case */
2013 } /* switch */
2014 } /* while */
2015 } /* proc */
2017 /* used when reading Motorola S-Record format ROM files */
2018 unsigned char read_hex(FILE *f)
2020 unsigned char a, b, c;
2021 for (a=0, b=0; a<2; a++)
2023 c = fgetc(f);
2024 c -= 48;
2025 if (c > 9) c -= 7;
2026 b = (b<<4) | (c & 0xF);
2028 checksum += b;
2029 return b;
2032 void load_xilinx(char *name)
2034 FILE *f;
2035 char *ucode;
2036 int c, i, length;
2038 if (verbose) printf("Load firmware from file %s...\n", name);
2039 if ((f = fopen(name, "r")) == 0)
2041 perror("Failed to open file");
2042 exit(1);
2045 ucode = (char *)malloc(8192); bzero(ucode, 8192);
2047 c = fgetc(f);
2048 if (c == 'X')
2049 { /* Xilinx raw bits file (foo.rbt) */
2050 /* skip seven lines of boiler plate */
2051 for (i=0; i<7;) if ((c=fgetc(f))=='\n') i++;
2052 /* build a dense bit array */
2053 i = length = 0;
2054 while ((c=fgetc(f))!=EOF)
2055 { /* LSB first */
2056 if (c=='1') ucode[length] |= 1<<i++;
2057 if (c=='0') i++;
2058 if (i==8) { i=0; length++; }
2061 else if (c == 'S')
2062 { /* Motarola S records (foo.exo) */
2063 int blklen;
2064 length = 0;
2065 ungetc(c, f);
2066 while ((c = fgetc(f)) != EOF)
2068 if (c != 'S')
2070 printf("I'm confused; I expected an 'S'\n");
2071 exit(1);
2073 c = fgetc(f);
2074 if (c == '9') break;
2075 else if (c == '1')
2077 checksum = 0;
2078 blklen = read_hex(f) -3;
2079 read_hex(f); /* hi blkaddr */
2080 read_hex(f); /* lo blkaddr */
2081 for (i=0; i<blklen; i++)
2082 ucode[length++] = read_hex(f);
2083 read_hex(f); /* process but ignore checksum */
2084 if (checksum != 0xFF)
2086 printf("File checksum error\n");
2087 exit(1);
2089 c = fgetc(f); /* throw away eol */
2090 c = fgetc(f); /* throw away eol */
2092 else
2094 printf("I'm confused; I expected a '1' or a '9'\n");
2095 exit(1);
2097 } /* while */
2098 } /* Motorola S-Record */
2099 else
2101 printf("Unknown file type giving up\n");
2102 exit(1);
2105 load_xilinx_from_file(ucode, length);
2108 /* 32-bit CRC calculated right-to-left over 8-bit bytes */
2109 u_int32_t crc32(u_int8_t *bufp, int len)
2111 int bit, i;
2112 u_int32_t data;
2113 u_int32_t crc = 0xFFFFFFFFL;
2114 u_int32_t poly = 0xEDB88320L;
2116 for (i = 0; i < len; i++)
2117 for (data = *bufp++, bit = 0; bit < 8; bit++, data >>= 1)
2118 crc = (crc >> 1) ^ (((crc ^ data) & 1) ? poly : 0);
2120 return crc;
2123 /* 8-bit CRC calculated left-to-right over 16-bit words */
2124 u_int8_t crc8(u_int16_t *bufp, int len)
2126 int bit, i;
2127 u_int16_t data;
2128 u_int8_t crc = 0xFF;
2129 u_int8_t poly = 0x07;
2131 for (i = 0; i < len; i++)
2132 for (data = *bufp++, bit = 15; bit >= 0; bit--)
2134 if ((i==8) && (bit==7)) break;
2135 crc = (crc << 1) ^ ((((crc >> 7) ^ (data >> bit)) & 1) ? poly : 0);
2137 return crc;
2140 void main_cmd(int argc, char **argv)
2142 int ch;
2143 const char *optstring = "13a:bBcCdDeEf:gG:hi:L:mM:pP:sS:tT:uUvVw:x:X:yY?";
2145 while ((ch = getopt(argc, argv, optstring)) != -1)
2147 switch (ch)
2149 case '1': /* T1 commands */
2151 if (verbose) printf("Doing T1 settings\n");
2152 if (status.card_type != CSID_LMC_T1E1)
2154 printf("T1 settings only apply to T1E1 cards\n");
2155 exit(1);
2157 t1_cmd(argc, argv);
2158 break;
2160 case '3': /* T3 commands */
2162 if (verbose) printf("Doing T3 settings\n");
2163 if (status.card_type != CSID_LMC_T3)
2165 printf("T3 settings only apply to T3 cards\n");
2166 exit(1);
2168 t3_cmd(argc, argv);
2169 break;
2171 case 'a': /* clock source */
2173 if ((status.card_type != CSID_LMC_T1E1) ||
2174 (status.card_type != CSID_LMC_HSSI) ||
2175 (status.card_type != CSID_LMC_HSSIc))
2177 if (verbose) print_tx_clk_src();
2178 config.tx_clk_src = strtoul(optarg, NULL, 0);
2179 update = 1;
2181 else
2182 printf("txclksrc only applies to T1E1 and HSSI card types\n");
2183 break;
2185 case 'b': /* read bios rom */
2187 unsigned int i;
2188 printf("Bios ROM:\n");
2189 printf(" 0 1 2 3 4 5 6 7 8 9 A B C D E F");
2190 for (i=0; i<256; i++)
2192 if (i%16 == 0) printf("\n%02X: ", i);
2193 printf("%02X ", read_bios_rom(i));
2195 printf("\n\n");
2196 break;
2198 case 'B': /* write bios rom */
2200 unsigned int i;
2201 for (i=0; i<256; i++) write_bios_rom(i, 255-i);
2202 if (verbose) printf("wrote (0..255) to bios rom addrs (0..255)\n");
2203 break;
2205 case 'c': /* set crc_len = 16 */
2207 config.crc_len = CFG_CRC_16;
2208 if (verbose) print_crc_len();
2209 update = 1;
2210 break;
2212 case 'C': /* set crc_len = 32 */
2214 config.crc_len = CFG_CRC_32;
2215 if (verbose) print_crc_len();
2216 update = 1;
2217 break;
2219 case 'd': /* clear DEBUG flag */
2221 config.debug = 0;
2222 if (verbose) printf("DEBUG flag cleared\n");
2223 update = 1;
2224 break;
2226 case 'D': /* set DEBUG flag */
2228 config.debug = 1;
2229 if (verbose) printf("DEBUG flag set\n");
2230 update = 1;
2231 break;
2233 case 'e': /* set DTE (default) */
2235 if ((status.card_type == CSID_LMC_SSI) ||
2236 (status.card_type == CSID_LMC_HSSIc))
2238 config.dte_dce = CFG_DTE;
2239 if (verbose) print_dte_dce();
2240 update = 1;
2242 else
2243 printf("DTE cmd only applies to SSI & HSSIc cards\n");
2244 break;
2246 case 'E': /* set DCE */
2248 if ((status.card_type == CSID_LMC_SSI) ||
2249 (status.card_type == CSID_LMC_HSSIc))
2251 config.dte_dce = CFG_DCE;
2252 if (verbose) print_dte_dce();
2253 update = 1;
2255 else
2256 printf("DCE cmd only applies to SSI & HSSIc cards\n");
2257 break;
2259 case 'f': /* set synth osc freq */
2261 if ((status.card_type == CSID_LMC_SSI) ||
2262 (status.card_type == CSID_LMC_HSSIc))
2264 synth_freq(strtoul(optarg, NULL, 0));
2265 write_synth(config.synth);
2266 if (verbose) print_synth_freq();
2268 else
2269 printf("synth osc freq only applies to SSI & HSSIc cards\n");
2270 break;
2272 case 'g': /* load gate array microcode from ROM */
2274 load_xilinx_from_rom();
2275 if (verbose) printf("gate array configured from on-board ROM\n");
2276 break;
2278 case 'G': /* load gate array microcode from file */
2280 load_xilinx(optarg);
2281 if (verbose) printf("gate array configured from file %s\n", optarg);
2282 break;
2284 case 'h': /* help */
2285 case '?':
2287 usage();
2288 exit(0);
2289 /*NOTREACHED*/
2291 case 'i': /* interface name */
2293 /* already scanned this */
2294 break;
2296 case 'L': /* set loopback modes */
2298 config.loop_back = strtoul(optarg, NULL, 0);
2299 if (verbose) print_loop_back(0);
2300 update = 1;
2301 break;
2303 case 'm': /* read and print MII regs */
2305 int i;
2306 printf("MII regs:\n");
2307 printf(" 0 1 2 3 4 5 6 7");
2308 for (i=0; i<32; i++)
2310 u_int16_t mii = read_mii(i);
2311 if (i%8 == 0) printf("\n%02X: ", i);
2312 printf("%04X ", mii);
2314 printf("\n\n");
2315 break;
2317 case 'M': /* write MII reg */
2319 u_int32_t addr = strtoul(optarg, NULL, 0);
2320 u_int32_t data = strtoul(argv[optind++], NULL, 0);
2321 write_mii(addr, data);
2322 if (verbose)
2324 data = read_mii(addr);
2325 printf("Write mii register: addr = 0x%02X data = 0x%04X\n", addr, data);
2327 break;
2329 case 'p': /* read and print PCI config regs */
2331 int i;
2332 printf("21140A PCI Config regs:\n");
2333 printf(" 0 1 2 3");
2334 for (i=0; i<16; i++)
2336 if (i%4 == 0) printf("\n%X: ", i);
2337 printf("%08X ", read_pci_config(i<<2));
2339 printf("\n\n");
2340 break;
2342 case 'P': /* write PCI config reg */
2344 u_int32_t addr = strtoul(optarg, NULL, 0);
2345 u_int32_t data = strtoul(argv[optind++], NULL, 0);
2346 write_pci_config(addr, data);
2347 if (verbose)
2349 data = read_pci_config(addr);
2350 printf("Write PCI config reg: addr = 0x%02X data = 0x%08X\n", addr, data);
2352 break;
2354 case 's': /* read and print Tulip SROM */
2356 int i;
2357 printf("21140A SROM:\n");
2358 printf(" 0 1 2 3 4 5 6 7 8 9 A B C D E F");
2359 for (i=0; i<64; i++)
2361 u_int16_t srom = read_srom(i);
2362 if (i%8 == 0) printf("\n%02X: ", i<<1);
2363 printf("%02X %02X ", srom & 0xFF, srom>>8);
2365 printf("\n\n");
2366 break;
2368 case 'S': /* write Tulip SROM loc */
2370 int i;
2371 u_int16_t srom[64];
2372 u_int32_t board = strtoul(optarg, NULL, 0);
2373 /* board: HSSI=3, DS3=4, SSI=5, T1E1=6, HSSIc=7 */
2375 for (i=0; i<64; i++) srom[i] = 0;
2376 srom[0] = 0x1376; /* subsys vendor id */
2377 srom[1] = board ? (u_int16_t)board : (read_mii(3)>>4 & 0xF) +1;
2378 /* Tulip hardware checks this checksum */
2379 srom[8] = crc8(srom, 9);
2380 srom[10] = 0x6000; /* ethernet address */
2381 srom[11] = 0x0099; /* ethernet address */
2382 srom[12] = read_srom(12); /* 0x0000; */
2383 /* srom checksum is low 16 bits of Ethernet CRC-32 */
2384 srom[63] = (u_int16_t)~crc32((u_int8_t *)srom, 126);
2386 #if 0 /* really write it */
2387 for (i=0; i<64; i++) write_srom(i, srom[i]);
2388 #else /* print what would be written */
2389 printf("Caution! Recompile %s to enable this.\n", progname);
2390 printf("This is what would have been written:\n");
2391 printf(" 0 1 2 3 4 5 6 7 8 9 A B C D E F");
2392 for (i=0; i<64; i++)
2394 if (i%8 == 0) printf("\n%02X: ", i<<1);
2395 printf("%02X %02X ", srom[i] & 0xFF, srom[i]>>8);
2397 printf("\n\n");
2398 #endif
2399 break;
2401 case 't': /* read and print Tulip CSRs */
2403 int i;
2404 printf("21140A CSRs:\n");
2405 printf(" 0 1 2 3");
2406 for (i=0; i<16; i++)
2408 if (i%4 == 0) printf("\n%X: ", i);
2409 printf("%08X ", read_csr(i));
2411 printf("\n\n");
2412 break;
2414 case 'T': /* write Tulip CSR */
2416 u_int32_t addr = strtoul(optarg, NULL, 0);
2417 u_int32_t data = strtoul(argv[optind++], NULL, 0);
2418 write_csr(addr, data);
2419 if (verbose)
2421 data = read_csr(addr);
2422 printf("Write 21140A CSR: addr = 0x%02X data = 0x%08X\n", addr, data);
2424 break;
2426 case 'u': /* reset event counters */
2428 ioctl_reset_cntrs();
2429 if (verbose) printf("Event counters reset\n");
2430 break;
2432 case 'U': /* reset gate array */
2434 reset_xilinx();
2435 if (verbose) printf("gate array reset\n");
2436 break;
2438 case 'v': /* set verbose mode */
2440 verbose = 1;
2441 break;
2443 case 'V': /* print card configuration */
2445 summary = 1;
2446 break;
2448 case 'w':
2450 waittime = strtoul(optarg, NULL, 0);
2451 break;
2453 case 'x': /* <number> set line protocol */
2455 config.keep_alive = 1; /* required for LMI operation */
2456 config.proto = strtoul(optarg, NULL, 0);
2457 if (verbose) printf("line protocol set to %d\n", config.proto);
2458 update = 1;
2459 break;
2461 case 'X': /* <number> set line package */
2463 config.keep_alive = 1; /* required for LMI operation */
2464 config.stack = strtoul(optarg, NULL, 0);
2465 if (verbose) printf("line package set to %d\n", config.stack);
2466 update = 1;
2467 break;
2469 case 'y': /* disable SPPP keep-alive packets */
2471 if ((config.stack == STACK_SPPP) &&
2472 (config.proto == PROTO_FRM_RLY))
2473 printf("keep-alives must be ON for Frame-Relay/SPPP\n");
2474 else
2476 config.keep_alive = 0;
2477 if (verbose) printf("SPPP keep-alive packets disabled\n");
2478 update = 1;
2480 break;
2482 case 'Y': /* enable SPPP keep-alive packets */
2484 config.keep_alive = 1;
2485 if (verbose) printf("SPPP keep-alive packets enabled\n");
2486 update = 1;
2487 break;
2489 default:
2491 printf("Unknown command char: %c\n", ch);
2492 exit(1);
2493 } /* case */
2494 } /* switch */
2495 } /* while */
2496 } /* proc */
2498 int main(int argc, char **argv)
2500 int i, error;
2502 progname = (char *)argv[0];
2504 /* 1) Read the interface name from the command line. */
2505 #if __linux__
2506 ifname = (argc==1) ? "hdlc0" : (char *)argv[1];
2507 #else
2508 ifname = (argc==1) ? DEVICE_NAME"0" : (char *)argv[1];
2509 #endif
2511 /* 2) Open the device; decide if netgraph is being used, */
2512 /* use netgraph if ifname ends with ":" */
2513 for (i=0; ifname[i] != 0; i++) continue;
2515 /* Get a socket type file descriptor. */
2516 #if defined(NETGRAPH)
2517 if ((netgraph = (ifname[i-1] == ':')))
2518 error = NgMkSockNode(NULL, &fdcs, NULL);
2519 else
2520 #endif
2521 error = fdcs = socket(AF_INET, SOCK_DGRAM, 0);
2522 if (error < 0)
2524 fprintf(stderr, "%s: %s() failed: %s\n", progname,
2525 netgraph? "NgMkSockNode" : "socket", strerror(errno));
2526 exit(1);
2529 /* 3) Read the current interface configuration from the driver. */
2530 ioctl_read_config();
2531 ioctl_read_status();
2533 summary = (argc <= 2); /* print summary at end */
2534 update = 0; /* write to card at end */
2536 /* 4) Read the command line args and carry out their actions. */
2537 optind = 2;
2538 if (argc > 2) main_cmd(argc, argv);
2540 if (summary) print_summary();
2542 /* 5) Write the modified interface configuration to the driver. */
2543 if (update) ioctl_write_config();
2545 while (waittime)
2547 struct status old;
2549 ioctl_read_status();
2550 old = status;
2551 sleep(waittime);
2552 ioctl_read_status();
2554 status.cntrs.ibytes -= old.cntrs.ibytes;
2555 status.cntrs.obytes -= old.cntrs.obytes;
2556 status.cntrs.ipackets -= old.cntrs.ipackets;
2557 status.cntrs.opackets -= old.cntrs.opackets;
2558 status.cntrs.ierrors -= old.cntrs.ierrors;
2559 status.cntrs.oerrors -= old.cntrs.oerrors;
2560 status.cntrs.idrops -= old.cntrs.idrops;
2561 status.cntrs.missed -= old.cntrs.missed;
2562 status.cntrs.odrops -= old.cntrs.odrops;
2563 status.cntrs.fifo_over -= old.cntrs.fifo_over;
2564 status.cntrs.overruns -= old.cntrs.overruns;
2565 status.cntrs.fifo_under-= old.cntrs.fifo_under;
2566 status.cntrs.underruns -= old.cntrs.underruns;
2567 status.cntrs.crc_errs -= old.cntrs.crc_errs;
2568 status.cntrs.lcv_errs -= old.cntrs.lcv_errs;
2569 status.cntrs.frm_errs -= old.cntrs.frm_errs;
2570 status.cntrs.febe_errs -= old.cntrs.febe_errs;
2571 status.cntrs.par_errs -= old.cntrs.par_errs;
2572 status.cntrs.cpar_errs -= old.cntrs.cpar_errs;
2573 status.cntrs.mfrm_errs -= old.cntrs.mfrm_errs;
2574 status.cntrs.rxbuf -= old.cntrs.rxbuf;
2575 status.cntrs.txdma -= old.cntrs.txdma;
2576 status.cntrs.lck_watch -= old.cntrs.lck_watch;
2577 status.cntrs.lck_intr -= old.cntrs.lck_intr;
2578 status.cntrs.spare1 -= old.cntrs.spare1;
2579 status.cntrs.spare2 -= old.cntrs.spare2;
2580 status.cntrs.spare3 -= old.cntrs.spare3;
2581 status.cntrs.spare4 -= old.cntrs.spare4;
2583 putchar('\n');
2585 print_summary();
2588 exit(0);
2589 /* NOTREACHED */