1*c1e8532bStholo /* $OpenBSD: ttyflags.c,v 1.5 1996/10/30 08:17:05 tholo Exp $ */ 2f3bae140Sderaadt /* $NetBSD: ttyflags.c,v 1.8 1996/04/09 05:20:30 cgd Exp $ */ 3df930be7Sderaadt 4df930be7Sderaadt /* 546f3f978Sderaadt * Copyright (c) 1996 Theo de Raadt 6df930be7Sderaadt * Copyright (c) 1994 Christopher G. Demetriou 7df930be7Sderaadt * All rights reserved. 8df930be7Sderaadt * 9df930be7Sderaadt * Redistribution and use in source and binary forms, with or without 10df930be7Sderaadt * modification, are permitted provided that the following conditions 11df930be7Sderaadt * are met: 12df930be7Sderaadt * 1. Redistributions of source code must retain the above copyright 13df930be7Sderaadt * notice, this list of conditions and the following disclaimer. 14df930be7Sderaadt * 2. Redistributions in binary form must reproduce the above copyright 15df930be7Sderaadt * notice, this list of conditions and the following disclaimer in the 16df930be7Sderaadt * documentation and/or other materials provided with the distribution. 17df930be7Sderaadt * 3. All advertising materials mentioning features or use of this software 18df930be7Sderaadt * must display the following acknowledgement: 19df930be7Sderaadt * This product includes software developed by Christopher G. Demetriou. 20df930be7Sderaadt * 4. The name of the author may not be used to endorse or promote products 21df930be7Sderaadt * derived from this software without specific prior written permission 22df930be7Sderaadt * 23df930be7Sderaadt * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR 24df930be7Sderaadt * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES 25df930be7Sderaadt * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. 26df930be7Sderaadt * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, 27df930be7Sderaadt * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT 28df930be7Sderaadt * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 29df930be7Sderaadt * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 30df930be7Sderaadt * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 31df930be7Sderaadt * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF 32df930be7Sderaadt * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 33df930be7Sderaadt */ 34df930be7Sderaadt 35df930be7Sderaadt #ifndef lint 36df930be7Sderaadt char copyright[] = 37df930be7Sderaadt "@(#) Copyright (c) 1994 Christopher G. Demetriou\n\ 38df930be7Sderaadt All rights reserved.\n"; 39df930be7Sderaadt #endif /* not lint */ 40df930be7Sderaadt 41df930be7Sderaadt #ifndef lint 42*c1e8532bStholo static char rcsid[] = "$OpenBSD: ttyflags.c,v 1.5 1996/10/30 08:17:05 tholo Exp $"; 43df930be7Sderaadt #endif /* not lint */ 44df930be7Sderaadt 45df930be7Sderaadt #include <sys/types.h> 46df930be7Sderaadt #include <sys/cdefs.h> 47df930be7Sderaadt #include <sys/ioctl.h> 48df930be7Sderaadt 49df930be7Sderaadt #include <err.h> 50df930be7Sderaadt #include <errno.h> 51df930be7Sderaadt #include <fcntl.h> 52df930be7Sderaadt #include <limits.h> 53df930be7Sderaadt #include <paths.h> 54df930be7Sderaadt #include <stdio.h> 55df930be7Sderaadt #include <stdlib.h> 56f3bae140Sderaadt #include <string.h> 57df930be7Sderaadt #include <ttyent.h> 58df930be7Sderaadt #include <unistd.h> 59df930be7Sderaadt 6046f3f978Sderaadt int all __P((int)); 6146f3f978Sderaadt int ttys __P((char **, int)); 6246f3f978Sderaadt int ttyflags __P((struct ttyent *, int)); 63df930be7Sderaadt void usage __P((void)); 64df930be7Sderaadt 65df930be7Sderaadt int nflag, vflag; 66df930be7Sderaadt 67df930be7Sderaadt /* 68df930be7Sderaadt * Ttyflags sets the device-specific tty flags, based on the contents 69df930be7Sderaadt * of /etc/ttys. It can either set all of the ttys' flags, or set 70df930be7Sderaadt * the flags of the ttys specified on the command line. 71df930be7Sderaadt */ 72df930be7Sderaadt int 73df930be7Sderaadt main(argc, argv) 74df930be7Sderaadt int argc; 75df930be7Sderaadt char *argv[]; 76df930be7Sderaadt { 7746f3f978Sderaadt int aflag, ch, rval, pflag = 0; 78df930be7Sderaadt 79df930be7Sderaadt aflag = nflag = vflag = 0; 8046f3f978Sderaadt while ((ch = getopt(argc, argv, "panv")) != EOF) 81df930be7Sderaadt switch (ch) { 82df930be7Sderaadt case 'a': 83df930be7Sderaadt aflag = 1; 84df930be7Sderaadt break; 85df930be7Sderaadt case 'n': /* undocumented */ 86df930be7Sderaadt nflag = 1; 87df930be7Sderaadt break; 8846f3f978Sderaadt case 'p': 8946f3f978Sderaadt pflag = 1; 9046f3f978Sderaadt break; 91df930be7Sderaadt case 'v': 92df930be7Sderaadt vflag = 1; 93df930be7Sderaadt break; 94df930be7Sderaadt case '?': 95df930be7Sderaadt default: 96df930be7Sderaadt usage(); 97df930be7Sderaadt } 98df930be7Sderaadt argc -= optind; 99df930be7Sderaadt argv += optind; 100df930be7Sderaadt 101df930be7Sderaadt if (aflag && argc != 0) 102df930be7Sderaadt usage(); 103df930be7Sderaadt 104df930be7Sderaadt if (setttyent() == 0) 105df930be7Sderaadt err(1, "setttyent"); 106df930be7Sderaadt 107df930be7Sderaadt if (aflag) 10846f3f978Sderaadt rval = all(pflag); 109df930be7Sderaadt else 11046f3f978Sderaadt rval = ttys(argv, pflag); 111df930be7Sderaadt 112df930be7Sderaadt if (endttyent() == 0) 113df930be7Sderaadt warn("endttyent"); 114df930be7Sderaadt 115df930be7Sderaadt exit(rval); 116df930be7Sderaadt } 117df930be7Sderaadt 118df930be7Sderaadt /* 119df930be7Sderaadt * Change all /etc/ttys entries' flags. 120df930be7Sderaadt */ 121df930be7Sderaadt int 12246f3f978Sderaadt all(print) 12346f3f978Sderaadt int print; 124df930be7Sderaadt { 125df930be7Sderaadt struct ttyent *tep; 126df930be7Sderaadt int rval; 127df930be7Sderaadt 128df930be7Sderaadt rval = 0; 129df930be7Sderaadt for (tep = getttyent(); tep != NULL; tep = getttyent()) 13046f3f978Sderaadt if (ttyflags(tep, print)) 131df930be7Sderaadt rval = 1; 132df930be7Sderaadt return (rval); 133df930be7Sderaadt } 134df930be7Sderaadt 135df930be7Sderaadt /* 136df930be7Sderaadt * Change the specified ttys' flags. 137df930be7Sderaadt */ 138df930be7Sderaadt int 13946f3f978Sderaadt ttys(ttylist, print) 140df930be7Sderaadt char **ttylist; 14146f3f978Sderaadt int print; 142df930be7Sderaadt { 143df930be7Sderaadt struct ttyent *tep; 144df930be7Sderaadt int rval; 145df930be7Sderaadt 146df930be7Sderaadt rval = 0; 147df930be7Sderaadt for (; *ttylist != NULL; ttylist++) { 148df930be7Sderaadt tep = getttynam(*ttylist); 149df930be7Sderaadt if (tep == NULL) { 150df930be7Sderaadt warnx("couldn't find an entry in %s for \"%s\"", 151df930be7Sderaadt _PATH_TTYS, *ttylist); 152df930be7Sderaadt rval = 1; 153df930be7Sderaadt continue; 154df930be7Sderaadt } 155df930be7Sderaadt 15646f3f978Sderaadt if (ttyflags(tep, print)) 157df930be7Sderaadt rval = 1; 158df930be7Sderaadt } 159df930be7Sderaadt return (rval); 160df930be7Sderaadt } 161df930be7Sderaadt 162f3bae140Sderaadt 163df930be7Sderaadt /* 164f3bae140Sderaadt * Actually do the work; find out what the new flags value should be, 165df930be7Sderaadt * open the device, and change the flags. 166df930be7Sderaadt */ 167df930be7Sderaadt int 16846f3f978Sderaadt ttyflags(tep, print) 169df930be7Sderaadt struct ttyent *tep; 17046f3f978Sderaadt int print; 171df930be7Sderaadt { 172*c1e8532bStholo int fd, flags = 0, rval = 0, st, sep = 0; 173df930be7Sderaadt char path[PATH_MAX]; 174*c1e8532bStholo char strflags[256]; 175*c1e8532bStholo 176*c1e8532bStholo st = tep->ty_status; 177*c1e8532bStholo strflags[0] = '\0'; 178df930be7Sderaadt 17946f3f978Sderaadt if (print == 0) { 180df930be7Sderaadt /* Convert ttyent.h flags into ioctl flags. */ 181f3bae140Sderaadt if (st & TTY_LOCAL) { 182df930be7Sderaadt flags |= TIOCFLAG_CLOCAL; 183f3bae140Sderaadt (void)strcat(strflags, "local"); 184f3bae140Sderaadt sep++; 185f3bae140Sderaadt } 186f3bae140Sderaadt if (st & TTY_RTSCTS) { 187df930be7Sderaadt flags |= TIOCFLAG_CRTSCTS; 188f3bae140Sderaadt if (sep++) 189f3bae140Sderaadt (void)strcat(strflags, "|"); 190f3bae140Sderaadt (void)strcat(strflags, "rtscts"); 191f3bae140Sderaadt } 192f3bae140Sderaadt if (st & TTY_SOFTCAR) { 193df930be7Sderaadt flags |= TIOCFLAG_SOFTCAR; 194f3bae140Sderaadt if (sep++) 195f3bae140Sderaadt (void)strcat(strflags, "|"); 196f3bae140Sderaadt (void)strcat(strflags, "softcar"); 197f3bae140Sderaadt } 198f3bae140Sderaadt if (st & TTY_MDMBUF) { 199df930be7Sderaadt flags |= TIOCFLAG_MDMBUF; 200f3bae140Sderaadt if (sep++) 201f3bae140Sderaadt (void)strcat(strflags, "|"); 202f3bae140Sderaadt (void)strcat(strflags, "mdmbuf"); 203f3bae140Sderaadt } 20446f3f978Sderaadt if (vflag) 20546f3f978Sderaadt printf("%s setting flags to: %s\n", path, strflags); 20646f3f978Sderaadt } 207df930be7Sderaadt 208df930be7Sderaadt /* Find the full device path name. */ 209df930be7Sderaadt (void)snprintf(path, sizeof path, "%s%s", _PATH_DEV, tep->ty_name); 210df930be7Sderaadt 211df930be7Sderaadt if (nflag) 212df930be7Sderaadt return (0); 213df930be7Sderaadt 214df930be7Sderaadt /* Open the device NON-BLOCKING, set the flags, and close it. */ 215df930be7Sderaadt if ((fd = open(path, O_RDONLY | O_NONBLOCK, 0)) == -1) { 216df930be7Sderaadt if (!(errno == ENXIO || 217df930be7Sderaadt (errno == ENOENT && (st & TTY_ON) == 0))) 218df930be7Sderaadt rval = 1; 21946f3f978Sderaadt if (vflag) 220df930be7Sderaadt warn("open %s", path); 221df930be7Sderaadt return (rval); 222df930be7Sderaadt } 22346f3f978Sderaadt if (print == 0) { 224df930be7Sderaadt if (ioctl(fd, TIOCSFLAGS, &flags) == -1) 225df930be7Sderaadt if (errno != ENOTTY || vflag) { 226df930be7Sderaadt warn("TIOCSFLAGS on %s", path); 227df930be7Sderaadt rval = (errno != ENOTTY); 228df930be7Sderaadt } 22946f3f978Sderaadt } else { 23046f3f978Sderaadt if (ioctl(fd, TIOCGFLAGS, &flags) == -1) 23146f3f978Sderaadt if (errno != ENOTTY || vflag) { 23246f3f978Sderaadt warn("TIOCSFLAGS on %s", path); 23346f3f978Sderaadt rval = (errno != ENOTTY); 23446f3f978Sderaadt } 23546f3f978Sderaadt if (flags & TIOCFLAG_CLOCAL) { 23646f3f978Sderaadt (void)strcat(strflags, "local"); 23746f3f978Sderaadt sep++; 23846f3f978Sderaadt } 23946f3f978Sderaadt if (flags & TIOCFLAG_CRTSCTS) { 24046f3f978Sderaadt if (sep++) 24146f3f978Sderaadt (void)strcat(strflags, "|"); 24246f3f978Sderaadt (void)strcat(strflags, "rtscts"); 24346f3f978Sderaadt } 24446f3f978Sderaadt if (flags & TIOCFLAG_SOFTCAR) { 24546f3f978Sderaadt if (sep++) 24646f3f978Sderaadt (void)strcat(strflags, "|"); 24746f3f978Sderaadt (void)strcat(strflags, "softcar"); 24846f3f978Sderaadt } 24946f3f978Sderaadt if (flags & TIOCFLAG_MDMBUF) { 25046f3f978Sderaadt if (sep++) 25146f3f978Sderaadt (void)strcat(strflags, "|"); 25246f3f978Sderaadt (void)strcat(strflags, "mdmbuf"); 25346f3f978Sderaadt } 25446f3f978Sderaadt printf("%s flags are: %s\n", path, strflags); 25546f3f978Sderaadt } 256df930be7Sderaadt if (close(fd) == -1) { 257df930be7Sderaadt warn("close %s", path); 258df930be7Sderaadt return (1); 259df930be7Sderaadt } 260df930be7Sderaadt return (rval); 261df930be7Sderaadt } 262df930be7Sderaadt 263df930be7Sderaadt /* 264df930be7Sderaadt * Print usage information when a bogus set of arguments is given. 265df930be7Sderaadt */ 266df930be7Sderaadt void 267df930be7Sderaadt usage() 268df930be7Sderaadt { 26946f3f978Sderaadt (void)fprintf(stderr, "usage: ttyflags [-v] [-p] [-a | tty ... ]\n"); 270df930be7Sderaadt exit(1); 271df930be7Sderaadt } 272