|
|
1.1 root 1: #include <sgtty.h>
2: #include <signal.h>
3: #include <errno.h>
4: #include <stdio.h>
5: #include <sys/types.h>
6: #include <sys/stat.h>
7: #include <pwd.h>
8:
9: #define ACUFILE1 "/usr/lib/aculist"
10: #define ACUFILE "/etc/aculist"
11: #undef DKACU
12:
13: char *malloc();
14: char *word();
15: struct aculine *readacu();
16:
17: struct aculine {
18: char *class;
19: char *line;
20: char *acu;
21: char *speed;
22: char *prefix;
23: char *postfix;
24: };
25:
26: #define MONITOR
27: #define eq(x, y) (strcmp(x, y)==0)
28:
29: extern int dt_ld;
30: extern int tty_ld;
31: extern int buf_ld;
32:
33: dialout(telno, type)
34: char *telno, *type;
35: {
36: char digits[30];
37: register struct aculine *ap;
38: int pid, dh, retval, r, acu;
39: int sigalrm(), (*sal)();
40: time_t starttime, time();
41: struct sgttyb vec;
42:
43: sal = signal(SIGALRM, sigalrm);
44: alarm(0);
45: dh = -1;
46: retval = -9; /* unknown service class */
47: ap = readacu();
48: if (ap == NULL)
49: return(retval);
50: for (; ap->class; ap++) {
51: #ifdef DEBUG
52: printf("class %s, line %s, acu %s, speed %s, prefix %s, postfix %s\n",
53: ap->class, ap->line, ap->acu, ap->speed, ap->prefix, ap->postfix);
54: #endif
55: if(!eq(ap->class, type))
56: continue;
57: acu = -1;
58: if (eq(ap->acu, "none"))
59: goto noACU;
60: retval = -1; /* acu busy */
61: if (eq(ap->line, "DKVENTEL") || eq(ap->line, "DKACU")){
62: retval = tdkdialout(ap->acu, telno, type);
63: if(retval >= 0)
64: break;
65: continue;
66: }
67: for (r=0; r<60; r += 3) {
68: acu = open(ap->acu, 1);
69: if (acu<0 && !eq(ap->prefix, "-")) {
70: sleep(3);
71: continue;
72: }
73: break;
74: }
75: if (acu < 0)
76: continue;
77: digits[0] = '\0';
78: if (!eq(ap->prefix, "-"))
79: strcpy(digits, ap->prefix);
80: strcat(digits, telno);
81: strcat(digits, ap->postfix);
82: if ((pid=fork())==0) {
83: alarm(60);
84: close(acu);
85: dh = open(ap->line, 2);
86: exit(0);
87: }
88: alarm(20);
89: #ifdef DEBUG
90: printf("dial %s\n", digits);
91: #endif
92: r = write(acu, digits, strlen(digits));
93: #ifdef DEBUG
94: printf("wrote %d\n", r);
95: #endif
96: alarm(0);
97: close(acu);
98: if (r!=strlen(digits)) {
99: kill(pid, 9);
100: wait(0);
101: continue;
102: }
103: noACU:
104: alarm(60);
105: starttime = time(NULL);
106: retval = -3; /* no carrier */
107: dh = open(ap->line, 2);
108: #ifdef DEBUG
109: printf("open %s\n", ap->line);
110: #endif
111: alarm(0);
112: kill(pid, 9);
113: wait(0);
114: if (dh>=0) {
115: #ifdef DEBUG
116: printf("open succeeds\n");
117: #endif
118: retval = dh;
119: break;
120: }
121: close(acu); /* This compensates for a system bug. */
122: #ifdef DEBUG
123: printf("open failed\n");
124: #endif
125: if (time(NULL) > starttime+45) /* quit if timeout */
126: break;
127: }
128: ret:
129: if (retval > 0) {
130: int ld;
131:
132: ioctl(retval, FIOPUSHLD, &buf_ld);
133: ld = ioctl(retval, FIOLOOKLD, (char *)0);
134: if (ld != tty_ld)
135: ioctl(retval, FIOPUSHLD, &tty_ld);
136: ioctl(retval, TIOCGETP, &vec);
137: vec.sg_flags &= ~ECHO;
138: vec.sg_flags |= RAW|EVENP|ODDP;
139: vec.sg_ispeed = vec.sg_ospeed = getspeed(ap->speed);
140: ioctl(retval, TIOCSETP, &vec);
141: ioctl(retval, TIOCHPCL, 0);
142: ioctl(retval, TIOCEXCL, 0);
143: if (vec.sg_ispeed == 0) {
144: close(retval);
145: retval = -3;
146: }
147: }
148: signal(SIGALRM, sal);
149: recordit(type, telno, retval);
150: return(retval);
151: }
152:
153: static
154: sigalrm()
155: {
156: signal(SIGALRM, sigalrm);
157: return;
158: }
159:
160: static struct aculine *
161: readacu()
162: {
163: char *ap;
164: int nline, i, f;
165: struct stat sb;
166: struct aculine *acp;
167:
168: if ((f = open(ACUFILE, 0)) < 0){
169: if((f = open(ACUFILE1, 0)) < 0){
170: return(NULL);
171: }
172: }
173: fstat(f, &sb);
174: ap = malloc(2*(unsigned short)sb.st_size);
175: if (ap == NULL)
176: return(NULL);
177: i = read(f, ap, (unsigned short)sb.st_size);
178: close(f);
179: if (i < 0)
180: i = 0;
181: ap[i] = '\0';
182: for (nline=0, i=0; ap[i]; i++)
183: if (ap[i] == '\n')
184: nline++;
185: acp = (struct aculine *)malloc(2*(nline+1)*sizeof(struct aculine));
186: if (acp == NULL)
187: return(NULL);
188: for (i=0; i<nline; i++) {
189: ap = word(ap, &acp[i].class, 1);
190: ap = word(ap, &acp[i].line, 0);
191: ap = word(ap, &acp[i].acu, 0);
192: ap = word(ap, &acp[i].speed, 0);
193: ap = word(ap, &acp[i].prefix, 0);
194: ap = word(ap, &acp[i].postfix, 0);
195: }
196: acp[nline].class = NULL;
197: *ap = '\0';
198:
199: return(acp);
200: }
201:
202: static char *
203: word(cp, loc, f)
204: register char *cp, **loc;
205: {
206: register char *bw;
207:
208: while (*cp == ' ' || *cp == '\t' || (*cp == '\n' && f))
209: *cp++ = '\0';
210: bw = cp;
211: while (*cp > ' ')
212: cp++;
213: *loc = bw;
214: return(cp);
215: }
216:
217: static
218: getspeed(sp)
219: char *sp;
220: {
221: switch(atoi(sp)) {
222:
223: case 50:
224: return(B50);
225: case 75:
226: return(B75);
227: case 110:
228: return(B110);
229: case 134:
230: return(B134);
231: case 150:
232: return(B150);
233: case 300:
234: return(B300);
235: case 600:
236: return(B600);
237: case 1200:
238: return(B1200);
239: case 1800:
240: return(B1800);
241: case 2400:
242: return(B2400);
243: case 4800:
244: return(B4800);
245: case 9600:
246: return(B9600);
247: default:
248: if (eq(sp, "exta"))
249: return(EXTA);
250: if (eq(sp, "extb"))
251: return(EXTB);
252: return(0);
253: }
254: }
255:
256: static
257: recordit(class, telno, retval)
258: char *class, *telno;
259: {
260: FILE *fp;
261: long time();
262: long tm = time(0);
263: struct passwd *pwp, *getpwuid();
264:
265: fp = fopen("/usr/adm/smdr", "a");
266: if (fp == NULL)
267: return(0);
268: pwp = getpwuid(geteuid());
269: fprintf(fp, "%s %s %s %s %.12s\n", telno, class, retval>=0?"OK":"NG",
270: pwp?pwp->pw_name:"?", ctime(&tm)+4);
271: fclose(fp);
272: }
273:
274: #ifdef DKACU
275: #include <dk.h>
276: #include <ctype.h>
277:
278: tdkdialout(addr, telno, dt)
279: char *addr;
280: char *telno, *dt;
281: {
282: char atelno[100];
283: char buf[100];
284: int fd, i;
285:
286: for(i = 0; telno[i]; i++){
287: if(telno[i] == '-'){
288: atelno[i] = '%';
289: } else if(telno[i] == '='){
290: atelno[i] = '%';
291: } else if(telno[i] == '+'){
292: atelno[i] = '&';
293: } else {
294: atelno[i] = telno[i];
295: }
296: }
297: atelno[i] = '\0';
298: if(dt[0] == 'C' && atelno[0] != '9' && atelno[0] != '8'){
299: /* C1200 or C300; ventel is on dimension, not centrex */
300: return(-9);
301: }
302: sprintf(buf, "%s.%s", addr, atelno);
303: /* tdkdial times out itself */
304: /* the 3 means wait for a meaningful answer */
305: fd = _tdkdial(3, 0, buf);
306: if(fd < 0)
307: return(-3);
308: if (dkproto(fd, dt_ld) < 0)
309: return(-1);
310: return(fd);
311: }
312: #else
313: tdkdialout(addr, telno, dt)
314: char *addr;
315: char *telno, *dt;
316: {
317: return(-1);
318: }
319: #endif DKACU
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.