xref: /original-bsd/usr.bin/tip/aculib/ventel.c (revision 6b7db209)
1 /*	ventel.c	1.2	82/07/29	*/
2 
3 #if VENTEL
4 /*
5  * Routines for calling up on a Ventel Modem
6  */
7 #include "tip.h"
8 #include <setjmp.h>
9 #include <errno.h>
10 
11 #define	MAXRETRY	5
12 #define	DISCONNECT	"\03"		/* ^C */
13 
14 static int sigALRM();
15 static int timeout = 0;
16 
17 ven_dialer(num, acu)
18 	register char *num;
19 	char *acu;
20 {
21 	register char *cp;
22 	register int connected = 0;
23 	char c;
24 #ifdef ACULOG
25 	char line[80];
26 #endif
27 	/*
28 	 * Get in synch with a couple of carriage returns
29 	 */
30 	if (!vensync(FD)) {
31 		printf("can't synchronize with ventel\n");
32 #ifdef ACULOG
33 		logent(value(HOST), num, "ventel", "can't synch up");
34 #endif
35 		return (0);
36 	}
37 	if (boolean(value(VERBOSE)))
38 		printf("\ndialing...");
39 	fflush(stdout);
40 	ioctl(FD, TIOCHPCL, 0);
41 	echo("k$\r$\n$D$I$A$L$:$ <");
42 	for (cp = num; *cp; cp++) {
43 		sleep(1);
44 		write(FD, cp, 1);
45 		read(FD, &c, 1);
46 	}
47 	echo(">\r$\n");
48 	if (gobble('\n'))
49 		connected = gobble('!');
50 	ioctl(FD, TIOCFLUSH);
51 #ifdef ACULOG
52 	if (timeout) {
53 		sprintf(line, "%d second dial timeout",
54 			number(value(DIALTIMEOUT)));
55 		logent(value(HOST), num, "ventel", line);
56 	}
57 #endif
58 	if (timeout)
59 		ven_disconnect();	/* insurance */
60 	return (connected);
61 }
62 
63 ven_disconnect()
64 {
65 	close(FD);
66 }
67 
68 ven_abort()
69 {
70 	write(FD, "\03", 1);
71 	close(FD);
72 }
73 
74 static int
75 echo(s)
76 	register char *s;
77 {
78 	char c;
79 
80 	while (c = *s++) switch (c) {
81 
82 	case '$':
83 		read(FD, &c, 1);
84 		s++;
85 		break;
86 
87 	case '#':
88 		c = *s++;
89 		write(FD, &c, 1);
90 		break;
91 
92 	default:
93 		write(FD, &c, 1);
94 		read(FD, &c, 1);
95 	}
96 }
97 
98 static int
99 sigALRM()
100 {
101 	signal(SIGALRM, SIG_IGN);
102 	printf("\07timeout waiting for reply\n");
103 	timeout = 1;
104 }
105 
106 static int
107 gobble(s)
108 	register char s;
109 {
110 	char c;
111 
112 	signal(SIGALRM, sigALRM);
113 	timeout = 0;
114 	do {
115 		alarm(number(value(DIALTIMEOUT)));
116 		read(FD, &c, 1);
117 		c &= 0177;
118 		alarm(0);
119 #ifdef notdef
120 		if (boolean(value(VERBOSE)))
121 			putchar(c);
122 #endif
123 		if (timeout)
124 			return (0);
125 	} while (c != '\n' && c != s);
126 	signal(SIGALRM, SIG_DFL);
127 	return (c == s);
128 }
129 
130 #define min(a,b)	((a)>(b)?(b):(a))
131 /*
132  * This convoluted piece of code attempts to get
133  * the ventel in sync.  If you don't have the capacity or nread
134  * call there are gory ways to simulate this.
135  */
136 static int
137 vensync(fd)
138 {
139 	long nread;
140 	register int already = 0, nbytes;
141 	char buf[60];
142 
143 	/*
144 	 * Toggle DTR to force anyone off that might have left
145 	 * the modem connected, and insure a consistent state
146 	 * to start from.
147 	 *
148 	 * If you don't have the ioctl calls to diddle directly
149 	 * with DTR, you can always try setting the baud rate to 0.
150 	 */
151 	ioctl(FD, TIOCCDTR, 0);
152 	sleep(2);
153 	ioctl(FD, TIOCSDTR, 0);
154 	while (already < MAXRETRY) {
155 		/*
156 		 * After reseting the modem, send it two \r's to
157 		 * autobaud on. Make sure to delay between them
158 		 * so the modem can frame the incoming characters.
159 		 */
160 		write(fd, "\r", 1);
161 		sleep(1);
162 		write(fd, "\r", 1);
163 		sleep(3);
164 		if (ioctl(fd, FIONREAD, (caddr_t)&nread) >= 0) {
165 			nbytes = nread;
166 			while (nbytes > 0) {
167 				read(fd, buf, min(nbytes, 60));
168 				if ((buf[nbytes-1]&0177) == '$')
169 					return (1);
170 				nbytes -= min(nbytes, 60);
171 			}
172 			sleep(1);
173 			already++;
174 		}
175 	}
176 	return (0);
177 }
178 #endif
179