rogers@dadla.UUCP (Roger Southwick) (11/27/84)
<HACKING MAKES ME FEEL GOO-OO-OOD!!> A few days (a week or two) ago I posted a advertisment for a nifty little program to change the modes of disabled tty devices to be 0666. And as promised (threatened maybe), if I got mode than 5 requests for it, I'd post it. Well I got the requests, so here it is! Thanks to all who responded to my article- -Roger --- cut here and place in it's own directory, then feed to Bourne shell --- # This is a shell archive. Remove anything before this line, then # unpack it by saving it in a file and typing "sh file". (Files # unpacked will be owned by you and have default permissions.) # # This archive contains: # READ_ME chttys.c chttys.8 ttymodes.5 ttymodes echo x - READ_ME cat > "READ_ME" << '//E*O*F READ_ME//' The chttys program By: Roger S. Southwick Logic Analyzers Computer Resource Group Tektronix, Inc. DISCLAIMER: This software is considered PUBLIC DOMAIN, and may be copied and/or modified without consent of the author, or Tektronix, Inc. The author (or Tektronix, Inc), assume no responsibility either written or implied for the software. Installation notes: 1a) Edit the file chttys.c, and set MODEFILE to be a location on your system you'ld like the ttymodes file to be. This file is described in the ttymodes.5 man page, and if you change the location of the ttymodes file, be sure and change the ttymodes.5 and the chttys.8 man page. This is originally set to be /etc/ttymodes. 1b) Also, change LL to be the path of the "ls -l" for your system. This is used under the -l option of the chttys command. See the chttys.8 man page for description of the option. 2) Compile chttys.c into object: cc -O -s -o chttys chttys.c This does work on PDP11's (2.8 BSD) and Vaxen (4.1 BSD), so I assume most all Unixes will work with this code. 3) Move chttys to live in someplace like /etc, as it is intended for use by the super user (see GENERAL NOTES 1 & 2) 4) Copy the chttys.8 and ttymodes.5 into apropos spots. GENERAL NOTES: 1) The chttys program must be run by root (so it can do a chmod() on the tty devices) although it does check this fact. One therefore could make it suid root, but this is not advised. 2) If your system is like ours, we have a shell script which does the apropos "kill -N 1" for this system (since we have 3 PDP's with 2.8 (and use kill -2 1), and a Vax with 4.1 (and use kill -1 1)). The rdttys program can be added to the shell script, and no more mode troubles (except the MODEFILE editing) should happen. 3) The main reason for using the chttys program over simple lines of "chmod 0666 /dev/tty??" in the above shell script, is that the list of ttys is more or less dynamic, and therefore is a pain to keep track of. The ttys which you'll describe in the ttymodes file are probably ones for uucp, printer ports, and so on, which are turned off and not mode 0666 (i.e. more of the permanent installation type critters). 4) I have included a sample ttymodes file in this directory for your enjoyment, but of course our tty names are probably different than yours. 5) I will be happy to consult (via E-mail) with anyone having questions and/or problems (within reason). If any bugs are discovered, mail them to me as well. Good Luck... Roger Southwick UUCP: HOST!tektronix!dadla!rogers Where HOST is any one of: masscomp,decvax,allegra,uf-cgrl,mit-eddie,mit-ems, uoregon,psu-cs,orstcs,zehntel,ucbcad,ucbvax,purdue, uw-beaver,reed,ogcvax,ihnp4,tekred,minn-ua,cbosg CSnet: rogers%dadla@tektronix ARPAnet: rogers%dadla%tektronix@csnet-relay BELLnet (phone): (503)-629-1911 SNAILnet (U.S. Mail): Roger Southwick Tektronix, Inc. P.O. Box 4600, D.S. 92-731 Beaverton, Oregon 97075 //E*O*F READ_ME// echo x - chttys.c cat > "chttys.c" << '//E*O*F chttys.c//' /*------------------------------------------------------------- The chttys program By: Roger S. Southwick Logic Analyzers Computer Resource Group Tektronix, Inc. November 19, 1984 DISCLAIMER: This software is considered PUBLIC DOMAIN, and may be copied and/or modified without consent of the author, or Tektronix, Inc. The author (or Tektronix, Inc), assume no responsibility either written or implied for the software. This program changes the permission modes of /dev/tty?? to be 666 when it is turned off in the /etc/ttys file. Usage: chttys [-v] [-l] [-V] Where: -v turns on verbose mode, echoing ttys as it changes them. -l does an ls -l of the ttys before and after mode change. -V turns on the very verbose mode (both -v and -l). The program will also consult the MODEFILE (usually set to be /etc/ttymodes), for any ttys described, and use the mode in the file instead of the default 666 mode. The format of the MODEFILE is: /dev/tty?? mode "mode" is an octal number representing the permission mode bits ala chmod(1) and chmod(2). Lines beginning with a ; (semicolon) or a newline are ignored in the MODEFILE, and can be used for comments. NOTES: 1) For your system, set MODEFILE and LL to be paths you wish. 2) This program must be run by root, although it does check this fact. One therefore could make it suid, but this is not advised. 3) If your system is like ours, we have a shell script which does the apropos "kill -N 1" for this system (since we have 3 PDP's with 2.8 (and use kill -2 1), and a Vax with 4.1 (use kill -1 1)). The rdttys program can be added to the shell script, and no more mode troubles (except the MODEFILE editing) should happen. --------------------------------------------------------------- * * MODIFICATION HISTORY: * * $Log$ * -------------------------------------------------------------*/ #include <stdio.h> #define MODEFILE "/etc/ttymodes" /* location of ttymodes */ #define LL "/usr/ucb/ls -l" /* location of ll cmd */ /* * ttymodes structure. Read from MODEFILE and stored in this linked list */ struct ttymode { char *t_tname; /* The tty name */ int t_tmode; /* The tty mode */ struct ttymode *t_next; /* Next tty structure */ }; /* * tty structure. Disabled ttys in /etc/ttys. */ struct ttys { char *tty_name; /* The tty name (minus /dev) */ struct ttys *tty_next; /* The next tty name */ }; main(argc, argv) int argc; char *argv[]; { int strcmp(), chmod(); struct ttys *rdttys(); struct ttymode *rdmodes(); register struct ttys *tty_top, *tt; register struct ttymode *tm_top, *tm; register int mode, verbose, list; register char *cp; char buf[BUFSIZ]; /* * Process the arguments. */ for(list = 0, verbose = 0; --argc > 0 && (*++argv)[0] == '-'; ){ for(cp = argv[0] + 1; *cp != '\0'; cp++){ switch(*cp){ case 'v': verbose = 1; break; case 'l': list = 1; break; case 'V': list = 1; verbose = 1; break; default: usage(); } } } if(argc != 0) usage(); tty_top = rdttys(); tm_top = rdmodes(); /* * Set up command for performing ls -l (if list flag is set) */ if(list == 1){ for(strcpy(buf, LL), tt = tty_top; tt != NULL; tt = tt->tty_next){ strcat(buf, " "); strcat(buf, tt->tty_name); } system(buf); } /* * For each tty in /etc/ttys which is turned off, compare * it to ones in MODEFILE. If in MODEFILE, use mode from * the file. Otherwise, use default 0666 mode. */ for(tt = tty_top; tt != NULL; tt = tt->tty_next){ for(mode = 0666, tm = tm_top; tm != NULL; tm = tm->t_next){ if(strcmp(tt->tty_name, tm->t_tname) == 0){ mode = tm->t_tmode; break; } } if(verbose == 1) printf("chttys: chmod(%s, 0%o) %s",tt->tty_name,mode,(mode != 0666)? "(special)\n" : "\n"); if(chmod(tt->tty_name, mode) == -1){ fprintf(stderr,"chttys: chmod(%s, 0%o) failed - ",tt->tty_name, mode); perror("chttys"); } } if(list == 1) system(buf); exit(0); } /* * Print usage, then die. */ usage() { fprintf(stderr,"usage: chttys [-v] [-l] [-V]\n"); exit(1); } /* * Read the /etc/ttys file into linked list, and return pointer * to the top of the linked list. */ struct ttys * rdttys() { FILE *fopen(); int fscanf(); struct ttys *ttylink(); register FILE *fp; register struct ttys *top = NULL; register int fi; char buf[30], buf2[60]; if((fp = fopen("/etc/ttys", "r")) == NULL){ fprintf(stderr,"chttys: could not open /etc/ttys\n"); exit(1); } while((fi = fscanf(fp, "%s", buf)) != EOF){ if(fi != 1){ fprintf(stderr,"chttys: format error in /etc/ttys\n"); continue; } if(buf[0] != '0') /* Ignore any enabled ttys */ continue; strcpy(buf2,"/dev/"); strcat(buf2, &buf[2]); /* Skip first 2 chars */ top = ttylink(top, buf2); } fclose(fp); return(top); } /* * Read MODEFILE into a linked list, and return pointer to top. * The MODEFILE may contain ; as leading character comment lines * (or blank lines), and they are ignored. */ struct ttymode * rdmodes() { FILE *fopen(); char *fgets(); int sscanf(), access(); struct ttymode *tlink(); register FILE *fp; register struct ttymode *top = NULL; register int fi; char buf[BUFSIZ], tbuf[30]; int mode; if(access(MODEFILE, 4) == -1){ return(NULL); } if((fp = fopen(MODEFILE, "r")) == NULL){ fprintf(stderr,"chttys: could not open %s\n",MODEFILE); exit(1); } while(fgets(buf, BUFSIZ, fp) != NULL){ if(buf[0] == '\n' || buf[0] == ';') /* Ignore comments */ continue; if(sscanf(buf, "%s %o", tbuf, &mode) != 2){ fprintf(stderr,"chttys: format error in %s\n",MODEFILE); continue; } top = tlink(top, tbuf, mode); } fclose(fp); return(top); } /* * Build a linked list of ttymode structures. */ struct ttymode * tlink(tm, name, mode) register struct ttymode *tm; register char *name; register int mode; { char *malloc(), *strsave(); if(tm == NULL){ tm = (struct ttymode *)malloc(sizeof(struct ttymode)); tm->t_tname = strsave(name); tm->t_tmode = mode; tm->t_next = NULL; } else tm->t_next = tlink(tm->t_next, name, mode); return(tm); } /* * Build a linked list of ttys structures. */ struct ttys * ttylink(tt, name) register struct ttys *tt; register char *name; { char *malloc(), *strsave(); if(tt == NULL){ tt = (struct ttys *)malloc(sizeof(struct ttys)); tt->tty_name = strsave(name); tt->tty_next = NULL; } else tt->tty_next = ttylink(tt->tty_next, name); return(tt); } /* * The strsave routine allocates some memory for the string * str, copies the string to that place and returns a pointer * to the place in memory. If passed a NULL pointer, a NULL * pointer is returned. */ char * strsave(str) register char *str; { int strlen(); char *malloc(); register char *cp; if(str == NULL) return(NULL); if((cp = (char *)malloc(strlen(str) + 1)) != NULL) strcpy(cp, str); return(cp); } //E*O*F chttys.c// echo x - chttys.8 cat > "chttys.8" << '//E*O*F chttys.8//' .TH CHTTYS 8 .UC 4 .SH NAME chttys \- change modes of ttys .SH SYNOPSIS .B chttys [-vlV] .SH DESCRIPTION .PP .I Chttys changes the modes of the ttys which have been made non-loginable in the /etc/ttys file to be 0666 (rw-rw-rw-). The mode can be made to be any value by placing an entry in the /etc/ttymodes file, discussed below. .PP .I Chttys will do it's work silently, unless one (or more) of the options are given. The options are: .IP .B \-v verbose mode: This basically will output a message showing which ttys are changing and to what mode they will be. The text .B (special) denotes the mode was described in the /etc/ttymodes file. .IP .B \-l list mode: This makes the program provide an ls -l of the ttys before and after the mode change happens. .IP .B \-V very verbose mode: This makes the program do both the .B \-v and the .B \-l option. .PP The .I chttys program can also change the modes on the disabled ttys to be a mode other than 0666. This is done by reading the file .B /etc/ttymodes and using the listed devices and their corresponding modes. .PP The .B /etc/ttymodes file consists of two fields, one with the complete path of the device, and the OCTAL mode for the device. .PP The .B /etc/ttymodes file is described and exampled in ttymodes(5). .SH FILES /etc/ttys .br /etc/ttymodes .SH AUTHOR Roger Southwick .br Logic Analyzers Computer Resource Group .br Tektronix, Inc. .SH BUGS To be discovered. .SH "SEE ALSO" chmod(1), chmod(2), ttymodes(5) //E*O*F chttys.8// echo x - ttymodes.5 cat > "ttymodes.5" << '//E*O*F ttymodes.5//' .TH TTYMODES 5 .UC 4 .SH NAME ttymodes \- permission modes for tty devices .SH DESCRIPTION .PP The .I ttymodes file is read by the .B chttys program and specifies the permission modes to which ttys are changed. .PP The file consists of either comment lines or information lines. Comment lines are defined as lines beginning with a semicolon or a newline character. Information lines have two fields with the complete path of the tty, and the OCTAL mode the tty should be. .PP It is important to note that only terminals which are disabled (i.e non-loginable) need be in this file, as all other entries are ignored. .PP Here is an example .I ttymodes file: .RS .br ; .br ; This file is read by the chttys program to set modes .br ; for terminals to be other than the default 0666. .br ; .br ; Note that the format is 2 fields, one of the device .br ; name (complete path), and the other an OCTAL number .br ; which will become the device's mode. .br ; .br ; Lines starting with a semicolon or a newline are .br ; ignored and can be used as comments. .br ; .br .br /dev/ttyv3 0600 .br /dev/ttyu6 0622 .br /dev/ttyu7 0622 .RE .SH FILES /etc/ttymodes .SH AUTHOR Roger Southwick .br Logic Analyzers Computer Resource Group .br Tektronix, Inc. .SH BUGS To be discovered. .SH "SEE ALSO" chmod(1), chmod(2), chttys(8) //E*O*F ttymodes.5// echo x - ttymodes cat > "ttymodes" << '//E*O*F ttymodes//' ; ; This file is read by the chttys program to set modes for ; terminals to be other than the default 0666. ; ; Note that the format is 2 fields, one of the device name ; (complete path), and the other an OCTAL number which will ; become the device's mode. ; ; Lines starting with a semicolon or a newline are ignored ; and can be used as comments. ; /dev/ttyv3 0600 /dev/ttyu6 0622 /dev/ttyu7 0622 //E*O*F ttymodes// echo Possible errors detected by \'wc\' [hopefully none]: temp=/tmp/shar$$ trap "rm -f $temp; exit" 0 1 2 3 15 cat > $temp <<\!!! 93 484 2973 READ_ME 353 1047 7344 chttys.c 65 263 1481 chttys.8 72 239 1314 ttymodes.5 15 79 400 ttymodes 598 2112 13512 total !!! wc READ_ME chttys.c chttys.8 ttymodes.5 ttymodes | sed 's=[^ ]*/==' | diff -b $temp - exit 0