xref: /original-bsd/usr.bin/tip/aculib/v831.c (revision 5656414f)
1 /*
2  * Copyright (c) 1983 The Regents of the University of California.
3  * All rights reserved.
4  *
5  * %sccs.include.redist.c%
6  */
7 
8 #ifndef lint
9 static char sccsid[] = "@(#)v831.c	5.3 (Berkeley) 06/01/90";
10 #endif /* not lint */
11 
12 /*
13  * Routines for dialing up on Vadic 831
14  */
15 #include <sys/time.h>
16 
17 #include "tip.h"
18 
19 int	v831_abort();
20 static	int alarmtr();
21 extern	errno;
22 
23 static jmp_buf jmpbuf;
24 static int child = -1;
25 
26 v831_dialer(num, acu)
27         char *num, *acu;
28 {
29         int status, pid, connected = 1;
30         register int timelim;
31 
32         if (boolean(value(VERBOSE)))
33                 printf("\nstarting call...");
34 #ifdef DEBUG
35         printf ("(acu=%s)\n", acu);
36 #endif
37         if ((AC = open(acu, O_RDWR)) < 0) {
38                 if (errno == EBUSY)
39                         printf("line busy...");
40                 else
41                         printf("acu open error...");
42                 return (0);
43         }
44         if (setjmp(jmpbuf)) {
45                 kill(child, SIGKILL);
46                 close(AC);
47                 return (0);
48         }
49         signal(SIGALRM, alarmtr);
50         timelim = 5 * strlen(num);
51         alarm(timelim < 30 ? 30 : timelim);
52         if ((child = fork()) == 0) {
53                 /*
54                  * ignore this stuff for aborts
55                  */
56                 signal(SIGALRM, SIG_IGN);
57 		signal(SIGINT, SIG_IGN);
58                 signal(SIGQUIT, SIG_IGN);
59                 sleep(2);
60                 exit(dialit(num, acu) != 'A');
61         }
62         /*
63          * open line - will return on carrier
64          */
65         if ((FD = open(DV, O_RDWR)) < 0) {
66 #ifdef DEBUG
67                 printf("(after open, errno=%d)\n", errno);
68 #endif
69                 if (errno == EIO)
70                         printf("lost carrier...");
71                 else
72                         printf("dialup line open failed...");
73                 alarm(0);
74                 kill(child, SIGKILL);
75                 close(AC);
76                 return (0);
77         }
78         alarm(0);
79 #ifdef notdef
80         ioctl(AC, TIOCHPCL, 0);
81 #endif
82         signal(SIGALRM, SIG_DFL);
83         while ((pid = wait(&status)) != child && pid != -1)
84                 ;
85         if (status) {
86                 close(AC);
87                 return (0);
88         }
89         return (1);
90 }
91 
92 static
93 alarmtr()
94 {
95 
96         alarm(0);
97         longjmp(jmpbuf, 1);
98 }
99 
100 /*
101  * Insurance, for some reason we don't seem to be
102  *  hanging up...
103  */
104 v831_disconnect()
105 {
106         struct sgttyb cntrl;
107 
108         sleep(2);
109 #ifdef DEBUG
110         printf("[disconnect: FD=%d]\n", FD);
111 #endif
112         if (FD > 0) {
113                 ioctl(FD, TIOCCDTR, 0);
114                 ioctl(FD, TIOCGETP, &cntrl);
115                 cntrl.sg_ispeed = cntrl.sg_ospeed = 0;
116                 ioctl(FD, TIOCSETP, &cntrl);
117                 ioctl(FD, TIOCNXCL, (struct sgttyb *)NULL);
118         }
119         close(FD);
120 }
121 
122 v831_abort()
123 {
124 
125 #ifdef DEBUG
126         printf("[abort: AC=%d]\n", AC);
127 #endif
128         sleep(2);
129         if (child > 0)
130                 kill(child, SIGKILL);
131         if (AC > 0)
132                 ioctl(FD, TIOCNXCL, (struct sgttyb *)NULL);
133                 close(AC);
134         if (FD > 0)
135                 ioctl(FD, TIOCCDTR, 0);
136         close(FD);
137 }
138 
139 /*
140  * Sigh, this probably must be changed at each site.
141  */
142 struct vaconfig {
143 	char	*vc_name;
144 	char	vc_rack;
145 	char	vc_modem;
146 } vaconfig[] = {
147 	{ "/dev/cua0",'4','0' },
148 	{ "/dev/cua1",'4','1' },
149 	{ 0 }
150 };
151 
152 #define pc(x)	(c = x, write(AC,&c,1))
153 #define ABORT	01
154 #define SI	017
155 #define STX	02
156 #define ETX	03
157 
158 static
159 dialit(phonenum, acu)
160 	register char *phonenum;
161 	char *acu;
162 {
163         register struct vaconfig *vp;
164 	struct sgttyb cntrl;
165         char c, *sanitize();
166         int i, two = 2;
167 
168         phonenum = sanitize(phonenum);
169 #ifdef DEBUG
170         printf ("(dial phonenum=%s)\n", phonenum);
171 #endif
172         if (*phonenum == '<' && phonenum[1] == 0)
173                 return ('Z');
174 	for (vp = vaconfig; vp->vc_name; vp++)
175 		if (strcmp(vp->vc_name, acu) == 0)
176 			break;
177 	if (vp->vc_name == 0) {
178 		printf("Unable to locate dialer (%s)\n", acu);
179 		return ('K');
180 	}
181         ioctl(AC, TIOCGETP, &cntrl);
182         cntrl.sg_ispeed = cntrl.sg_ospeed = B2400;
183         cntrl.sg_flags = RAW | EVENP | ODDP;
184         ioctl(AC, TIOCSETP, &cntrl);
185 	ioctl(AC, TIOCFLUSH, &two);
186         pc(STX);
187 	pc(vp->vc_rack);
188 	pc(vp->vc_modem);
189 	while (*phonenum && *phonenum != '<')
190 		pc(*phonenum++);
191         pc(SI);
192 	pc(ETX);
193         sleep(1);
194         i = read(AC, &c, 1);
195 #ifdef DEBUG
196         printf("read %d chars, char=%c, errno %d\n", i, c, errno);
197 #endif
198         if (i != 1)
199 		c = 'M';
200         if (c == 'B' || c == 'G') {
201                 char cc, oc = c;
202 
203                 pc(ABORT);
204                 read(AC, &cc, 1);
205 #ifdef DEBUG
206                 printf("abort response=%c\n", cc);
207 #endif
208                 c = oc;
209                 v831_disconnect();
210         }
211         close(AC);
212 #ifdef DEBUG
213         printf("dialit: returns %c\n", c);
214 #endif
215         return (c);
216 }
217 
218 static char *
219 sanitize(s)
220 	register char *s;
221 {
222         static char buf[128];
223         register char *cp;
224 
225         for (cp = buf; *s; s++) {
226 		if (!isdigit(*s) && *s == '<' && *s != '_')
227 			continue;
228 		if (*s == '_')
229 			*s = '=';
230 		*cp++ = *s;
231 	}
232         *cp++ = 0;
233         return (buf);
234 }
235