xref: /onnv-gate/usr/src/cmd/tip/aculib/ventel.c (revision 549:9e644232f978)
10Sstevel@tonic-gate /*
20Sstevel@tonic-gate  * Copyright 2005 Sun Microsystems, Inc.  All rights reserved.
30Sstevel@tonic-gate  * Use is subject to license terms.
40Sstevel@tonic-gate  */
5*549Smuffin 
60Sstevel@tonic-gate /*
70Sstevel@tonic-gate  * Copyright (c) 1983 Regents of the University of California.
80Sstevel@tonic-gate  * All rights reserved. The Berkeley software License Agreement
90Sstevel@tonic-gate  * specifies the terms and conditions for redistribution.
100Sstevel@tonic-gate  */
11*549Smuffin 
12*549Smuffin #pragma ident	"%Z%%M%	%I%	%E% SMI"
130Sstevel@tonic-gate 
140Sstevel@tonic-gate /*
150Sstevel@tonic-gate  * Routines for calling up on a Ventel Modem
160Sstevel@tonic-gate  * Define VENNOECHO if the Ventel is strapped for "no echo".
170Sstevel@tonic-gate  */
180Sstevel@tonic-gate #include "tip.h"
190Sstevel@tonic-gate 
200Sstevel@tonic-gate #define	MAXRETRY	5
210Sstevel@tonic-gate 
22*549Smuffin static int	vensync(int);
23*549Smuffin static int	gobble(char);
24*549Smuffin static void	echo(char *);
25*549Smuffin static void	sigALRM(void);
26*549Smuffin static int	timeout = 0;
27*549Smuffin static sigjmp_buf	timeoutbuf;
280Sstevel@tonic-gate 
29*549Smuffin void	ven_disconnect(void);
30*549Smuffin 
31*549Smuffin /* ARGSUSED */
32*549Smuffin int
ven_dialer(char * num,char * acu)33*549Smuffin ven_dialer(char *num, char *acu)
340Sstevel@tonic-gate {
35*549Smuffin 	char *cp;
36*549Smuffin 	int connected = 0;
370Sstevel@tonic-gate 	struct termios buf;
380Sstevel@tonic-gate #ifdef ACULOG
390Sstevel@tonic-gate 	char line[80];
400Sstevel@tonic-gate #endif
410Sstevel@tonic-gate 	/*
420Sstevel@tonic-gate 	 * Get in synch with a couple of carriage returns
430Sstevel@tonic-gate 	 */
440Sstevel@tonic-gate 	if (!vensync(FD)) {
45*549Smuffin 		(void) printf("can't synchronize with ventel\n");
460Sstevel@tonic-gate #ifdef ACULOG
470Sstevel@tonic-gate 		logent(value(HOST), num, "ventel", "can't synch up");
480Sstevel@tonic-gate #endif
490Sstevel@tonic-gate 		return (0);
500Sstevel@tonic-gate 	}
510Sstevel@tonic-gate 	if (boolean(value(VERBOSE)))
52*549Smuffin 		(void) printf("\ndialing...");
53*549Smuffin 	(void) fflush(stdout);
54*549Smuffin 	(void) ioctl(FD, TCGETS, &buf);
550Sstevel@tonic-gate 	buf.c_cflag |= HUPCL;
56*549Smuffin 	(void) ioctl(FD, TCSETSF, &buf);
570Sstevel@tonic-gate #ifdef VENNOECHO
580Sstevel@tonic-gate 	echo("#k$\r$\n$D$I$A$L$:$ ");
590Sstevel@tonic-gate 	for (cp = num; *cp; cp++) {
60*549Smuffin 		(void) sleep(1);
61*549Smuffin 		(void) write(FD, cp, 1);
620Sstevel@tonic-gate 	}
630Sstevel@tonic-gate 	echo("\r$\n");
640Sstevel@tonic-gate #else
650Sstevel@tonic-gate 	echo("k$\r$\n$D$I$A$L$:$ <");
660Sstevel@tonic-gate 	for (cp = num; *cp; cp++) {
670Sstevel@tonic-gate 		char c;
680Sstevel@tonic-gate 
69*549Smuffin 		(void) sleep(1);
70*549Smuffin 		(void) write(FD, cp, 1);
71*549Smuffin 		(void) read(FD, &c, 1);
720Sstevel@tonic-gate 	}
730Sstevel@tonic-gate 	echo(">\r$\n");
740Sstevel@tonic-gate #endif
750Sstevel@tonic-gate 	if (gobble('\n'))
760Sstevel@tonic-gate 		connected = gobble('!');
77*549Smuffin 	(void) ioctl(FD, TCFLSH, TCIOFLUSH);
780Sstevel@tonic-gate #ifdef ACULOG
790Sstevel@tonic-gate 	if (timeout) {
80*549Smuffin 		(void) sprintf(line, "%d second dial timeout",
81*549Smuffin 		    number(value(DIALTIMEOUT)));
820Sstevel@tonic-gate 		logent(value(HOST), num, "ventel", line);
830Sstevel@tonic-gate 	}
840Sstevel@tonic-gate #endif
850Sstevel@tonic-gate 	if (timeout)
860Sstevel@tonic-gate 		ven_disconnect();	/* insurance */
870Sstevel@tonic-gate 	return (connected);
880Sstevel@tonic-gate }
890Sstevel@tonic-gate 
90*549Smuffin void
ven_disconnect(void)91*549Smuffin ven_disconnect(void)
920Sstevel@tonic-gate {
930Sstevel@tonic-gate 
94*549Smuffin 	(void) close(FD);
950Sstevel@tonic-gate }
960Sstevel@tonic-gate 
97*549Smuffin void
ven_abort(void)98*549Smuffin ven_abort(void)
990Sstevel@tonic-gate {
1000Sstevel@tonic-gate 
101*549Smuffin 	(void) write(FD, "\03", 1);
102*549Smuffin 	(void) close(FD);
1030Sstevel@tonic-gate }
1040Sstevel@tonic-gate 
105*549Smuffin static void
echo(char * s)106*549Smuffin echo(char *s)
1070Sstevel@tonic-gate {
1080Sstevel@tonic-gate 	char c;
1090Sstevel@tonic-gate 
1100Sstevel@tonic-gate 	while (c = *s++) {
1110Sstevel@tonic-gate 		switch (c) {
1120Sstevel@tonic-gate 		case '$':
113*549Smuffin 			(void) read(FD, &c, 1);
1140Sstevel@tonic-gate 			s++;
1150Sstevel@tonic-gate 			break;
1160Sstevel@tonic-gate 
1170Sstevel@tonic-gate 		case '#':
1180Sstevel@tonic-gate 			c = *s++;
119*549Smuffin 			(void) write(FD, &c, 1);
1200Sstevel@tonic-gate 			break;
1210Sstevel@tonic-gate 
1220Sstevel@tonic-gate 		default:
123*549Smuffin 			(void) write(FD, &c, 1);
124*549Smuffin 			(void) read(FD, &c, 1);
1250Sstevel@tonic-gate 		}
1260Sstevel@tonic-gate 	}
1270Sstevel@tonic-gate }
1280Sstevel@tonic-gate 
1290Sstevel@tonic-gate static void
sigALRM(void)130*549Smuffin sigALRM(void)
1310Sstevel@tonic-gate {
1320Sstevel@tonic-gate 
133*549Smuffin 	(void) printf("\07timeout waiting for reply\n");
1340Sstevel@tonic-gate 	timeout = 1;
1350Sstevel@tonic-gate 	siglongjmp(timeoutbuf, 1);
1360Sstevel@tonic-gate }
1370Sstevel@tonic-gate 
1380Sstevel@tonic-gate static int
gobble(char match)139*549Smuffin gobble(char match)
1400Sstevel@tonic-gate {
1410Sstevel@tonic-gate 	char c;
1420Sstevel@tonic-gate 	sig_handler_t f;
1430Sstevel@tonic-gate 
1440Sstevel@tonic-gate 	f = signal(SIGALRM, (sig_handler_t)sigALRM);
1450Sstevel@tonic-gate 	timeout = 0;
1460Sstevel@tonic-gate 	do {
1470Sstevel@tonic-gate 		if (sigsetjmp(timeoutbuf, 1)) {
148*549Smuffin 			(void) signal(SIGALRM, f);
1490Sstevel@tonic-gate 			return (0);
1500Sstevel@tonic-gate 		}
151*549Smuffin 		(void) alarm(number(value(DIALTIMEOUT)));
152*549Smuffin 		(void) read(FD, &c, 1);
153*549Smuffin 		(void) alarm(0);
1540Sstevel@tonic-gate 		c &= 0177;
1550Sstevel@tonic-gate #ifdef notdef
1560Sstevel@tonic-gate 		if (boolean(value(VERBOSE)))
157*549Smuffin 			(void) putchar(c);
1580Sstevel@tonic-gate #endif
1590Sstevel@tonic-gate 	} while (c != '\n' && c != match);
160*549Smuffin 	(void) signal(SIGALRM, SIG_DFL);
1610Sstevel@tonic-gate 	return (c == match);
1620Sstevel@tonic-gate }
1630Sstevel@tonic-gate 
1640Sstevel@tonic-gate #define	min(a, b)	(((a) > (b)) ? (b) : (a))
1650Sstevel@tonic-gate /*
1660Sstevel@tonic-gate  * This convoluted piece of code attempts to get
1670Sstevel@tonic-gate  * the ventel in sync.  If you don't have FIONREAD
1680Sstevel@tonic-gate  * there are gory ways to simulate this.
1690Sstevel@tonic-gate  */
1700Sstevel@tonic-gate static int
vensync(int fd)171*549Smuffin vensync(int fd)
1720Sstevel@tonic-gate {
1730Sstevel@tonic-gate 	int already = 0, nread;
1740Sstevel@tonic-gate 	char buf[60];
1750Sstevel@tonic-gate 	int dtr = TIOCM_DTR;
1760Sstevel@tonic-gate 
1770Sstevel@tonic-gate 	/*
1780Sstevel@tonic-gate 	 * Toggle DTR to force anyone off that might have left
1790Sstevel@tonic-gate 	 * the modem connected, and insure a consistent state
1800Sstevel@tonic-gate 	 * to start from.
1810Sstevel@tonic-gate 	 *
1820Sstevel@tonic-gate 	 * If you don't have the ioctl calls to diddle directly
1830Sstevel@tonic-gate 	 * with DTR, you can always try setting the baud rate to 0.
1840Sstevel@tonic-gate 	 */
185*549Smuffin 	(void) ioctl(FD, TIOCMBIC, &dtr);
186*549Smuffin 	(void) sleep(2);
187*549Smuffin 	(void) ioctl(FD, TIOCMBIS, &dtr);
1880Sstevel@tonic-gate 	while (already < MAXRETRY) {
1890Sstevel@tonic-gate 		/*
1900Sstevel@tonic-gate 		 * After reseting the modem, send it two \r's to
1910Sstevel@tonic-gate 		 * autobaud on. Make sure to delay between them
1920Sstevel@tonic-gate 		 * so the modem can frame the incoming characters.
1930Sstevel@tonic-gate 		 */
194*549Smuffin 		(void) write(fd, "\r", 1);
1950Sstevel@tonic-gate #ifdef VMUNIX
1960Sstevel@tonic-gate 		{
1970Sstevel@tonic-gate #include <sys/time.h>
1980Sstevel@tonic-gate 		struct timeval tv = {0, 500000};
1990Sstevel@tonic-gate 
200*549Smuffin 		(void) select(0, 0, 0, 0, &tv);
2010Sstevel@tonic-gate 		}
2020Sstevel@tonic-gate #else
203*549Smuffin 		(void) sleep(1);
2040Sstevel@tonic-gate #endif
205*549Smuffin 		(void) write(fd, "\r", 1);
206*549Smuffin 		(void) sleep(3);
2070Sstevel@tonic-gate 		if (ioctl(fd, FIONREAD, (caddr_t)&nread) < 0) {
2080Sstevel@tonic-gate 			perror("tip: ioctl");
2090Sstevel@tonic-gate 			continue;
2100Sstevel@tonic-gate 		}
2110Sstevel@tonic-gate 		while (nread > 0) {
212*549Smuffin 			(void) read(fd, buf, min(nread, 60));
2130Sstevel@tonic-gate 			if ((buf[nread - 1] & 0177) == '$')
2140Sstevel@tonic-gate 				return (1);
2150Sstevel@tonic-gate 			nread -= min(nread, 60);
2160Sstevel@tonic-gate 		}
217*549Smuffin 		(void) sleep(1);
2180Sstevel@tonic-gate 		already++;
2190Sstevel@tonic-gate 	}
2200Sstevel@tonic-gate 	return (0);
2210Sstevel@tonic-gate }
222