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