|
|
1.1 root 1: /*
2: * Copyright (c) 1983 The Regents of the University of California.
3: * All rights reserved.
4: *
5: * Redistribution and use in source and binary forms are permitted
6: * provided that: (1) source distributions retain this entire copyright
7: * notice and comment, and (2) distributions including binaries display
8: * the following acknowledgement: ``This product includes software
9: * developed by the University of California, Berkeley and its contributors''
10: * in the documentation or other materials provided with the distribution
11: * and in all advertising materials mentioning features or use of this
12: * software. Neither the name of the University nor the names of its
13: * contributors may be used to endorse or promote products derived
14: * from this software without specific prior written permission.
15: * THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR
16: * IMPLIED WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED
17: * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.
18: */
19:
20: #ifndef lint
21: static char sccsid[] = "@(#)ventel.c 5.3 (Berkeley) 6/1/90";
22: #endif /* not lint */
23:
24: /*
25: * Routines for calling up on a Ventel Modem
26: * The Ventel is expected to be strapped for local echo (just like uucp)
27: */
28: #include "tip.h"
29:
30: #define MAXRETRY 5
31:
32: static int sigALRM();
33: static int timeout = 0;
34: static jmp_buf timeoutbuf;
35:
36: /*
37: * some sleep calls have been replaced by this macro
38: * because some ventel modems require two <cr>s in less than
39: * a second in order to 'wake up'... yes, it is dirty...
40: */
41: #define delay(num,denom) busyloop(CPUSPEED*num/denom)
42: #define CPUSPEED 1000000 /* VAX 780 is 1MIPS */
43: #define DELAY(n) { register long N = (n); while (--N > 0); }
44: busyloop(n) { DELAY(n); }
45:
46: ven_dialer(num, acu)
47: register char *num;
48: char *acu;
49: {
50: register char *cp;
51: register int connected = 0;
52: char *msg, *index(), line[80];
53:
54: /*
55: * Get in synch with a couple of carriage returns
56: */
57: if (!vensync(FD)) {
58: printf("can't synchronize with ventel\n");
59: #ifdef ACULOG
60: logent(value(HOST), num, "ventel", "can't synch up");
61: #endif
62: return (0);
63: }
64: if (boolean(value(VERBOSE)))
65: printf("\ndialing...");
66: fflush(stdout);
67: ioctl(FD, TIOCHPCL, 0);
68: echo("#k$\r$\n$D$I$A$L$:$ ");
69: for (cp = num; *cp; cp++) {
70: delay(1, 10);
71: write(FD, cp, 1);
72: }
73: delay(1, 10);
74: write(FD, "\r", 1);
75: gobble('\n', line);
76: if (gobble('\n', line))
77: connected = gobble('!', line);
78: ioctl(FD, TIOCFLUSH);
79: #ifdef ACULOG
80: if (timeout) {
81: sprintf(line, "%d second dial timeout",
82: number(value(DIALTIMEOUT)));
83: logent(value(HOST), num, "ventel", line);
84: }
85: #endif
86: if (timeout)
87: ven_disconnect(); /* insurance */
88: if (connected || timeout || !boolean(value(VERBOSE)))
89: return (connected);
90: /* call failed, parse response for user */
91: cp = index(line, '\r');
92: if (cp)
93: *cp = '\0';
94: for (cp = line; cp = index(cp, ' '); cp++)
95: if (cp[1] == ' ')
96: break;
97: if (cp) {
98: while (*cp == ' ')
99: cp++;
100: msg = cp;
101: while (*cp) {
102: if (isupper(*cp))
103: *cp = tolower(*cp);
104: cp++;
105: }
106: printf("%s...", msg);
107: }
108: return (connected);
109: }
110:
111: ven_disconnect()
112: {
113:
114: close(FD);
115: }
116:
117: ven_abort()
118: {
119:
120: write(FD, "\03", 1);
121: close(FD);
122: }
123:
124: static int
125: echo(s)
126: register char *s;
127: {
128: char c;
129:
130: while (c = *s++) switch (c) {
131:
132: case '$':
133: read(FD, &c, 1);
134: s++;
135: break;
136:
137: case '#':
138: c = *s++;
139: write(FD, &c, 1);
140: break;
141:
142: default:
143: write(FD, &c, 1);
144: read(FD, &c, 1);
145: }
146: }
147:
148: static int
149: sigALRM()
150: {
151:
152: printf("\07timeout waiting for reply\n");
153: timeout = 1;
154: longjmp(timeoutbuf, 1);
155: }
156:
157: static int
158: gobble(match, response)
159: register char match;
160: char response[];
161: {
162: register char *cp = response;
163: char c;
164: int (*f)();
165:
166: signal(SIGALRM, sigALRM);
167: timeout = 0;
168: do {
169: if (setjmp(timeoutbuf)) {
170: signal(SIGALRM, f);
171: *cp = '\0';
172: return (0);
173: }
174: alarm(number(value(DIALTIMEOUT)));
175: read(FD, cp, 1);
176: alarm(0);
177: c = (*cp++ &= 0177);
178: #ifdef notdef
179: if (boolean(value(VERBOSE)))
180: putchar(c);
181: #endif
182: } while (c != '\n' && c != match);
183: signal(SIGALRM, SIG_DFL);
184: *cp = '\0';
185: return (c == match);
186: }
187:
188: #define min(a,b) ((a)>(b)?(b):(a))
189: /*
190: * This convoluted piece of code attempts to get
191: * the ventel in sync. If you don't have FIONREAD
192: * there are gory ways to simulate this.
193: */
194: static int
195: vensync(fd)
196: {
197: int already = 0, nread;
198: char buf[60];
199:
200: /*
201: * Toggle DTR to force anyone off that might have left
202: * the modem connected, and insure a consistent state
203: * to start from.
204: *
205: * If you don't have the ioctl calls to diddle directly
206: * with DTR, you can always try setting the baud rate to 0.
207: */
208: ioctl(FD, TIOCCDTR, 0);
209: sleep(1);
210: ioctl(FD, TIOCSDTR, 0);
211: while (already < MAXRETRY) {
212: /*
213: * After reseting the modem, send it two \r's to
214: * autobaud on. Make sure to delay between them
215: * so the modem can frame the incoming characters.
216: */
217: write(fd, "\r", 1);
218: delay(1,10);
219: write(fd, "\r", 1);
220: sleep(2);
221: if (ioctl(fd, FIONREAD, (caddr_t)&nread) < 0) {
222: perror("tip: ioctl");
223: continue;
224: }
225: while (nread > 0) {
226: read(fd, buf, min(nread, 60));
227: if ((buf[nread - 1] & 0177) == '$')
228: return (1);
229: nread -= min(nread, 60);
230: }
231: sleep(1);
232: already++;
233: }
234: return (0);
235: }
236:
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.