Annotation of 43BSDReno/usr.sbin/sliplogin/sliplogin.c, revision 1.1

1.1     ! root        1: /*-
        !             2:  * Copyright (c) 1990 The Regents of the University of California.
        !             3:  * All rights reserved.
        !             4:  *
        !             5:  * Redistribution and use in source and binary forms are permitted provided
        !             6:  * that: (1) source distributions retain this entire copyright notice and
        !             7:  * comment, and (2) distributions including binaries display the following
        !             8:  * acknowledgement:  ``This product includes software developed by the
        !             9:  * University of California, Berkeley and its contributors'' in the
        !            10:  * documentation or other materials provided with the distribution and in
        !            11:  * all advertising materials mentioning features or use of this software.
        !            12:  * Neither the name of the University nor the names of its contributors may
        !            13:  * be used to endorse or promote products derived from this software without
        !            14:  * specific prior written permission.
        !            15:  * THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR IMPLIED
        !            16:  * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
        !            17:  * MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.
        !            18:  */
        !            19: 
        !            20: #ifndef lint
        !            21: char copyright[] =
        !            22: "@(#) Copyright (c) 1990 The Regents of the University of California.\n\
        !            23:  All rights reserved.\n";
        !            24: #endif /* not lint */
        !            25: 
        !            26: #ifndef lint
        !            27: static char sccsid[] = "@(#)sliplogin.c        5.3 (Berkeley) 7/1/90";
        !            28: #endif /* not lint */
        !            29: 
        !            30: /*
        !            31:  * sliplogin.c
        !            32:  * [MUST BE RUN SUID, SLOPEN DOES A SUSER()!]
        !            33:  *
        !            34:  * This program initializes its own tty port to be an async TCP/IP interface.
        !            35:  * It sets the line discipline to slip, invokes a shell script to initialize
        !            36:  * the network interface, then pauses forever waiting for hangup.
        !            37:  *
        !            38:  * It is a remote descendant of several similar programs with incestuous ties:
        !            39:  * - Kirk Smith's slipconf, modified by Richard Johnsson @ DEC WRL.
        !            40:  * - slattach, probably by Rick Adams but touched by countless hordes.
        !            41:  * - the original sliplogin for 4.2bsd, Doug Kingston the mover behind it.
        !            42:  *
        !            43:  * There are two forms of usage:
        !            44:  *
        !            45:  * "sliplogin"
        !            46:  * Invoked simply as "sliplogin" and a realuid != 0, the program looks up
        !            47:  * the uid in /etc/passwd, and then the username in the file /etc/hosts.slip.
        !            48:  * If and entry is found, the line on fd0 is configured for SLIP operation
        !            49:  * as specified in the file.
        !            50:  *
        !            51:  * "sliplogin IPhost1 </dev/ttyb"
        !            52:  * Invoked by root with a username, the name is looked up in the
        !            53:  * /etc/hosts.slip file and if found fd0 is configured as in case 1.
        !            54:  */
        !            55: 
        !            56: #include <sys/param.h>
        !            57: #include <sys/socket.h>
        !            58: #include <sys/ioctl.h>
        !            59: #include <sys/signal.h>
        !            60: #include <sys/file.h>
        !            61: #include <sys/syslog.h>
        !            62: #include <netdb.h>
        !            63: 
        !            64: #if defined(BSD4_4)
        !            65: #define TERMIOS
        !            66: #endif
        !            67: #ifdef TERMIOS
        !            68: #include <sys/termios.h>
        !            69: #include <ttyent.h>
        !            70: #endif
        !            71: #include <netinet/in.h>
        !            72: #include <net/if.h>
        !            73: #include <net/if_slvar.h>
        !            74: 
        !            75: #include <stdio.h>
        !            76: #include <errno.h>
        !            77: #include <ctype.h>
        !            78: #include <string.h>
        !            79: #include "pathnames.h"
        !            80: 
        !            81: int    unit;
        !            82: int    slip_mode;
        !            83: int    speed;
        !            84: char   loginargs[BUFSIZ];
        !            85: char   loginfile[BUFSIZ];
        !            86: char   logoutfile[BUFSIZ];
        !            87: char   loginname[BUFSIZ];
        !            88: 
        !            89: struct slip_modes {
        !            90:        char    *sm_name;
        !            91:        int     sm_value;
        !            92: }       modes[] = {
        !            93:        "normal",       0,              
        !            94:        "compress",     SC_COMPRESS,   
        !            95:        "noicmp",       SC_NOICMP,
        !            96:        "autocomp",     SC_AUTOCOMP
        !            97: };
        !            98: 
        !            99: void
        !           100: findid(name)
        !           101:        char *name;
        !           102: {
        !           103:        FILE *fp;
        !           104:        static char slopt[5][16];
        !           105:        static char laddr[16];
        !           106:        static char raddr[16];
        !           107:        static char mask[16];
        !           108:        char user[16];
        !           109:        int i, j, n;
        !           110: 
        !           111:        (void)strcpy(loginname, name);
        !           112:        if ((fp = fopen(_PATH_ACCESS, "r")) == NULL) {
        !           113:                (void)fprintf(stderr, "sliplogin: %s: %s\n",
        !           114:                    _PATH_ACCESS, strerror(errno));
        !           115:                syslog(LOG_ERR, "%s: %m\n", _PATH_ACCESS);
        !           116:                exit(1);
        !           117:        }
        !           118:        while (fgets(loginargs, sizeof(loginargs) - 1, fp)) {
        !           119:                if (ferror(fp))
        !           120:                        break;
        !           121:                n = sscanf(loginargs, "%15s%*[ \t]%15s%*[ \t]%15s%*[ \t]%15s%*[ \t]%15s%*[ \t]%15s%*[ \t]%15s%*[ \t]%15s%*[ \t]%15s\n",
        !           122:                         user, laddr, raddr, mask, slopt[0], slopt[1], 
        !           123:                        slopt[2], slopt[3], slopt[4]);
        !           124:                if (user[0] == '#' || isspace(user[0]))
        !           125:                        continue;
        !           126:                if (strcmp(user, name) != 0)
        !           127:                        continue;
        !           128: 
        !           129:                slip_mode = 0;
        !           130:                for (i = 0; i < n - 4; i++) {
        !           131:                        for (j = 0; j < sizeof(modes)/sizeof(struct slip_modes);
        !           132:                                j++) {
        !           133:                                if (strcmp(modes[j].sm_name, slopt[i]) == 0) {
        !           134:                                        slip_mode |= modes[j].sm_value;
        !           135:                                        break;
        !           136:                                }
        !           137:                        }
        !           138:                }
        !           139: 
        !           140:                /*
        !           141:                 * we've found the guy we're looking for -- see if
        !           142:                 * there's a login file we can use.  First check for
        !           143:                 * one specific to this host.  If none found, try for
        !           144:                 * a generic one.
        !           145:                 */
        !           146:                (void)sprintf(loginfile, "%s.%s", _PATH_LOGIN, name);
        !           147:                if (access(loginfile, R_OK|X_OK)) {
        !           148:                        (void)strcpy(loginfile, _PATH_LOGIN);
        !           149:                        (void)strcpy(logoutfile, _PATH_LOGOUT);
        !           150:                        if (access(loginfile, R_OK|X_OK)) {
        !           151:                                fputs("access denied - no login file\n",
        !           152:                                      stderr);
        !           153:                                syslog(LOG_ERR,
        !           154:                                       "access denied for %s - no %s\n",
        !           155:                                       name, _PATH_LOGIN);
        !           156:                                exit(5);
        !           157:                        }
        !           158:                } else
        !           159:                        (void)sprintf(logoutfile, "%s.%s", _PATH_LOGOUT, name);
        !           160: 
        !           161:                (void) fclose(fp);
        !           162:                return;
        !           163:        }
        !           164:        (void)fprintf(stderr, "SLIP access denied for %s\n", name);
        !           165:        syslog(LOG_ERR, "SLIP access denied for %s\n", name);
        !           166:        exit(4);
        !           167:        /* NOTREACHED */
        !           168: }
        !           169: 
        !           170: char *
        !           171: sigstr(s)
        !           172:        int s;
        !           173: {
        !           174:        static char buf[32];
        !           175: 
        !           176:        switch (s) {
        !           177:        case SIGHUP:    return("HUP");
        !           178:        case SIGINT:    return("INT");
        !           179:        case SIGQUIT:   return("QUIT");
        !           180:        case SIGILL:    return("ILL");
        !           181:        case SIGTRAP:   return("TRAP");
        !           182:        case SIGIOT:    return("IOT");
        !           183:        case SIGEMT:    return("EMT");
        !           184:        case SIGFPE:    return("FPE");
        !           185:        case SIGKILL:   return("KILL");
        !           186:        case SIGBUS:    return("BUS");
        !           187:        case SIGSEGV:   return("SEGV");
        !           188:        case SIGSYS:    return("SYS");
        !           189:        case SIGPIPE:   return("PIPE");
        !           190:        case SIGALRM:   return("ALRM");
        !           191:        case SIGTERM:   return("TERM");
        !           192:        case SIGURG:    return("URG");
        !           193:        case SIGSTOP:   return("STOP");
        !           194:        case SIGTSTP:   return("TSTP");
        !           195:        case SIGCONT:   return("CONT");
        !           196:        case SIGCHLD:   return("CHLD");
        !           197:        case SIGTTIN:   return("TTIN");
        !           198:        case SIGTTOU:   return("TTOU");
        !           199:        case SIGIO:     return("IO");
        !           200:        case SIGXCPU:   return("XCPU");
        !           201:        case SIGXFSZ:   return("XFSZ");
        !           202:        case SIGVTALRM: return("VTALRM");
        !           203:        case SIGPROF:   return("PROF");
        !           204:        case SIGWINCH:  return("WINCH");
        !           205: #ifdef SIGLOST
        !           206:        case SIGLOST:   return("LOST");
        !           207: #endif
        !           208:        case SIGUSR1:   return("USR1");
        !           209:        case SIGUSR2:   return("USR2");
        !           210:        }
        !           211:        (void)sprintf(buf, "sig %d", s);
        !           212:        return(buf);
        !           213: }
        !           214: 
        !           215: int
        !           216: hup_handler(s)
        !           217:        int s;
        !           218: {
        !           219:        if (access(logoutfile, R_OK|X_OK) == 0) {
        !           220:                char logincmd[2*BUFSIZ+32];
        !           221: 
        !           222:                (void)sprintf(logincmd, "%s %d %d %s", logoutfile, unit, speed,
        !           223:                              loginargs);
        !           224:                (void)system(logincmd);
        !           225:        }
        !           226:        (void)close(0);
        !           227:        syslog(LOG_INFO, "closed %s slip unit %d (%s)\n", loginname, unit,
        !           228:               sigstr(s));
        !           229:        exit(1);
        !           230:        /* NOTREACHED */
        !           231: }
        !           232: 
        !           233: main(argc, argv)
        !           234:        int argc;
        !           235:        char *argv[];
        !           236: {
        !           237:        int     fd, s, ldisc, odisc;
        !           238:        char *name;
        !           239: #ifdef TERMIOS
        !           240:        struct  termios tios, otios;
        !           241: #else
        !           242:        struct  sgttyb tty, otty;
        !           243: #endif
        !           244:        char logincmd[2*BUFSIZ+32];
        !           245:        extern uid_t getuid();
        !           246: 
        !           247:        if ((name = strrchr(argv[0], '/')) == NULL)
        !           248:                name = argv[0];
        !           249:        s = getdtablesize();
        !           250:        for (fd = 3 ; fd < s ; fd++)
        !           251:                (void) close(fd);
        !           252:        openlog(name, LOG_PID, LOG_DAEMON);
        !           253:        if (argc > 1) {
        !           254:                if (argc > 2) {
        !           255:                        (void)fprintf(stderr, "Usage: %s loginname\n", argv[0]);
        !           256:                        exit(1);
        !           257:                }
        !           258:                findid(argv[1]);
        !           259: 
        !           260:                /*
        !           261:                 * Disassociate from current controlling terminal, if any,
        !           262:                 * and ensure that the slip line is our controlling terminal.
        !           263:                 */
        !           264: #ifdef TERMIOS
        !           265:                (void) setsid();
        !           266:                (void) ioctl(0, TIOCSCTTY, (caddr_t)0);
        !           267: #else
        !           268:                if ((fd = open("/dev/tty", O_RDONLY, 0)) >= 0) {
        !           269:                        extern char *ttyname();
        !           270: 
        !           271:                        (void) ioctl(fd, TIOCNOTTY, (caddr_t)0);
        !           272:                        (void) close(fd);
        !           273:                        /* open slip tty again to acquire as controlling tty? */
        !           274:                        fd = open(ttyname(0), O_RDWR, 0);
        !           275:                        if (fd >= 0)
        !           276:                                (void) close(fd);
        !           277:                }
        !           278:                (void) setpgrp(0, getpid());
        !           279: #endif
        !           280:        } else {
        !           281:                extern char *getenv();
        !           282: 
        !           283:                if ((name = getenv("USER")) == NULL) {
        !           284:                        (void) fprintf(stderr, "access denied - no username\n");
        !           285:                        syslog(LOG_ERR, "access denied - no username\n");
        !           286:                        exit(1);
        !           287:                }
        !           288:                findid(name);
        !           289:        }
        !           290:        (void) fchmod(0, 0600);
        !           291:        (void) fprintf(stderr, "starting slip login for %s\n", loginname);
        !           292: #ifdef TERMIOS
        !           293:        /* set up the line parameters */
        !           294:        if (ioctl(0, TIOCGETA, (caddr_t)&tios) < 0) {
        !           295:                syslog(LOG_ERR, "ioctl (TIOCGETA): %m");
        !           296:                exit(1);
        !           297:        }
        !           298:        otios = tios;
        !           299:        tios.c_cflag = CS8|CREAD|HUPCL;
        !           300:        tios.c_iflag = IGNBRK;
        !           301:        tios.c_oflag = tios.c_lflag = 0;
        !           302:        if (ioctl(0, TIOCSETA, (caddr_t)&tios) < 0) {
        !           303:                syslog(LOG_ERR, "ioctl (TIOCSETA) (1): %m");
        !           304:                exit(1);
        !           305:        }
        !           306: #else
        !           307:        /* set up the line parameters */
        !           308:        if (ioctl(0, TIOCGETP, (caddr_t)&tty) < 0) {
        !           309:                syslog(LOG_ERR, "ioctl (TIOCGETP): %m");
        !           310:                exit(1);
        !           311:        }
        !           312:        otty = tty;
        !           313:        speed = tty.sg_ispeed;
        !           314:        tty.sg_flags = RAW | ANYP;
        !           315:        if (ioctl(0, TIOCSETP, (caddr_t)&tty) < 0) {
        !           316:                syslog(LOG_ERR, "ioctl (TIOCSETP): %m");
        !           317:                exit(1);
        !           318:        }
        !           319: #endif
        !           320:        /* find out what ldisc we started with */
        !           321:        if (ioctl(0, TIOCGETD, (caddr_t)&odisc) < 0) {
        !           322:                syslog(LOG_ERR, "ioctl(TIOCGETD) (1): %m");
        !           323:                exit(1);
        !           324:        }
        !           325:        ldisc = SLIPDISC;
        !           326:        if (ioctl(0, TIOCSETD, (caddr_t)&ldisc) < 0) {
        !           327:                syslog(LOG_ERR, "ioctl(TIOCSETD): %m");
        !           328:                exit(1);
        !           329:        }
        !           330:        /* find out what unit number we were assigned */
        !           331:        if (ioctl(0, TIOCGETD, (caddr_t)&unit) < 0) {
        !           332:                syslog(LOG_ERR, "ioctl (TIOCGETD) (2): %m");
        !           333:                exit(1);
        !           334:        }
        !           335:        (void) signal(SIGHUP, hup_handler);
        !           336:        (void) signal(SIGTERM, hup_handler);
        !           337: 
        !           338:        syslog(LOG_INFO, "attaching slip unit %d for %s\n", unit, loginname);
        !           339:        (void)sprintf(logincmd, "%s %d %d %s", loginfile, unit, speed,
        !           340:                      loginargs);
        !           341:        /*
        !           342:         * aim stdout and errout at /dev/null so logincmd output won't
        !           343:         * babble into the slip tty line.
        !           344:         */
        !           345:        (void)close(1);
        !           346:        if ((fd = open("/dev/null", O_WRONLY, 0)) != 1) {
        !           347:                if (fd < 0) {
        !           348:                        syslog(LOG_ERR, "open /dev/null: %m");
        !           349:                        exit(1);
        !           350:                }
        !           351:                (void)dup2(fd, 1);
        !           352:                (void)close(fd);
        !           353:        }
        !           354:        (void)dup2(1,2);
        !           355:        if (s = system(logincmd)) {
        !           356:                syslog(LOG_ERR, "%s login failed: exit status %d from %s",
        !           357:                       loginname, s, loginfile);
        !           358:                (void) ioctl(0, TIOCSETD, (caddr_t)&odisc);
        !           359:                exit(6);
        !           360:        }
        !           361:        if (ioctl(0, SLIOCSFLAGS, (caddr_t)&slip_mode) < 0) {
        !           362:                syslog(LOG_ERR, "ioctl (SLIOCSFLAGS): %m");
        !           363:                exit(1);
        !           364:        }
        !           365: 
        !           366:        /* twiddle thumbs until we get a signal */
        !           367:        while (1)
        !           368:                sigpause(0);
        !           369: 
        !           370:        /* NOTREACHED */
        !           371: }

unix.superglobalmegacorp.com

This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.