|
|
1.1 ! root 1: /* ! 2: * Copyright (c) 1983 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) 1983 Regents of the University of California.\n\ ! 23: All rights reserved.\n"; ! 24: #endif /* not lint */ ! 25: ! 26: #ifndef lint ! 27: static char sccsid[] = "@(#)timedc.c 2.9 (Berkeley) 6/1/90"; ! 28: #endif /* not lint */ ! 29: ! 30: #include "timedc.h" ! 31: #include <signal.h> ! 32: #include <ctype.h> ! 33: #include <setjmp.h> ! 34: #include <syslog.h> ! 35: ! 36: int top; ! 37: int margc; ! 38: int fromatty; ! 39: char *margv[20]; ! 40: char cmdline[200]; ! 41: jmp_buf toplevel; ! 42: int intr(); ! 43: int priv_resources(); ! 44: struct cmd *getcmd(); ! 45: ! 46: ! 47: main(argc, argv) ! 48: char *argv[]; ! 49: { ! 50: register struct cmd *c; ! 51: ! 52: openlog("timedc", LOG_ODELAY, LOG_AUTH); ! 53: ! 54: /* ! 55: * security dictates! ! 56: */ ! 57: if (priv_resources() < 0) { ! 58: fprintf(stderr, "Could not get privileged resources\n"); ! 59: exit(1); ! 60: } ! 61: (void) setuid(getuid()); ! 62: ! 63: if (--argc > 0) { ! 64: c = getcmd(*++argv); ! 65: if (c == (struct cmd *)-1) { ! 66: printf("?Ambiguous command\n"); ! 67: exit(1); ! 68: } ! 69: if (c == 0) { ! 70: printf("?Invalid command\n"); ! 71: exit(1); ! 72: } ! 73: if (c->c_priv && getuid()) { ! 74: printf("?Privileged command\n"); ! 75: exit(1); ! 76: } ! 77: (*c->c_handler)(argc, argv); ! 78: exit(0); ! 79: } ! 80: fromatty = isatty(fileno(stdin)); ! 81: top = setjmp(toplevel) == 0; ! 82: if (top) ! 83: (void) signal(SIGINT, intr); ! 84: for (;;) { ! 85: cmdscanner(top); ! 86: top = 1; ! 87: } ! 88: } ! 89: ! 90: intr() ! 91: { ! 92: if (!fromatty) ! 93: exit(0); ! 94: longjmp(toplevel, 1); ! 95: } ! 96: ! 97: /* ! 98: * Command parser. ! 99: */ ! 100: cmdscanner(top) ! 101: int top; ! 102: { ! 103: register struct cmd *c; ! 104: extern int help(); ! 105: ! 106: if (!top) ! 107: putchar('\n'); ! 108: for (;;) { ! 109: if (fromatty) { ! 110: printf("timedc> "); ! 111: (void) fflush(stdout); ! 112: } ! 113: if (fgets(cmdline, sizeof(cmdline), stdin) == 0) ! 114: quit(); ! 115: if (cmdline[0] == 0) ! 116: break; ! 117: makeargv(); ! 118: c = getcmd(margv[0]); ! 119: if (c == (struct cmd *)-1) { ! 120: printf("?Ambiguous command\n"); ! 121: continue; ! 122: } ! 123: if (c == 0) { ! 124: printf("?Invalid command\n"); ! 125: continue; ! 126: } ! 127: if (c->c_priv && getuid()) { ! 128: printf("?Privileged command\n"); ! 129: continue; ! 130: } ! 131: (*c->c_handler)(margc, margv); ! 132: } ! 133: longjmp(toplevel, 0); ! 134: } ! 135: ! 136: struct cmd * ! 137: getcmd(name) ! 138: register char *name; ! 139: { ! 140: register char *p, *q; ! 141: register struct cmd *c, *found; ! 142: register int nmatches, longest; ! 143: extern struct cmd cmdtab[]; ! 144: extern int NCMDS; ! 145: ! 146: longest = 0; ! 147: nmatches = 0; ! 148: found = 0; ! 149: for (c = cmdtab; c < &cmdtab[NCMDS]; c++) { ! 150: p = c->c_name; ! 151: for (q = name; *q == *p++; q++) ! 152: if (*q == 0) /* exact match? */ ! 153: return(c); ! 154: if (!*q) { /* the name was a prefix */ ! 155: if (q - name > longest) { ! 156: longest = q - name; ! 157: nmatches = 1; ! 158: found = c; ! 159: } else if (q - name == longest) ! 160: nmatches++; ! 161: } ! 162: } ! 163: if (nmatches > 1) ! 164: return((struct cmd *)-1); ! 165: return(found); ! 166: } ! 167: ! 168: /* ! 169: * Slice a string up into argc/argv. ! 170: */ ! 171: makeargv() ! 172: { ! 173: register char *cp; ! 174: register char **argp = margv; ! 175: ! 176: margc = 0; ! 177: for (cp = cmdline; *cp;) { ! 178: while (isspace(*cp)) ! 179: cp++; ! 180: if (*cp == '\0') ! 181: break; ! 182: *argp++ = cp; ! 183: margc += 1; ! 184: while (*cp != '\0' && !isspace(*cp)) ! 185: cp++; ! 186: if (*cp == '\0') ! 187: break; ! 188: *cp++ = '\0'; ! 189: } ! 190: *argp++ = 0; ! 191: } ! 192: ! 193: #define HELPINDENT (sizeof ("directory")) ! 194: ! 195: /* ! 196: * Help command. ! 197: */ ! 198: help(argc, argv) ! 199: int argc; ! 200: char *argv[]; ! 201: { ! 202: register struct cmd *c; ! 203: extern struct cmd cmdtab[]; ! 204: ! 205: if (argc == 1) { ! 206: register int i, j, w; ! 207: int columns, width = 0, lines; ! 208: extern int NCMDS; ! 209: ! 210: printf("Commands may be abbreviated. Commands are:\n\n"); ! 211: for (c = cmdtab; c < &cmdtab[NCMDS]; c++) { ! 212: int len = strlen(c->c_name); ! 213: ! 214: if (len > width) ! 215: width = len; ! 216: } ! 217: width = (width + 8) &~ 7; ! 218: columns = 80 / width; ! 219: if (columns == 0) ! 220: columns = 1; ! 221: lines = (NCMDS + columns - 1) / columns; ! 222: for (i = 0; i < lines; i++) { ! 223: for (j = 0; j < columns; j++) { ! 224: c = cmdtab + j * lines + i; ! 225: printf("%s", c->c_name); ! 226: if (c + lines >= &cmdtab[NCMDS]) { ! 227: printf("\n"); ! 228: break; ! 229: } ! 230: w = strlen(c->c_name); ! 231: while (w < width) { ! 232: w = (w + 8) &~ 7; ! 233: putchar('\t'); ! 234: } ! 235: } ! 236: } ! 237: return; ! 238: } ! 239: while (--argc > 0) { ! 240: register char *arg; ! 241: arg = *++argv; ! 242: c = getcmd(arg); ! 243: if (c == (struct cmd *)-1) ! 244: printf("?Ambiguous help command %s\n", arg); ! 245: else if (c == (struct cmd *)0) ! 246: printf("?Invalid help command %s\n", arg); ! 247: else ! 248: printf("%-*s\t%s\n", HELPINDENT, ! 249: c->c_name, c->c_help); ! 250: } ! 251: }
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.