|
|
1.1 ! root 1: #ifndef lint ! 2: static char sccsid[] = "@(#)acucntrl.c 5.15 (Berkeley) 5/4/88"; ! 3: #endif ! 4: ! 5: /* acucntrl - turn around tty line between dialin and dialout ! 6: * ! 7: * Usage: acucntrl {enable,disable} /dev/ttydX ! 8: * ! 9: * History: ! 10: * First written by Allan Wilkes (fisher!allan) ! 11: * ! 12: * Modified June 8,1983 by W.Sebok (astrovax!wls) to poke kernel rather ! 13: * than use kernel hack to turn on/off modem control, using subroutine ! 14: * stolen from program written by Tsutomu Shimomura ! 15: * {astrovax,escher}!tsutomu ! 16: * ! 17: * Worked over many times by W.Sebok (i.e. hacked to death) ! 18: * ! 19: * Operation: ! 20: * disable (i.e. setup for dialing out) ! 21: * (1) check input arguments ! 22: * (2) look in /etc/utmp to check that the line is not in use by another ! 23: * (3) disable modem control on terminal ! 24: * (4) check for carrier on device ! 25: * (5) change owner of device to real id ! 26: * (6) edit /etc/ttys, changing the first character of the appropriate ! 27: * line to 0 ! 28: * (7) send a hangup to process 1 to poke init to disable getty ! 29: * (8) post uid name in capitals in /etc/utmp to let world know device has ! 30: * been grabbed ! 31: * (9) make sure that DTR is on ! 32: * ! 33: * enable (i.e.) restore for dialin ! 34: * (1) check input arguments ! 35: * (2) look in /etc/utmp to check that the line is not in use by another ! 36: * (3) make sure modem control on terminal is disabled ! 37: * (4) turn off DTR to make sure line is hung up ! 38: * (5) condition line: clear exclusive use and set hangup on close modes ! 39: * (6) turn on modem control ! 40: * (7) edit /etc/ttys, changing the first character of the appropriate ! 41: * line to 1 ! 42: * (8) send a hangup to process 1 to poke init to enable getty ! 43: * (9) clear uid name for /etc/utmp ! 44: */ ! 45: ! 46: /* #define SENSECARRIER */ ! 47: ! 48: #include "uucp.h" ! 49: #ifdef DIALINOUT ! 50: #include <sys/buf.h> ! 51: #include <signal.h> ! 52: #include <sys/conf.h> ! 53: #ifdef vax ! 54: #ifdef BSD4_2 ! 55: #include <vaxuba/ubavar.h> ! 56: #else ! 57: #include <sys/ubavar.h> ! 58: #endif ! 59: #endif /* vax */ ! 60: #include <sys/stat.h> ! 61: #include <nlist.h> ! 62: #include <sgtty.h> ! 63: #include <utmp.h> ! 64: #include <pwd.h> ! 65: #include <stdio.h> ! 66: #include <sys/file.h> ! 67: ! 68: #define NDZLINE 8 /* lines/dz */ ! 69: #define NDHLINE 16 /* lines/dh */ ! 70: #define NDMFLINE 8 /* lines/dmf */ ! 71: ! 72: #define DZ11 1 ! 73: #define DH11 2 ! 74: #define DMF 3 ! 75: ! 76: #define NLVALUE(val) (nl[val].n_value) ! 77: ! 78: struct nlist nl[] = { ! 79: #define CDEVSW 0 ! 80: { "_cdevsw" }, ! 81: ! 82: #define DZOPEN 1 ! 83: { "_dzopen" }, ! 84: #define DZINFO 2 ! 85: { "_dzinfo" }, ! 86: #define NDZ11 3 ! 87: { "_dz_cnt" }, ! 88: #define DZSCAR 4 ! 89: { "_dzsoftCAR" }, ! 90: ! 91: #define DHOPEN 5 ! 92: { "_dhopen" }, ! 93: #define DHINFO 6 ! 94: { "_dhinfo" }, ! 95: #define NDH11 7 ! 96: { "_ndh11" }, ! 97: #define DHSCAR 8 ! 98: { "_dhsoftCAR" }, ! 99: ! 100: #define DMFOPEN 9 ! 101: { "_dmfopen" }, ! 102: #define DMFINFO 10 ! 103: { "_dmfinfo" }, ! 104: #define NDMF 11 ! 105: { "_ndmf" }, ! 106: #define DMFSCAR 12 ! 107: { "_dmfsoftCAR" }, ! 108: ! 109: { "\0" } ! 110: }; ! 111: ! 112: #define ENABLE 1 ! 113: #define DISABLE 0 ! 114: ! 115: char Etcutmp[] = "/etc/utmp"; ! 116: char Etcttys[] = "/etc/ttys"; ! 117: #ifdef BSD4_3 ! 118: FILE *ttysfile, *nttysfile; ! 119: char NEtcttys[] = "/etc/ttys.new"; ! 120: extern long ftell(); ! 121: #endif BSD4_3 ! 122: char Devhome[] = "/dev"; ! 123: ! 124: char usage[] = "Usage: acucntrl {dis|en}able ttydX\n"; ! 125: ! 126: struct utmp utmp; ! 127: char resettty, resetmodem; ! 128: int etcutmp; ! 129: off_t utmploc; ! 130: off_t ttyslnbeg; ! 131: extern int errno; ! 132: extern char *sys_errlist[]; ! 133: off_t lseek(); ! 134: ! 135: #define NAMSIZ sizeof(utmp.ut_name) ! 136: #define LINSIZ sizeof(utmp.ut_line) ! 137: ! 138: main(argc, argv) ! 139: int argc; char *argv[]; ! 140: { ! 141: register char *p; ! 142: register int i; ! 143: char uname[NAMSIZ], Uname[NAMSIZ]; ! 144: int enable ; ! 145: char *device; ! 146: int devfile; ! 147: int uid, gid; ! 148: struct passwd *getpwuid(); ! 149: char *rindex(); ! 150: ! 151: /* check input arguments */ ! 152: if (argc!=3 && argc != 4) { ! 153: fprintf(stderr, usage); ! 154: exit(1); ! 155: } ! 156: ! 157: /* interpret command type */ ! 158: if (prefix(argv[1], "disable") || strcmp(argv[1], "dialout")==0) ! 159: enable = 0; ! 160: else if (prefix(argv[1], "enable") || strcmp(argv[1], "dialin")==0) ! 161: enable = 1; ! 162: else { ! 163: fprintf(stderr, usage); ! 164: exit(1); ! 165: } ! 166: ! 167: device = rindex(argv[2], '/'); ! 168: device = (device == NULL) ? argv[2]: device+1; ! 169: ! 170: opnttys(device); ! 171: ! 172: #ifdef vax ! 173: /* Get nlist info */ ! 174: nlist("/vmunix", nl); ! 175: #endif vax ! 176: ! 177: /* Chdir to /dev */ ! 178: if(chdir(Devhome) < 0) { ! 179: fprintf(stderr, "Cannot chdir to %s: %s\r\n", ! 180: Devhome, sys_errlist[errno]); ! 181: exit(1); ! 182: } ! 183: ! 184: /* Get uid information */ ! 185: uid = getuid(); ! 186: gid = getgid(); ! 187: ! 188: p = getpwuid(uid)->pw_name; ! 189: if (p==NULL) { ! 190: fprintf(stderr, "cannot get uid name\n"); ! 191: exit(1); ! 192: } ! 193: ! 194: if (strcmp(p, "uucp") == 0 && argc == 4) ! 195: p = argv[3]; ! 196: ! 197: /* to upper case */ ! 198: i = 0; ! 199: do { ! 200: uname[i] = *p; ! 201: Uname[i++] = (*p>='a' && *p<='z') ? (*p - ('a'-'A')) : *p; ! 202: } while (*p++ && i<NAMSIZ); ! 203: ! 204: /* check to see if line is being used */ ! 205: if( (etcutmp = open(Etcutmp, 2)) < 0) { ! 206: fprintf(stderr, "On open %s open: %s\n", ! 207: Etcutmp, sys_errlist[errno]); ! 208: exit(1); ! 209: } ! 210: ! 211: (void)lseek(etcutmp, utmploc, 0); ! 212: ! 213: i = read(etcutmp, (char *)&utmp, sizeof(struct utmp)); ! 214: ! 215: if( ! 216: i == sizeof(struct utmp) && ! 217: utmp.ut_line[0] != '\0' && ! 218: utmp.ut_name[0] != '\0' && ! 219: ( ! 220: !upcase(utmp.ut_name, NAMSIZ) || ! 221: ( ! 222: uid != 0 && ! 223: strncmp(utmp.ut_name, Uname, NAMSIZ) != 0 ! 224: ) ! 225: ) ! 226: ) { ! 227: fprintf(stderr, "%s in use by %s\n", device, utmp.ut_name); ! 228: exit(2); ! 229: } ! 230: ! 231: #ifndef sequent ! 232: /* Disable modem control */ ! 233: if (setmodem(device, DISABLE) < 0) { ! 234: fprintf(stderr, "Unable to disable modem control\n"); ! 235: exit(1); ! 236: } ! 237: #endif !sequent ! 238: ! 239: if (enable) { ! 240: #ifdef sequent ! 241: if (setmodem(device, ENABLE) < 0) { ! 242: fprintf(stderr, "Cannot Enable modem control\n"); ! 243: (void)setmodem(device, i); ! 244: exit(1); ! 245: } ! 246: #endif sequent ! 247: #ifndef sequent ! 248: if((devfile = open(device, 1)) < 0) { ! 249: fprintf(stderr, "On open of %s: %s\n", ! 250: device, sys_errlist[errno]); ! 251: (void)setmodem(device, resetmodem); ! 252: exit(1); ! 253: } ! 254: /* Try one last time to hang up */ ! 255: if (ioctl(devfile, (int)TIOCCDTR, (char *)0) < 0) ! 256: fprintf(stderr, "On TIOCCDTR ioctl: %s\n", ! 257: sys_errlist[errno]); ! 258: ! 259: if (ioctl(devfile, (int)TIOCNXCL, (char *)0) < 0) ! 260: fprintf(stderr, ! 261: "Cannot clear Exclusive Use on %s: %s\n", ! 262: device, sys_errlist[errno]); ! 263: ! 264: if (ioctl(devfile, (int)TIOCHPCL, (char *)0) < 0) ! 265: fprintf(stderr, ! 266: "Cannot set hangup on close on %s: %s\n", ! 267: device, sys_errlist[errno]); ! 268: ! 269: #endif !sequent ! 270: i = resetmodem; ! 271: ! 272: #ifndef sequent ! 273: if (setmodem(device, ENABLE) < 0) { ! 274: fprintf(stderr, "Cannot Enable modem control\n"); ! 275: (void)setmodem(device, i); ! 276: exit(1); ! 277: } ! 278: #endif sequent ! 279: resetmodem=i; ! 280: ! 281: if (settys(ENABLE)) { ! 282: fprintf(stderr, "%s already enabled\n", device); ! 283: } else { ! 284: pokeinit(device, Uname, enable); ! 285: } ! 286: post(device, ""); ! 287: ! 288: } else { ! 289: #if defined(TIOCMGET) && defined(SENSECARRIER) ! 290: if (uid!=0) { ! 291: int linestat = 0; ! 292: ! 293: /* check for presence of carrier */ ! 294: sleep(2); /* need time after modem control turnoff */ ! 295: ! 296: if((devfile = open(device, 1)) < 0) { ! 297: fprintf(stderr, "On open of %s: %s\n", ! 298: device, sys_errlist[errno]); ! 299: (void)setmodem(device, resetmodem); ! 300: exit(1); ! 301: } ! 302: ! 303: (void)ioctl(devfile, TIOCMGET, &linestat); ! 304: ! 305: if (linestat&TIOCM_CAR) { ! 306: fprintf(stderr, "%s is in use (Carrier On)\n", ! 307: device); ! 308: (void)setmodem(device, resetmodem); ! 309: exit(2); ! 310: } ! 311: (void)close(devfile); ! 312: } ! 313: #endif TIOCMGET ! 314: /* chown device */ ! 315: if(chown(device, uid, gid) < 0) ! 316: fprintf(stderr, "Cannot chown %s: %s\n", ! 317: device, sys_errlist[errno]); ! 318: ! 319: ! 320: /* poke init */ ! 321: if(settys(DISABLE)) { ! 322: fprintf(stderr, "%s already disabled\n", device); ! 323: } else { ! 324: pokeinit(device, Uname, enable); ! 325: } ! 326: post(device, Uname); ! 327: #ifdef sequent ! 328: /* Disable modem control */ ! 329: if (setmodem(device, DISABLE) < 0) { ! 330: fprintf(stderr, "Unable to disable modem control\n"); ! 331: exit(1); ! 332: } ! 333: #endif sequent ! 334: if((devfile = open(device, O_RDWR|O_NDELAY)) < 0) { ! 335: fprintf(stderr, "On %s open: %s\n", ! 336: device, sys_errlist[errno]); ! 337: } else { ! 338: if(ioctl(devfile, (int)TIOCSDTR, (char *)0) < 0) ! 339: fprintf(stderr, ! 340: "Cannot set DTR on %s: %s\n", ! 341: device, sys_errlist[errno]); ! 342: } ! 343: } ! 344: ! 345: exit(0); ! 346: } ! 347: ! 348: /* return true if no lower case */ ! 349: upcase(str, len) ! 350: register char *str; ! 351: register int len; ! 352: { ! 353: for (; *str, --len >= 0 ; str++) ! 354: if (*str>='a' && *str<='z') ! 355: return(0); ! 356: return(1); ! 357: } ! 358: ! 359: /* Post name to public */ ! 360: post(device, name) ! 361: char *device, *name; ! 362: { ! 363: (void)time((time_t *)&utmp.ut_time); ! 364: strncpy(utmp.ut_line, device, LINSIZ); ! 365: strncpy(utmp.ut_name, name, NAMSIZ); ! 366: if (lseek(etcutmp, utmploc, 0) < 0) ! 367: fprintf(stderr, "on lseek in /etc/utmp: %s", ! 368: sys_errlist[errno]); ! 369: if (write(etcutmp, (char *)&utmp, sizeof(utmp)) < 0) ! 370: fprintf(stderr, "on write in /etc/utmp: %s", ! 371: sys_errlist[errno]); ! 372: } ! 373: ! 374: /* poke process 1 and wait for it to do its thing */ ! 375: pokeinit(device, uname, enable) ! 376: char *uname, *device; int enable; ! 377: { ! 378: struct utmp utmp; ! 379: register int i; ! 380: ! 381: post(device, uname); ! 382: ! 383: /* poke init */ ! 384: if (kill(1, SIGHUP)) { ! 385: fprintf(stderr, ! 386: "Cannot send hangup to init process: %s\n", ! 387: sys_errlist[errno]); ! 388: (void)settys(resettty); ! 389: (void)setmodem(device, resetmodem); ! 390: exit(1); ! 391: } ! 392: ! 393: if (enable) ! 394: return; ! 395: ! 396: /* wait till init has responded, clearing the utmp entry */ ! 397: i = 100; ! 398: do { ! 399: sleep(1); ! 400: if (lseek(etcutmp, utmploc, 0) < 0) ! 401: fprintf(stderr, "On lseek in /etc/utmp: %s", ! 402: sys_errlist[errno]); ! 403: if (read(etcutmp, (char *)&utmp, sizeof utmp) < 0) ! 404: fprintf(stderr, "On read from /etc/utmp: %s", ! 405: sys_errlist[errno]); ! 406: } while (utmp.ut_name[0] != '\0' && --i > 0); ! 407: } ! 408: ! 409: #ifdef BSD4_3 ! 410: /* identify terminal line in ttys */ ! 411: opnttys(device) ! 412: char *device; ! 413: { ! 414: register int ndevice; ! 415: register char *p; ! 416: char *index(); ! 417: char linebuf[BUFSIZ]; ! 418: ! 419: ttysfile = NULL; ! 420: do { ! 421: if (ttysfile != NULL) { ! 422: fclose(ttysfile); ! 423: sleep(5); ! 424: } ! 425: ttysfile = fopen(Etcttys, "r"); ! 426: if(ttysfile == NULL) { ! 427: fprintf(stderr, "Cannot open %s: %s\n", Etcttys, ! 428: sys_errlist[errno]); ! 429: exit(1); ! 430: } ! 431: } while (flock(fileno(ttysfile), LOCK_NB|LOCK_EX) < 0); ! 432: nttysfile = fopen(NEtcttys, "w"); ! 433: if(nttysfile == NULL) { ! 434: fprintf(stderr, "Cannot open %s: %s\n", Etcttys, ! 435: sys_errlist[errno]); ! 436: exit(1); ! 437: } ! 438: ! 439: ndevice = strlen(device); ! 440: #ifndef BRL4_2 ! 441: utmploc = sizeof(utmp); ! 442: #else BRL4_2 ! 443: utmploc = 0; ! 444: #endif BRL4_2 ! 445: ! 446: while(fgets(linebuf, sizeof(linebuf) - 1, ttysfile) != NULL) { ! 447: if(strncmp(device, linebuf, ndevice) == 0) ! 448: return; ! 449: ttyslnbeg += strlen(linebuf); ! 450: if (linebuf[0] != '#' && linebuf[0] != '\0') ! 451: utmploc += sizeof(utmp); ! 452: if (fputs(linebuf, nttysfile) == NULL) { ! 453: fprintf(stderr, "On %s write: %s\n", ! 454: Etcttys, sys_errlist[errno]); ! 455: exit(1); ! 456: } ! 457: ! 458: } ! 459: fprintf(stderr, "%s not found in %s\n", device, Etcttys); ! 460: exit(1); ! 461: } ! 462: ! 463: /* modify appropriate line in /etc/ttys to turn on/off the device */ ! 464: settys(enable) ! 465: int enable; ! 466: { ! 467: register char *cp, *cp2; ! 468: char lbuf[BUFSIZ]; ! 469: int i; ! 470: char c1, c2; ! 471: ! 472: (void) fseek(ttysfile, ttyslnbeg, 0); ! 473: if(fgets(lbuf, BUFSIZ, ttysfile) == NULL) { ! 474: fprintf(stderr, "On %s read: %s\n", ! 475: Etcttys, sys_errlist[errno]); ! 476: exit(1); ! 477: } ! 478: /* format is now */ ! 479: /* ttyd0 std.100 dialup on secure # comment */ ! 480: /* except, 2nd item may have embedded spaces inside quotes, Hubert */ ! 481: cp = lbuf; ! 482: for (i=0;*cp && i<3;i++) { ! 483: if (*cp == '"') { ! 484: cp++; ! 485: while (*cp && *cp != '"') ! 486: cp++; ! 487: if (*cp != '\0') ! 488: cp++; ! 489: }else { ! 490: while (*cp && *cp != ' ' && *cp != '\t') ! 491: cp++; ! 492: } ! 493: while (*cp && (*cp == ' ' || *cp == '\t')) ! 494: cp++; ! 495: } ! 496: if (*cp == '\0') { ! 497: fprintf(stderr,"Badly formatted line in /etc/ttys:\n%s", lbuf); ! 498: exit(1); ! 499: } ! 500: c1 = *--cp; ! 501: *cp++ = '\0'; ! 502: cp2 = cp; ! 503: while (*cp && *cp != ' ' && *cp != '\t' && *cp != '\n') ! 504: cp++; ! 505: if (*cp == '\0') { ! 506: fprintf(stderr,"Badly formatted line in /etc/ttys:\n%s", lbuf); ! 507: exit(1); ! 508: } ! 509: c2 = *cp; ! 510: *cp++ = '\0'; ! 511: while (*cp && (*cp == ' ' || *cp == '\t')) ! 512: cp++; ! 513: resettty = strcmp("on", cp2) != 0; ! 514: fprintf(nttysfile,"%s%c%s%c%s", lbuf, c1, enable ? "on" : "off", c2, cp); ! 515: if (ferror(nttysfile)) { ! 516: fprintf(stderr, "On %s fprintf: %s\n", ! 517: NEtcttys, sys_errlist[errno]); ! 518: exit(1); ! 519: } ! 520: while(fgets(lbuf, sizeof(lbuf) - 1, ttysfile) != NULL) { ! 521: if (fputs(lbuf, nttysfile) == NULL) { ! 522: fprintf(stderr, "On %s write: %s\n", ! 523: NEtcttys, sys_errlist[errno]); ! 524: exit(1); ! 525: } ! 526: } ! 527: ! 528: if (enable^resettty) ! 529: (void) unlink(NEtcttys); ! 530: else { ! 531: struct stat statb; ! 532: if (stat(Etcttys, &statb) == 0) { ! 533: fchmod(fileno(nttysfile) ,statb.st_mode); ! 534: fchown(fileno(nttysfile), statb.st_uid, statb.st_gid); ! 535: } ! 536: (void) rename(NEtcttys, Etcttys); ! 537: } ! 538: (void) fclose(nttysfile); ! 539: (void) fclose(ttysfile); ! 540: return enable^resettty; ! 541: } ! 542: ! 543: #else !BSD4_3 ! 544: ! 545: /* identify terminal line in ttys */ ! 546: opnttys(device) ! 547: char *device; ! 548: { ! 549: register FILE *ttysfile; ! 550: register int ndevice, lnsiz; ! 551: register char *p; ! 552: char *index(); ! 553: char linebuf[BUFSIZ]; ! 554: ! 555: ttysfile = fopen(Etcttys, "r"); ! 556: if(ttysfile == NULL) { ! 557: fprintf(stderr, "Cannot open %s: %s\n", Etcttys, ! 558: sys_errlist[errno]); ! 559: exit(1); ! 560: } ! 561: ! 562: ndevice = strlen(device); ! 563: ttyslnbeg = 0; ! 564: utmploc = 0; ! 565: ! 566: while(fgets(linebuf, sizeof(linebuf) - 1, ttysfile) != NULL) { ! 567: lnsiz = strlen(linebuf); ! 568: if ((p = index(linebuf, '\n')) != NULL) ! 569: *p = '\0'; ! 570: if(strncmp(device, &linebuf[2], ndevice) == 0) { ! 571: (void)fclose(ttysfile); ! 572: #ifdef sequent ! 573: /* Why is the sequent off by one? */ ! 574: utmploc += sizeof(utmp); ! 575: #endif sequent ! 576: return; ! 577: } ! 578: ttyslnbeg += lnsiz; ! 579: utmploc += sizeof(utmp); ! 580: } ! 581: fprintf(stderr, "%s not found in %s\n", device, Etcttys); ! 582: exit(1); ! 583: } ! 584: ! 585: /* modify appropriate line in /etc/ttys to turn on/off the device */ ! 586: settys(enable) ! 587: int enable; ! 588: { ! 589: int ittysfil; ! 590: char out, in; ! 591: ! 592: ittysfil = open(Etcttys, 2); ! 593: if(ittysfil < 0) { ! 594: fprintf(stderr, "Cannot open %s for output: %s\n", ! 595: Etcttys, sys_errlist[errno]); ! 596: exit(1); ! 597: } ! 598: (void)lseek(ittysfil, ttyslnbeg, 0); ! 599: if(read(ittysfil, &in, 1)<0) { ! 600: fprintf(stderr, "On %s write: %s\n", ! 601: Etcttys, sys_errlist[errno]); ! 602: exit(1); ! 603: } ! 604: resettty = (in == '1'); ! 605: out = enable ? '1' : '0'; ! 606: (void)lseek(ittysfil, ttyslnbeg, 0); ! 607: if(write(ittysfil, &out, 1)<0) { ! 608: fprintf(stderr, "On %s write: %s\n", ! 609: Etcttys, sys_errlist[errno]); ! 610: exit(1); ! 611: } ! 612: (void)close(ittysfil); ! 613: return(in==out); ! 614: } ! 615: #endif !BSD4_3 ! 616: ! 617: #ifdef sequent ! 618: setmodem(ttyline, enable) ! 619: char *ttyline; int enable; ! 620: { ! 621: char *sysbuf[BUFSIZ]; ! 622: sprintf(sysbuf,"/etc/ttyconfig /dev/%s -special %s", ttyline, ! 623: enable ? "-carrier" : "-nocarrier"); ! 624: system(sysbuf); ! 625: } ! 626: #endif /* sequent */ ! 627: #ifdef vax ! 628: /* ! 629: * Excerpted from (June 8, 1983 W.Sebok) ! 630: * > ttymodem.c - enable/disable modem control for tty lines. ! 631: * > ! 632: * > Knows about DZ11s and DH11/DM11s. ! 633: * > 23.3.83 - TS ! 634: * > modified to know about DMF's (hasn't been tested) Nov 8, 1984 - WLS ! 635: */ ! 636: ! 637: ! 638: setmodem(ttyline, enable) ! 639: char *ttyline; int enable; ! 640: { ! 641: dev_t dev; ! 642: int kmem; ! 643: int unit, line, nlines, addr, tflags; ! 644: int devtype=0; ! 645: char cflags; short sflags; ! 646: #ifdef BSD4_2 ! 647: int flags; ! 648: #else ! 649: short flags; ! 650: #endif ! 651: struct uba_device *ubinfo; ! 652: struct stat statb; ! 653: struct cdevsw cdevsw; ! 654: ! 655: if(nl[CDEVSW].n_type == 0) { ! 656: fprintf(stderr, "No namelist.\n"); ! 657: return(-1); ! 658: } ! 659: ! 660: if((kmem = open("/dev/kmem", 2)) < 0) { ! 661: fprintf(stderr, "/dev/kmem open: %s\n", sys_errlist[errno]); ! 662: return(-1); ! 663: } ! 664: ! 665: if(stat(ttyline, &statb) < 0) { ! 666: fprintf(stderr, "%s stat: %s\n", ttyline, sys_errlist[errno]); ! 667: return(-1); ! 668: } ! 669: ! 670: if((statb.st_mode&S_IFMT) != S_IFCHR) { ! 671: fprintf(stderr, "%s is not a character device.\n",ttyline); ! 672: return(-1); ! 673: } ! 674: ! 675: dev = statb.st_rdev; ! 676: (void)lseek(kmem, ! 677: (off_t) &(((struct cdevsw *)NLVALUE(CDEVSW))[major(dev)]),0); ! 678: (void)read(kmem, (char *) &cdevsw, sizeof cdevsw); ! 679: ! 680: if((int)(cdevsw.d_open) == NLVALUE(DZOPEN)) { ! 681: devtype = DZ11; ! 682: unit = minor(dev) / NDZLINE; ! 683: line = minor(dev) % NDZLINE; ! 684: addr = (int) &(((int *)NLVALUE(DZINFO))[unit]); ! 685: (void)lseek(kmem, (off_t) NLVALUE(NDZ11), 0); ! 686: } else if((int)(cdevsw.d_open) == NLVALUE(DHOPEN)) { ! 687: devtype = DH11; ! 688: unit = minor(dev) / NDHLINE; ! 689: line = minor(dev) % NDHLINE; ! 690: addr = (int) &(((int *)NLVALUE(DHINFO))[unit]); ! 691: (void)lseek(kmem, (off_t) NLVALUE(NDH11), 0); ! 692: } else if((int)(cdevsw.d_open) == NLVALUE(DMFOPEN)) { ! 693: devtype = DMF; ! 694: unit = minor(dev) / NDMFLINE; ! 695: line = minor(dev) % NDMFLINE; ! 696: addr = (int) &(((int *)NLVALUE(DMFINFO))[unit]); ! 697: (void)lseek(kmem, (off_t) NLVALUE(NDMF), 0); ! 698: } else { ! 699: fprintf(stderr, "Device %s (%d/%d) unknown.\n", ttyline, ! 700: major(dev), minor(dev)); ! 701: return(-1); ! 702: } ! 703: ! 704: (void)read(kmem, (char *) &nlines, sizeof nlines); ! 705: if(minor(dev) >= nlines) { ! 706: fprintf(stderr, "Sub-device %d does not exist (only %d).\n", ! 707: minor(dev), nlines); ! 708: return(-1); ! 709: } ! 710: ! 711: (void)lseek(kmem, (off_t)addr, 0); ! 712: (void)read(kmem, (char *) &ubinfo, sizeof ubinfo); ! 713: (void)lseek(kmem, (off_t) &(ubinfo->ui_flags), 0); ! 714: (void)read(kmem, (char *) &flags, sizeof flags); ! 715: ! 716: tflags = 1<<line; ! 717: resetmodem = ((flags&tflags) == 0); ! 718: flags = enable ? (flags & ~tflags) : (flags | tflags); ! 719: (void)lseek(kmem, (off_t) &(ubinfo->ui_flags), 0); ! 720: (void)write(kmem, (char *) &flags, sizeof flags); ! 721: switch(devtype) { ! 722: case DZ11: ! 723: if((addr = NLVALUE(DZSCAR)) == 0) { ! 724: fprintf(stderr, "No dzsoftCAR.\n"); ! 725: return(-1); ! 726: } ! 727: cflags = flags; ! 728: (void)lseek(kmem, (off_t) &(((char *)addr)[unit]), 0); ! 729: (void)write(kmem, (char *) &cflags, sizeof cflags); ! 730: break; ! 731: case DH11: ! 732: if((addr = NLVALUE(DHSCAR)) == 0) { ! 733: fprintf(stderr, "No dhsoftCAR.\n"); ! 734: return(-1); ! 735: } ! 736: sflags = flags; ! 737: (void)lseek(kmem, (off_t) &(((short *)addr)[unit]), 0); ! 738: (void)write(kmem, (char *) &sflags, sizeof sflags); ! 739: break; ! 740: case DMF: ! 741: if((addr = NLVALUE(DMFSCAR)) == 0) { ! 742: fprintf(stderr, "No dmfsoftCAR.\n"); ! 743: return(-1); ! 744: } ! 745: cflags = flags; ! 746: (void)lseek(kmem, (off_t) &(((char *)addr)[unit]), 0); ! 747: (void)write(kmem, (char *) &cflags, sizeof cflags); ! 748: break; ! 749: default: ! 750: fprintf(stderr, "Unknown device type\n"); ! 751: return(-1); ! 752: } ! 753: return(0); ! 754: } ! 755: #endif /* vax */ ! 756: ! 757: prefix(s1, s2) ! 758: register char *s1, *s2; ! 759: { ! 760: register char c; ! 761: ! 762: while ((c = *s1++) == *s2++) ! 763: if (c == '\0') ! 764: return (1); ! 765: return (c == '\0'); ! 766: } ! 767: #else /* !DIALINOUT */ ! 768: main() ! 769: { ! 770: fprintf(stderr,"acucntrl is not supported on this system\n"); ! 771: } ! 772: #endif /* !DIALINOUT */
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.