121565Sdist /* 233161Sbostic * Copyright (c) 1980, 1987 Regents of the University of California. 333161Sbostic * All rights reserved. 433161Sbostic * 533161Sbostic * Redistribution and use in source and binary forms are permitted 634911Sbostic * provided that the above copyright notice and this paragraph are 734911Sbostic * duplicated in all such forms and that any documentation, 834911Sbostic * advertising materials, and other materials related to such 934911Sbostic * distribution and use acknowledge that the software was developed 1034911Sbostic * by the University of California, Berkeley. The name of the 1134911Sbostic * University may not be used to endorse or promote products derived 1234911Sbostic * from this software without specific prior written permission. 1334911Sbostic * THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR 1434911Sbostic * IMPLIED WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED 1534911Sbostic * WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE. 1621565Sdist */ 1721565Sdist 1812989Ssam #ifndef lint 1921565Sdist char copyright[] = 2033161Sbostic "@(#) Copyright (c) 1980, 1987 Regents of the University of California.\n\ 2121565Sdist All rights reserved.\n"; 2233161Sbostic #endif /* not lint */ 2312989Ssam 2421565Sdist #ifndef lint 25*42062Sbostic static char sccsid[] = "@(#)lock.c 5.12 (Berkeley) 05/15/90"; 2633161Sbostic #endif /* not lint */ 2721565Sdist 2812989Ssam /* 2930956Sbostic * Lock a terminal up until the given key is entered, until the root 3030956Sbostic * password is entered, or the given interval times out. 3116239Sralph * 3216239Sralph * Timeout interval is by default TIMEOUT, it can be changed with 3316239Sralph * an argument of the form -time where time is in minutes 3412989Ssam */ 3516239Sralph 3630652Sbostic #include <sys/param.h> 375748Sroot #include <sys/stat.h> 3816239Sralph #include <sys/time.h> 3930652Sbostic #include <sys/signal.h> 4036867Sbostic #include <sgtty.h> 4130652Sbostic #include <pwd.h> 4230652Sbostic #include <stdio.h> 4332615Sbostic #include <ctype.h> 44*42062Sbostic #include <string.h> 451041Sbill 4630956Sbostic #define TIMEOUT 15 471041Sbill 4839228Sbostic void quit(), bye(), hi(); 4916239Sralph 5030652Sbostic struct timeval timeout; 5130652Sbostic struct timeval zerotime; 5216239Sralph struct sgttyb tty, ntty; 5330956Sbostic long nexttime; /* keep the timeout time */ 5416239Sralph 5530956Sbostic /*ARGSUSED*/ 5630956Sbostic main(argc, argv) 5736292Sbostic int argc; 5836292Sbostic char **argv; 591041Sbill { 6036292Sbostic extern char *optarg; 6136867Sbostic extern int errno, optind; 6236867Sbostic struct passwd *pw; 6336292Sbostic struct timeval timval; 6436292Sbostic struct itimerval ntimer, otimer; 6536292Sbostic struct tm *timp; 6636867Sbostic int ch, sectimeout, usemine; 6736869Sbostic char *ap, *mypw, *ttynam, *tzn; 6836292Sbostic char hostname[MAXHOSTNAMELEN], s[BUFSIZ], s1[BUFSIZ]; 6936867Sbostic char *crypt(), *ttyname(); 701041Sbill 7136292Sbostic sectimeout = TIMEOUT; 7236867Sbostic mypw = NULL; 7336867Sbostic usemine = 0; 7436292Sbostic while ((ch = getopt(argc, argv, "pt:")) != EOF) 7536292Sbostic switch((char)ch) { 7636292Sbostic case 't': 7739228Sbostic if ((sectimeout = atoi(optarg)) <= 0) { 7839228Sbostic (void)fprintf(stderr, 7939228Sbostic "lock: illegal timeout value.\n"); 8036867Sbostic exit(1); 8139228Sbostic } 8236292Sbostic break; 8336292Sbostic case 'p': 8436867Sbostic usemine = 1; 8536867Sbostic if (!(pw = getpwuid(getuid()))) { 8639228Sbostic (void)fprintf(stderr, 8739228Sbostic "lock: unknown uid %d.\n", getuid()); 8836867Sbostic exit(1); 8936867Sbostic } 9036867Sbostic mypw = strdup(pw->pw_passwd); 9136292Sbostic break; 9236292Sbostic case '?': 9336292Sbostic default: 9439228Sbostic (void)fprintf(stderr, 9539228Sbostic "usage: lock [-p] [-t timeout]\n"); 9636292Sbostic exit(1); 9716239Sralph } 9816239Sralph timeout.tv_sec = sectimeout * 60; 9916239Sralph 10036867Sbostic setuid(getuid()); /* discard privs */ 10136867Sbostic 10236867Sbostic if (ioctl(0, TIOCGETP, &tty)) /* get information for header */ 1031041Sbill exit(1); 10416239Sralph gethostname(hostname, sizeof(hostname)); 10530652Sbostic if (!(ttynam = ttyname(0))) { 10639228Sbostic (void)printf("lock: not a terminal?\n"); 10730956Sbostic exit(1); 10816239Sralph } 10930652Sbostic if (gettimeofday(&timval, (struct timezone *)NULL)) { 11039228Sbostic (void)fprintf(stderr, 11139228Sbostic "lock: gettimeofday: %s\n", strerror(errno)); 11230956Sbostic exit(1); 11330652Sbostic } 11416239Sralph nexttime = timval.tv_sec + (sectimeout * 60); 11516239Sralph timp = localtime(&timval.tv_sec); 11616239Sralph ap = asctime(timp); 11730652Sbostic tzn = timp->tm_zone; 11816239Sralph 11930652Sbostic (void)signal(SIGINT, quit); 12030652Sbostic (void)signal(SIGQUIT, quit); 1211041Sbill ntty = tty; ntty.sg_flags &= ~ECHO; 12230652Sbostic (void)ioctl(0, TIOCSETP, &ntty); 12330652Sbostic 12436867Sbostic if (!mypw) { 12530956Sbostic /* get key and check again */ 12639228Sbostic (void)printf("Key: "); 12736867Sbostic if (!fgets(s, sizeof(s), stdin) || *s == '\n') 12830956Sbostic quit(); 12939228Sbostic (void)printf("\nAgain: "); 13030956Sbostic /* 13130956Sbostic * Don't need EOF test here, if we get EOF, then s1 != s 13230956Sbostic * and the right things will happen. 13330956Sbostic */ 13436867Sbostic (void)fgets(s1, sizeof(s1), stdin); 13539228Sbostic (void)putchar('\n'); 13630956Sbostic if (strcmp(s1, s)) { 13739228Sbostic (void)printf("\07lock: passwords didn't match.\n"); 13830956Sbostic ioctl(0, TIOCSETP, &tty); 13930956Sbostic exit(1); 14030956Sbostic } 14130956Sbostic s[0] = NULL; 14236867Sbostic mypw = s1; 1431041Sbill } 14416239Sralph 14530956Sbostic /* set signal handlers */ 14630652Sbostic (void)signal(SIGINT, hi); 14730652Sbostic (void)signal(SIGQUIT, hi); 14830652Sbostic (void)signal(SIGTSTP, hi); 14930652Sbostic (void)signal(SIGALRM, bye); 15030652Sbostic 15116239Sralph ntimer.it_interval = zerotime; 15216239Sralph ntimer.it_value = timeout; 15316239Sralph setitimer(ITIMER_REAL, &ntimer, &otimer); 15416239Sralph 15530956Sbostic /* header info */ 15639228Sbostic (void)printf("lock: %s on %s. timeout in %d minutes\ntime now is %.20s%s%s", 15739228Sbostic ttynam, hostname, sectimeout, ap, tzn, ap + 19); 15816239Sralph 15930956Sbostic for (;;) { 16039228Sbostic (void)printf("Key: "); 16136867Sbostic if (!fgets(s, sizeof(s), stdin)) { 16216599Skre clearerr(stdin); 16316599Skre hi(); 16416599Skre continue; 16516599Skre } 16636867Sbostic if (usemine) { 16737235Sbostic s[strlen(s) - 1] = '\0'; 16836867Sbostic if (!strcmp(mypw, crypt(s, mypw))) 16930956Sbostic break; 17030956Sbostic } 17136867Sbostic else if (!strcmp(s, s1)) 1721041Sbill break; 17339228Sbostic (void)printf("\07\n"); 17412989Ssam if (ioctl(0, TIOCGETP, &ntty)) 1751041Sbill exit(1); 1761041Sbill } 17730652Sbostic quit(); 1781041Sbill } 17916239Sralph 18039228Sbostic void 18130652Sbostic hi() 18230652Sbostic { 18336292Sbostic struct timeval timval; 18430652Sbostic 18530652Sbostic if (!gettimeofday(&timval, (struct timezone *)NULL)) 18639228Sbostic (void)printf("lock: type in the unlock key. timeout in %ld:%ld minutes\n", 18730956Sbostic (nexttime - timval.tv_sec) / 60, (nexttime - timval.tv_sec) % 60); 18830652Sbostic } 18930652Sbostic 19039228Sbostic void 19116239Sralph quit() 19216239Sralph { 19339228Sbostic (void)putchar('\n'); 19430652Sbostic (void)ioctl(0, TIOCSETP, &tty); 19530956Sbostic exit(0); 19616239Sralph } 19716239Sralph 19839228Sbostic void 19916239Sralph bye() 20016239Sralph { 20130652Sbostic (void)ioctl(0, TIOCSETP, &tty); 20239228Sbostic (void)printf("lock: timeout\n"); 20330956Sbostic exit(1); 20416239Sralph } 205