118480Sralph #ifndef lint 2*33557Srick static char sccsid[] = "@(#)acucntrl.c 5.10 (Berkeley) 02/24/88"; 318480Sralph #endif 418480Sralph 518480Sralph /* acucntrl - turn around tty line between dialin and dialout 618480Sralph * 718480Sralph * Usage: acucntrl {enable,disable} /dev/ttydX 818480Sralph * 918480Sralph * History: 1018480Sralph * First written by Allan Wilkes (fisher!allan) 1118480Sralph * 1218480Sralph * Modified June 8,1983 by W.Sebok (astrovax!wls) to poke kernel rather 1318480Sralph * than use kernel hack to turn on/off modem control, using subroutine 1418480Sralph * stolen from program written by Tsutomu Shimomura 1518480Sralph * {astrovax,escher}!tsutomu 1618480Sralph * 1718480Sralph * Worked over many times by W.Sebok (i.e. hacked to death) 1818480Sralph * 1918480Sralph * Operation: 2018480Sralph * disable (i.e. setup for dialing out) 2118480Sralph * (1) check input arguments 2218480Sralph * (2) look in /etc/utmp to check that the line is not in use by another 2318480Sralph * (3) disable modem control on terminal 2418480Sralph * (4) check for carrier on device 2518480Sralph * (5) change owner of device to real id 2618480Sralph * (6) edit /etc/ttys, changing the first character of the appropriate 2718480Sralph * line to 0 2818480Sralph * (7) send a hangup to process 1 to poke init to disable getty 2918480Sralph * (8) post uid name in capitals in /etc/utmp to let world know device has 3018480Sralph * been grabbed 3118480Sralph * (9) make sure that DTR is on 3218480Sralph * 3318480Sralph * enable (i.e.) restore for dialin 3418480Sralph * (1) check input arguments 3518480Sralph * (2) look in /etc/utmp to check that the line is not in use by another 3618480Sralph * (3) make sure modem control on terminal is disabled 3718480Sralph * (4) turn off DTR to make sure line is hung up 3818480Sralph * (5) condition line: clear exclusive use and set hangup on close modes 3918480Sralph * (6) turn on modem control 4018480Sralph * (7) edit /etc/ttys, changing the first character of the appropriate 4118480Sralph * line to 1 4218480Sralph * (8) send a hangup to process 1 to poke init to enable getty 4318480Sralph * (9) clear uid name for /etc/utmp 4418480Sralph */ 4518480Sralph 4618480Sralph /* #define SENSECARRIER */ 4718480Sralph 4818480Sralph #include "uucp.h" 49*33557Srick #ifdef DIALINOUT 5018480Sralph #include <sys/buf.h> 5118614Sralph #include <signal.h> 5218480Sralph #include <sys/conf.h> 53*33557Srick #ifdef vax 54*33557Srick #ifdef BSD4_2 55*33557Srick #include <vaxuba/ubavar.h> 56*33557Srick #else 57*33557Srick #include <sys/ubavar.h> 58*33557Srick #endif 59*33557Srick #endif /* vax */ 6018480Sralph #include <sys/stat.h> 6118480Sralph #include <nlist.h> 6218480Sralph #include <sgtty.h> 6318480Sralph #include <utmp.h> 6418480Sralph #include <pwd.h> 6518480Sralph #include <stdio.h> 6625123Sbloom #include <sys/file.h> 6718480Sralph 6818480Sralph #define NDZLINE 8 /* lines/dz */ 6918480Sralph #define NDHLINE 16 /* lines/dh */ 7018480Sralph #define NDMFLINE 8 /* lines/dmf */ 7118480Sralph 7218480Sralph #define DZ11 1 7318480Sralph #define DH11 2 7418480Sralph #define DMF 3 7518480Sralph 7618480Sralph #define NLVALUE(val) (nl[val].n_value) 7718480Sralph 7818480Sralph struct nlist nl[] = { 7918480Sralph #define CDEVSW 0 8018480Sralph { "_cdevsw" }, 8118480Sralph 8218480Sralph #define DZOPEN 1 8318480Sralph { "_dzopen" }, 8418480Sralph #define DZINFO 2 8518480Sralph { "_dzinfo" }, 8618480Sralph #define NDZ11 3 8718480Sralph { "_dz_cnt" }, 8818480Sralph #define DZSCAR 4 8918480Sralph { "_dzsoftCAR" }, 9018480Sralph 9118480Sralph #define DHOPEN 5 9218480Sralph { "_dhopen" }, 9318480Sralph #define DHINFO 6 9418480Sralph { "_dhinfo" }, 9518480Sralph #define NDH11 7 9618480Sralph { "_ndh11" }, 9718480Sralph #define DHSCAR 8 9818480Sralph { "_dhsoftCAR" }, 9918480Sralph 10018480Sralph #define DMFOPEN 9 10118480Sralph { "_dmfopen" }, 10218480Sralph #define DMFINFO 10 10318480Sralph { "_dmfinfo" }, 10418480Sralph #define NDMF 11 10518480Sralph { "_ndmf" }, 10618480Sralph #define DMFSCAR 12 10718480Sralph { "_dmfsoftCAR" }, 10818480Sralph 10918480Sralph { "\0" } 11018480Sralph }; 11118480Sralph 11218480Sralph #define ENABLE 1 11318480Sralph #define DISABLE 0 11418480Sralph 11518480Sralph char Etcutmp[] = "/etc/utmp"; 11618480Sralph char Etcttys[] = "/etc/ttys"; 11723723Sbloom #ifdef BSD4_3 11825123Sbloom FILE *ttysfile, *nttysfile; 11923723Sbloom char NEtcttys[] = "/etc/ttys.new"; 12023723Sbloom extern long ftell(); 12123723Sbloom #endif BSD4_3 12218480Sralph char Devhome[] = "/dev"; 12318480Sralph 12418480Sralph char usage[] = "Usage: acucntrl {dis|en}able ttydX\n"; 12518480Sralph 12618480Sralph struct utmp utmp; 12718480Sralph char resettty, resetmodem; 12818480Sralph int etcutmp; 12918614Sralph off_t utmploc; 13018614Sralph off_t ttyslnbeg; 13118480Sralph 13218480Sralph #define NAMSIZ sizeof(utmp.ut_name) 13318480Sralph #define LINSIZ sizeof(utmp.ut_line) 13418480Sralph 13518480Sralph main(argc, argv) 13618480Sralph int argc; char *argv[]; 13718480Sralph { 13818480Sralph register char *p; 13918480Sralph register int i; 14018480Sralph char uname[NAMSIZ], Uname[NAMSIZ]; 14118480Sralph int enable ; 14218480Sralph char *device; 14318480Sralph int devfile; 14418480Sralph int uid, gid; 14518614Sralph off_t lseek(); 14618480Sralph struct passwd *getpwuid(); 14718480Sralph char *rindex(); 14818480Sralph extern int errno; 14918480Sralph extern char *sys_errlist[]; 15018480Sralph 15118480Sralph /* check input arguments */ 15218480Sralph if (argc!=3) { 15318480Sralph fprintf(stderr, usage); 15418480Sralph exit(1); 15518480Sralph } 15618480Sralph 15718480Sralph /* interpret command type */ 15823723Sbloom if (prefix(argv[1], "disable") || strcmp(argv[1], "dialout")==0) 15918480Sralph enable = 0; 16023723Sbloom else if (prefix(argv[1], "enable") || strcmp(argv[1], "dialin")==0) 16118480Sralph enable = 1; 16218480Sralph else { 16318480Sralph fprintf(stderr, usage); 16418480Sralph exit(1); 16518480Sralph } 16618480Sralph 16723723Sbloom device = rindex(argv[2], '/'); 16818480Sralph device = (device == NULL) ? argv[2]: device+1; 16918480Sralph 17018480Sralph /* only recognize devices of the form ttydX */ 17123723Sbloom if (strncmp(device, "ttyd", 4)!=0) { 17223723Sbloom fprintf(stderr, "Bad Device Name %s", device); 17318480Sralph exit(1); 17418480Sralph } 17518480Sralph 17618480Sralph opnttys(device); 17718480Sralph 178*33557Srick #ifdef vax 17918480Sralph /* Get nlist info */ 18023723Sbloom nlist("/vmunix", nl); 181*33557Srick #endif vax 18218480Sralph 18318480Sralph /* Chdir to /dev */ 18418480Sralph if(chdir(Devhome) < 0) { 18518480Sralph fprintf(stderr, "Cannot chdir to %s: %s\r\n", 18618480Sralph Devhome, sys_errlist[errno]); 18718480Sralph exit(1); 18818480Sralph } 18918480Sralph 19018480Sralph /* Get uid information */ 19118480Sralph uid = getuid(); 19218480Sralph gid = getgid(); 19318480Sralph 19418480Sralph p = getpwuid(uid)->pw_name; 19518480Sralph if (p==NULL) { 19623723Sbloom fprintf(stderr, "cannot get uid name\n"); 19718480Sralph exit(1); 19818480Sralph } 19918480Sralph 20018480Sralph /* to upper case */ 20118480Sralph i = 0; 20218480Sralph do { 20318480Sralph uname[i] = *p; 20418480Sralph Uname[i] = (*p>='a' && *p<='z') ? (*p - ('a'-'A')) : *p; 20518480Sralph i++; p++; 20618480Sralph } while (*p && i<NAMSIZ); 20718480Sralph 20818480Sralph 20918480Sralph /* check to see if line is being used */ 21018480Sralph if( (etcutmp = open(Etcutmp, 2)) < 0) { 21123723Sbloom fprintf(stderr, "On open %s open: %s\n", 21223723Sbloom Etcutmp, sys_errlist[errno]); 21318480Sralph exit(1); 21418480Sralph } 21518480Sralph 21623723Sbloom (void)lseek(etcutmp, utmploc, 0); 21718480Sralph 21823723Sbloom i = read(etcutmp, (char *)&utmp, sizeof(struct utmp)); 21918480Sralph 22018480Sralph if( 22118480Sralph i == sizeof(struct utmp) && 22218480Sralph utmp.ut_line[0] != '\0' && 22318480Sralph utmp.ut_name[0] != '\0' && 22418480Sralph ( 22523723Sbloom !upcase(utmp.ut_name, NAMSIZ) || 22618480Sralph ( 22718480Sralph uid != 0 && 22823723Sbloom strncmp(utmp.ut_name, Uname, NAMSIZ) != 0 22918480Sralph ) 23018480Sralph ) 23118480Sralph ) { 23218480Sralph fprintf(stderr, "%s in use by %s\n", device, utmp.ut_name); 23318480Sralph exit(2); 23418480Sralph } 23518480Sralph 236*33557Srick #ifndef sequent 23718480Sralph /* Disable modem control */ 23823723Sbloom if (setmodem(device, DISABLE) < 0) { 23923723Sbloom fprintf(stderr, "Unable to disable modem control\n"); 24018480Sralph exit(1); 24118480Sralph } 242*33557Srick #endif !sequent 24318480Sralph 24418480Sralph if (enable) { 245*33557Srick #ifdef sequent 246*33557Srick if (setmodem(device, ENABLE) < 0) { 247*33557Srick fprintf(stderr, "Cannot Enable modem control\n"); 248*33557Srick (void)setmodem(device, i); 249*33557Srick exit(1); 250*33557Srick } 251*33557Srick #endif sequent 252*33557Srick #ifndef sequent 25318480Sralph if((devfile = open(device, 1)) < 0) { 25423723Sbloom fprintf(stderr, "On open of %s: %s\n", 25518480Sralph device, sys_errlist[errno]); 25623723Sbloom (void)setmodem(device, resetmodem); 25718480Sralph exit(1); 25818480Sralph } 25918480Sralph /* Try one last time to hang up */ 26023723Sbloom if (ioctl(devfile, (int)TIOCCDTR, (char *)0) < 0) 26123723Sbloom fprintf(stderr, "On TIOCCDTR ioctl: %s\n", 26218480Sralph sys_errlist[errno]); 26318480Sralph 26423723Sbloom if (ioctl(devfile, (int)TIOCNXCL, (char *)0) < 0) 26518480Sralph fprintf(stderr, 26618480Sralph "Cannot clear Exclusive Use on %s: %s\n", 26718480Sralph device, sys_errlist[errno]); 26818480Sralph 26923723Sbloom if (ioctl(devfile, (int)TIOCHPCL, (char *)0) < 0) 27018480Sralph fprintf(stderr, 27118480Sralph "Cannot set hangup on close on %s: %s\n", 27218480Sralph device, sys_errlist[errno]); 27318480Sralph 274*33557Srick #endif !sequent 27518480Sralph i = resetmodem; 27618480Sralph 277*33557Srick #ifndef sequent 27823723Sbloom if (setmodem(device, ENABLE) < 0) { 27923723Sbloom fprintf(stderr, "Cannot Enable modem control\n"); 28023723Sbloom (void)setmodem(device, i); 28118480Sralph exit(1); 28218480Sralph } 283*33557Srick #endif sequent 28418480Sralph resetmodem=i; 28518480Sralph 28618614Sralph if (settys(ENABLE)) { 28723723Sbloom fprintf(stderr, "%s already enabled\n", device); 28818614Sralph } else { 28923723Sbloom pokeinit(device, Uname, enable); 29018614Sralph } 29123723Sbloom post(device, ""); 29218480Sralph 29318480Sralph } else { 29418480Sralph #if defined(TIOCMGET) && defined(SENSECARRIER) 29518480Sralph if (uid!=0) { 29618480Sralph int linestat = 0; 29718480Sralph 29818480Sralph /* check for presence of carrier */ 29918480Sralph sleep(2); /* need time after modem control turnoff */ 30018480Sralph 30118480Sralph if((devfile = open(device, 1)) < 0) { 30223723Sbloom fprintf(stderr, "On open of %s: %s\n", 30318480Sralph device, sys_errlist[errno]); 30423723Sbloom (void)setmodem(device, resetmodem); 30518480Sralph exit(1); 30618480Sralph } 30718480Sralph 30823723Sbloom (void)ioctl(devfile, TIOCMGET, &linestat); 30918480Sralph 31018480Sralph if (linestat&TIOCM_CAR) { 31123723Sbloom fprintf(stderr, "%s is in use (Carrier On)\n", 31218480Sralph device); 31323723Sbloom (void)setmodem(device, resetmodem); 31418480Sralph exit(2); 31518480Sralph } 31618480Sralph (void)close(devfile); 31718480Sralph } 31818480Sralph #endif TIOCMGET 31918480Sralph /* chown device */ 32018480Sralph if(chown(device, uid, gid) < 0) 32118480Sralph fprintf(stderr, "Cannot chown %s: %s\n", 32218480Sralph device, sys_errlist[errno]); 32318480Sralph 32418480Sralph 32518480Sralph /* poke init */ 32618614Sralph if(settys(DISABLE)) { 32723723Sbloom fprintf(stderr, "%s already disabled\n", device); 32818614Sralph } else { 32923723Sbloom pokeinit(device, Uname, enable); 33018614Sralph } 33123723Sbloom post(device, Uname); 332*33557Srick #ifdef sequent 333*33557Srick /* Disable modem control */ 334*33557Srick if (setmodem(device, DISABLE) < 0) { 335*33557Srick fprintf(stderr, "Unable to disable modem control\n"); 336*33557Srick exit(1); 337*33557Srick } 338*33557Srick #endif sequent 33925123Sbloom if((devfile = open(device, O_RDWR|O_NDELAY)) < 0) { 34018480Sralph fprintf(stderr, "On %s open: %s\n", 34118480Sralph device, sys_errlist[errno]); 34218480Sralph } else { 34318614Sralph if(ioctl(devfile, (int)TIOCSDTR, (char *)0) < 0) 34418480Sralph fprintf(stderr, 34518480Sralph "Cannot set DTR on %s: %s\n", 34618480Sralph device, sys_errlist[errno]); 34718480Sralph } 34818480Sralph } 34918480Sralph 35018480Sralph exit(0); 35118480Sralph } 35218480Sralph 35318480Sralph /* return true if no lower case */ 35423723Sbloom upcase(str, len) 35518480Sralph register char *str; 35618480Sralph register int len; 35718480Sralph { 35818480Sralph for (; *str, --len >= 0 ; str++) 35918480Sralph if (*str>='a' && *str<='z') 36018480Sralph return(0); 36118480Sralph return(1); 36218480Sralph } 36318480Sralph 36418480Sralph /* Post name to public */ 36523723Sbloom post(device, name) 36618480Sralph char *device, *name; 36718480Sralph { 36818614Sralph (void)time((time_t *)&utmp.ut_time); 36923583Sbloom strncpy(utmp.ut_line, device, LINSIZ); 37023583Sbloom strncpy(utmp.ut_name, name, NAMSIZ); 37125123Sbloom if (lseek(etcutmp, utmploc, 0) < 0) 37223723Sbloom fprintf(stderr, "on lseek in /etc/utmp: %s", 37318480Sralph sys_errlist[errno]); 37425123Sbloom if (write(etcutmp, (char *)&utmp, sizeof(utmp)) < 0) 37523723Sbloom fprintf(stderr, "on write in /etc/utmp: %s", 37618480Sralph sys_errlist[errno]); 37718480Sralph } 37818480Sralph 37918480Sralph /* poke process 1 and wait for it to do its thing */ 38023723Sbloom pokeinit(device, uname, enable) 38118480Sralph char *uname, *device; int enable; 38218480Sralph { 38318480Sralph struct utmp utmp; 38418614Sralph register int i; 38518480Sralph 38618480Sralph post(device, uname); 38718480Sralph 38818480Sralph /* poke init */ 38918480Sralph if (kill(1, SIGHUP)) { 39018480Sralph fprintf(stderr, 39118480Sralph "Cannot send hangup to init process: %s\n", 39218480Sralph sys_errlist[errno]); 39318614Sralph (void)settys(resettty); 39423723Sbloom (void)setmodem(device, resetmodem); 39518480Sralph exit(1); 39618480Sralph } 39718480Sralph 39818480Sralph if (enable) 39918480Sralph return; 40018480Sralph 40118480Sralph /* wait till init has responded, clearing the utmp entry */ 40225123Sbloom i = 100; 40318480Sralph do { 40418480Sralph sleep(1); 40525123Sbloom if (lseek(etcutmp, utmploc, 0) < 0) 40623723Sbloom fprintf(stderr, "On lseek in /etc/utmp: %s", 40718480Sralph sys_errlist[errno]); 40825123Sbloom if (read(etcutmp, (char *)&utmp, sizeof utmp) < 0) 40923723Sbloom fprintf(stderr, "On read from /etc/utmp: %s", 41018480Sralph sys_errlist[errno]); 41118614Sralph } while (utmp.ut_name[0] != '\0' && --i > 0); 41218480Sralph } 41318480Sralph 41423723Sbloom #ifdef BSD4_3 41518480Sralph /* identify terminal line in ttys */ 41618480Sralph opnttys(device) 41718480Sralph char *device; 41818480Sralph { 41923723Sbloom register int ndevice; 42023723Sbloom register char *p; 42123723Sbloom char *index(); 42223723Sbloom char linebuf[BUFSIZ]; 42323723Sbloom 42425123Sbloom ttysfile = NULL; 42525123Sbloom do { 42625123Sbloom if (ttysfile != NULL) { 42725123Sbloom fclose(ttysfile); 42825123Sbloom sleep(5); 42925123Sbloom } 43025123Sbloom ttysfile = fopen(Etcttys, "r"); 43125123Sbloom if(ttysfile == NULL) { 43225123Sbloom fprintf(stderr, "Cannot open %s: %s\n", Etcttys, 43325123Sbloom sys_errlist[errno]); 43425123Sbloom exit(1); 43525123Sbloom } 43625123Sbloom } while (flock(fileno(ttysfile), LOCK_NB|LOCK_EX) < 0); 43723723Sbloom nttysfile = fopen(NEtcttys, "w"); 43823723Sbloom if(nttysfile == NULL) { 43923723Sbloom fprintf(stderr, "Cannot open %s: %s\n", Etcttys, 44023723Sbloom sys_errlist[errno]); 44123723Sbloom exit(1); 44223723Sbloom } 44323723Sbloom 44423723Sbloom ndevice = strlen(device); 44525962Sbloom #ifndef BRL4_2 44625123Sbloom utmploc = sizeof(utmp); 44725962Sbloom #else BRL4_2 44825962Sbloom utmploc = 0; 44925962Sbloom #endif BRL4_2 45023723Sbloom 45123723Sbloom while(fgets(linebuf, sizeof(linebuf) - 1, ttysfile) != NULL) { 45225123Sbloom if(strncmp(device, linebuf, ndevice) == 0) 45325123Sbloom return; 45425123Sbloom ttyslnbeg += strlen(linebuf); 45525962Sbloom if (linebuf[0] != '#' && linebuf[0] != '\0') 45625962Sbloom utmploc += sizeof(utmp); 45723723Sbloom if (fputs(linebuf, nttysfile) == NULL) { 45823723Sbloom fprintf(stderr, "On %s write: %s\n", 45923723Sbloom Etcttys, sys_errlist[errno]); 46023723Sbloom exit(1); 46123723Sbloom } 46223723Sbloom 46323723Sbloom } 46423723Sbloom fprintf(stderr, "%s not found in %s\n", device, Etcttys); 46523723Sbloom exit(1); 46623723Sbloom } 46723723Sbloom 46823723Sbloom /* modify appropriate line in /etc/ttys to turn on/off the device */ 46923723Sbloom settys(enable) 47023723Sbloom int enable; 47123723Sbloom { 47223723Sbloom register char *cp, *cp2; 47323723Sbloom char lbuf[BUFSIZ]; 47423723Sbloom int i; 47523723Sbloom char c1, c2; 47623723Sbloom 47725123Sbloom (void) fseek(ttysfile, ttyslnbeg, 0); 47825123Sbloom if(fgets(lbuf, BUFSIZ, ttysfile) == NULL) { 47923723Sbloom fprintf(stderr, "On %s read: %s\n", 48023723Sbloom Etcttys, sys_errlist[errno]); 48123723Sbloom exit(1); 48223723Sbloom } 48323723Sbloom /* format is now */ 48423723Sbloom /* ttyd0 std.100 dialup on secure # comment */ 48525364Sbloom /* except, 2nd item may have embedded spaces inside quotes, Hubert */ 48623723Sbloom cp = lbuf; 48723723Sbloom for (i=0;*cp && i<3;i++) { 48825364Sbloom if (*cp == '"') { 48923723Sbloom cp++; 49025364Sbloom while (*cp && *cp != '"') 49125364Sbloom cp++; 49225364Sbloom if (*cp != '\0') 49325364Sbloom cp++; 49425364Sbloom }else { 49525364Sbloom while (*cp && *cp != ' ' && *cp != '\t') 49625364Sbloom cp++; 49725364Sbloom } 49823723Sbloom while (*cp && (*cp == ' ' || *cp == '\t')) 49923723Sbloom cp++; 50023723Sbloom } 50123723Sbloom if (*cp == '\0') { 50223723Sbloom fprintf(stderr,"Badly formatted line in /etc/ttys:\n%s", lbuf); 50323723Sbloom exit(1); 50423723Sbloom } 50523723Sbloom c1 = *--cp; 50623723Sbloom *cp++ = '\0'; 50723723Sbloom cp2 = cp; 50823723Sbloom while (*cp && *cp != ' ' && *cp != '\t' && *cp != '\n') 50923723Sbloom cp++; 51023723Sbloom if (*cp == '\0') { 51123723Sbloom fprintf(stderr,"Badly formatted line in /etc/ttys:\n%s", lbuf); 51223723Sbloom exit(1); 51323723Sbloom } 51423723Sbloom c2 = *cp; 51523723Sbloom *cp++ = '\0'; 51623723Sbloom while (*cp && (*cp == ' ' || *cp == '\t')) 51723723Sbloom cp++; 51823723Sbloom resettty = strcmp("on", cp2) != 0; 51925123Sbloom fprintf(nttysfile,"%s%c%s%c%s", lbuf, c1, enable ? "on" : "off", c2, cp); 52025123Sbloom if (ferror(nttysfile)) { 52123723Sbloom fprintf(stderr, "On %s fprintf: %s\n", 52223723Sbloom NEtcttys, sys_errlist[errno]); 52323723Sbloom exit(1); 52423723Sbloom } 52525123Sbloom while(fgets(lbuf, sizeof(lbuf) - 1, ttysfile) != NULL) { 52625123Sbloom if (fputs(lbuf, nttysfile) == NULL) { 52723723Sbloom fprintf(stderr, "On %s write: %s\n", 52823723Sbloom NEtcttys, sys_errlist[errno]); 52923723Sbloom exit(1); 53023723Sbloom } 53123723Sbloom } 53223723Sbloom 53323723Sbloom if (enable^resettty) 53423723Sbloom (void) unlink(NEtcttys); 53523723Sbloom else { 53623723Sbloom struct stat statb; 53723723Sbloom if (stat(Etcttys, &statb) == 0) { 53825123Sbloom fchmod(fileno(nttysfile) ,statb.st_mode); 53925123Sbloom fchown(fileno(nttysfile), statb.st_uid, statb.st_gid); 54023723Sbloom } 54123723Sbloom (void) rename(NEtcttys, Etcttys); 54223723Sbloom } 54325123Sbloom (void) fclose(nttysfile); 54425123Sbloom (void) fclose(ttysfile); 54523723Sbloom return enable^resettty; 54623723Sbloom } 54723723Sbloom 54823723Sbloom #else !BSD4_3 54923723Sbloom 55023723Sbloom /* identify terminal line in ttys */ 55123723Sbloom opnttys(device) 55223723Sbloom char *device; 55323723Sbloom { 55418480Sralph register FILE *ttysfile; 55518480Sralph register int ndevice, lnsiz; 55618480Sralph register char *p; 55718480Sralph char *index(); 55823723Sbloom char linebuf[BUFSIZ]; 55918480Sralph 56018480Sralph ttysfile = fopen(Etcttys, "r"); 56118480Sralph if(ttysfile == NULL) { 56218480Sralph fprintf(stderr, "Cannot open %s: %s\n", Etcttys, 56318480Sralph sys_errlist[errno]); 56418480Sralph exit(1); 56518480Sralph } 56618480Sralph 56718480Sralph ndevice = strlen(device); 56818480Sralph ttyslnbeg = 0; 56918480Sralph utmploc = 0; 57018480Sralph 57118480Sralph while(fgets(linebuf, sizeof(linebuf) - 1, ttysfile) != NULL) { 57218480Sralph lnsiz = strlen(linebuf); 57323723Sbloom if ((p = index(linebuf, '\n')) != NULL) 57418480Sralph *p = '\0'; 57518480Sralph if(strncmp(device, &linebuf[2], ndevice) == 0) { 57618480Sralph (void)fclose(ttysfile); 577*33557Srick #ifdef sequent 578*33557Srick /* Why is the sequent off by one? */ 579*33557Srick utmploc += sizeof(utmp); 580*33557Srick #endif sequent 58118480Sralph return; 58218480Sralph } 58318480Sralph ttyslnbeg += lnsiz; 58425123Sbloom utmploc += sizeof(utmp); 58518480Sralph } 58618480Sralph fprintf(stderr, "%s not found in %s\n", device, Etcttys); 58718480Sralph exit(1); 58818480Sralph } 58918480Sralph 59018480Sralph /* modify appropriate line in /etc/ttys to turn on/off the device */ 59118480Sralph settys(enable) 59218480Sralph int enable; 59318480Sralph { 59418480Sralph int ittysfil; 59523723Sbloom char out, in; 59618480Sralph 59718480Sralph ittysfil = open(Etcttys, 2); 59823723Sbloom if(ittysfil < 0) { 59918480Sralph fprintf(stderr, "Cannot open %s for output: %s\n", 60018480Sralph Etcttys, sys_errlist[errno]); 60118480Sralph exit(1); 60218480Sralph } 60323723Sbloom (void)lseek(ittysfil, ttyslnbeg, 0); 60423723Sbloom if(read(ittysfil, &in, 1)<0) { 60523723Sbloom fprintf(stderr, "On %s write: %s\n", 60618480Sralph Etcttys, sys_errlist[errno]); 60718480Sralph exit(1); 60818480Sralph } 60918480Sralph resettty = (in == '1'); 61018480Sralph out = enable ? '1' : '0'; 61123723Sbloom (void)lseek(ittysfil, ttyslnbeg, 0); 61223723Sbloom if(write(ittysfil, &out, 1)<0) { 61323723Sbloom fprintf(stderr, "On %s write: %s\n", 61418480Sralph Etcttys, sys_errlist[errno]); 61518480Sralph exit(1); 61618480Sralph } 61718480Sralph (void)close(ittysfil); 61818614Sralph return(in==out); 61918480Sralph } 62023723Sbloom #endif !BSD4_3 62118480Sralph 622*33557Srick #ifdef sequent 623*33557Srick setmodem(ttyline, enable) 624*33557Srick char *ttyline; int enable; 625*33557Srick { 626*33557Srick char *sysbuf[BUFSIZ]; 627*33557Srick sprintf(sysbuf,"/etc/ttyconfig /dev/%s -special %s", ttyline, 628*33557Srick enable ? "-carrier" : "-nocarrier"); 629*33557Srick system(sysbuf); 630*33557Srick } 631*33557Srick #endif /* sequent */ 632*33557Srick #ifdef vax 63318480Sralph /* 63423723Sbloom * Excerpted from (June 8, 1983 W.Sebok) 63518480Sralph * > ttymodem.c - enable/disable modem control for tty lines. 63618480Sralph * > 63718480Sralph * > Knows about DZ11s and DH11/DM11s. 63818480Sralph * > 23.3.83 - TS 63923723Sbloom * > modified to know about DMF's (hasn't been tested) Nov 8, 1984 - WLS 64018480Sralph */ 64118480Sralph 64218480Sralph 64323723Sbloom setmodem(ttyline, enable) 64418480Sralph char *ttyline; int enable; 64518480Sralph { 64618480Sralph dev_t dev; 64718480Sralph int kmem; 64823723Sbloom int unit, line, nlines, addr, tflags; 64918614Sralph int devtype=0; 65018614Sralph char cflags; short sflags; 65118614Sralph #ifdef BSD4_2 65218614Sralph int flags; 65318614Sralph #else 65418614Sralph short flags; 65518614Sralph #endif 65618480Sralph struct uba_device *ubinfo; 65718480Sralph struct stat statb; 65818480Sralph struct cdevsw cdevsw; 65918480Sralph 66018480Sralph if(nl[CDEVSW].n_type == 0) { 66123723Sbloom fprintf(stderr, "No namelist.\n"); 66218480Sralph return(-1); 66318480Sralph } 66418480Sralph 66518480Sralph if((kmem = open("/dev/kmem", 2)) < 0) { 66623723Sbloom fprintf(stderr, "/dev/kmem open: %s\n", sys_errlist[errno]); 66718480Sralph return(-1); 66818480Sralph } 66918480Sralph 67023723Sbloom if(stat(ttyline, &statb) < 0) { 67123723Sbloom fprintf(stderr, "%s stat: %s\n", ttyline, sys_errlist[errno]); 67218480Sralph return(-1); 67318480Sralph } 67418480Sralph 67518614Sralph if((statb.st_mode&S_IFMT) != S_IFCHR) { 67623723Sbloom fprintf(stderr, "%s is not a character device.\n",ttyline); 67718480Sralph return(-1); 67818480Sralph } 67918480Sralph 68018480Sralph dev = statb.st_rdev; 68118480Sralph (void)lseek(kmem, 68218614Sralph (off_t) &(((struct cdevsw *)NLVALUE(CDEVSW))[major(dev)]),0); 68323723Sbloom (void)read(kmem, (char *) &cdevsw, sizeof cdevsw); 68418480Sralph 68518480Sralph if((int)(cdevsw.d_open) == NLVALUE(DZOPEN)) { 68618480Sralph devtype = DZ11; 68718480Sralph unit = minor(dev) / NDZLINE; 68818480Sralph line = minor(dev) % NDZLINE; 68918480Sralph addr = (int) &(((int *)NLVALUE(DZINFO))[unit]); 69023723Sbloom (void)lseek(kmem, (off_t) NLVALUE(NDZ11), 0); 69118480Sralph } else if((int)(cdevsw.d_open) == NLVALUE(DHOPEN)) { 69218480Sralph devtype = DH11; 69318480Sralph unit = minor(dev) / NDHLINE; 69418480Sralph line = minor(dev) % NDHLINE; 69518480Sralph addr = (int) &(((int *)NLVALUE(DHINFO))[unit]); 69623723Sbloom (void)lseek(kmem, (off_t) NLVALUE(NDH11), 0); 69718480Sralph } else if((int)(cdevsw.d_open) == NLVALUE(DMFOPEN)) { 69818480Sralph devtype = DMF; 69918480Sralph unit = minor(dev) / NDMFLINE; 70018480Sralph line = minor(dev) % NDMFLINE; 70118480Sralph addr = (int) &(((int *)NLVALUE(DMFINFO))[unit]); 70223723Sbloom (void)lseek(kmem, (off_t) NLVALUE(NDMF), 0); 70318480Sralph } else { 70423723Sbloom fprintf(stderr, "Device %s (%d/%d) unknown.\n", ttyline, 70523723Sbloom major(dev), minor(dev)); 70618480Sralph return(-1); 70718480Sralph } 70818480Sralph 70923723Sbloom (void)read(kmem, (char *) &nlines, sizeof nlines); 71018480Sralph if(minor(dev) >= nlines) { 71123723Sbloom fprintf(stderr, "Sub-device %d does not exist (only %d).\n", 71223723Sbloom minor(dev), nlines); 71318480Sralph return(-1); 71418480Sralph } 71518480Sralph 71623723Sbloom (void)lseek(kmem, (off_t)addr, 0); 71723723Sbloom (void)read(kmem, (char *) &ubinfo, sizeof ubinfo); 71823723Sbloom (void)lseek(kmem, (off_t) &(ubinfo->ui_flags), 0); 71923723Sbloom (void)read(kmem, (char *) &flags, sizeof flags); 72018480Sralph 72118480Sralph tflags = 1<<line; 72218480Sralph resetmodem = ((flags&tflags) == 0); 72318480Sralph flags = enable ? (flags & ~tflags) : (flags | tflags); 72423723Sbloom (void)lseek(kmem, (off_t) &(ubinfo->ui_flags), 0); 72523723Sbloom (void)write(kmem, (char *) &flags, sizeof flags); 72618480Sralph switch(devtype) { 72718480Sralph case DZ11: 72818480Sralph if((addr = NLVALUE(DZSCAR)) == 0) { 72923723Sbloom fprintf(stderr, "No dzsoftCAR.\n"); 73018480Sralph return(-1); 73118480Sralph } 73218614Sralph cflags = flags; 73323723Sbloom (void)lseek(kmem, (off_t) &(((char *)addr)[unit]), 0); 73423723Sbloom (void)write(kmem, (char *) &cflags, sizeof cflags); 73518480Sralph break; 73618480Sralph case DH11: 73718480Sralph if((addr = NLVALUE(DHSCAR)) == 0) { 73823723Sbloom fprintf(stderr, "No dhsoftCAR.\n"); 73918480Sralph return(-1); 74018480Sralph } 74118614Sralph sflags = flags; 74223723Sbloom (void)lseek(kmem, (off_t) &(((short *)addr)[unit]), 0); 74323723Sbloom (void)write(kmem, (char *) &sflags, sizeof sflags); 74418480Sralph break; 74518480Sralph case DMF: 74618480Sralph if((addr = NLVALUE(DMFSCAR)) == 0) { 74723723Sbloom fprintf(stderr, "No dmfsoftCAR.\n"); 74818480Sralph return(-1); 74918480Sralph } 75018614Sralph cflags = flags; 75123723Sbloom (void)lseek(kmem, (off_t) &(((char *)addr)[unit]), 0); 75223723Sbloom (void)write(kmem, (char *) &flags, sizeof cflags); 75318480Sralph break; 75418480Sralph default: 75523723Sbloom fprintf(stderr, "Unknown device type\n"); 75618480Sralph return(-1); 75718480Sralph } 75818480Sralph return(0); 75918480Sralph } 760*33557Srick #endif /* vax */ 76118480Sralph 76218480Sralph prefix(s1, s2) 76318480Sralph register char *s1, *s2; 76418480Sralph { 76518480Sralph register char c; 76618480Sralph 76718480Sralph while ((c = *s1++) == *s2++) 76818480Sralph if (c == '\0') 76918480Sralph return (1); 77018480Sralph return (c == '\0'); 77118480Sralph } 772*33557Srick #endif /* DIALINOUT */ 773