xref: /csrg-svn/usr.sbin/lpr/lpc/lpc.c (revision 12744)
112380Sralph #ifndef lint
2*12744Sralph static char sccsid[] = "@(#)lpc.c	4.2 (Berkeley) 05/27/83";
312380Sralph #endif
412380Sralph 
512380Sralph /*
612380Sralph  * lpc -- line printer control program
712380Sralph  */
812380Sralph #include <stdio.h>
912380Sralph #include <signal.h>
1012380Sralph #include <ctype.h>
1112380Sralph #include <setjmp.h>
1212380Sralph 
1312380Sralph #include "lpc.h"
1412380Sralph 
1512380Sralph int	fromatty;
1612380Sralph 
1712380Sralph char	cmdline[200];
1812380Sralph int	margc;
1912380Sralph char	*margv[20];
2012380Sralph int	top;
2112380Sralph int	intr();
2212380Sralph struct	cmd *getcmd();
2312380Sralph 
2412380Sralph jmp_buf	toplevel;
2512380Sralph 
2612380Sralph main(argc, argv)
2712380Sralph 	char *argv[];
2812380Sralph {
2912380Sralph 	register struct cmd *c;
30*12744Sralph 	extern char *name;
3112380Sralph 
32*12744Sralph 	name = argv[0];
33*12744Sralph 
3412380Sralph 	if (--argc > 0) {
3512380Sralph 		c = getcmd(*++argv);
3612380Sralph 		if (c == (struct cmd *)-1) {
3712380Sralph 			printf("?Ambiguous command\n");
3812380Sralph 			exit(1);
3912380Sralph 		}
4012380Sralph 		if (c == 0) {
4112380Sralph 			printf("?Invalid command\n");
4212380Sralph 			exit(1);
4312380Sralph 		}
4412380Sralph 		if (c->c_priv && getuid()) {
4512380Sralph 			printf("?Privileged command\n");
4612380Sralph 			exit(1);
4712380Sralph 		}
4812380Sralph 		(*c->c_handler)(argc, argv);
4912380Sralph 		exit(0);
5012380Sralph 	}
5112380Sralph 	fromatty = isatty(fileno(stdin));
5212380Sralph 	top = setjmp(toplevel) == 0;
5312380Sralph 	if (top)
5412380Sralph 		sigset(SIGINT, intr);
5512380Sralph 	for (;;) {
5612380Sralph 		cmdscanner(top);
5712380Sralph 		top = 1;
5812380Sralph 	}
5912380Sralph }
6012380Sralph 
6112380Sralph intr()
6212380Sralph {
6312380Sralph 	if (!fromatty)
6412380Sralph 		exit(0);
6512380Sralph 	longjmp(toplevel, 1);
6612380Sralph }
6712380Sralph 
6812380Sralph /*
6912380Sralph  * Command parser.
7012380Sralph  */
7112380Sralph cmdscanner(top)
7212380Sralph 	int top;
7312380Sralph {
7412380Sralph 	register struct cmd *c;
7512380Sralph 	extern struct cmd cmdtab[];
7612380Sralph 	extern int help();
7712380Sralph 
7812380Sralph 	if (!top)
7912380Sralph 		putchar('\n');
8012380Sralph 	for (;;) {
8112380Sralph 		if (fromatty) {
8212380Sralph 			printf("lpc> ");
8312380Sralph 			fflush(stdout);
8412380Sralph 		}
8512380Sralph 		if (gets(cmdline) == 0)
8612380Sralph 			quit();
8712380Sralph 		if (cmdline[0] == 0)
8812380Sralph 			break;
8912380Sralph 		makeargv();
9012380Sralph 		c = getcmd(margv[0]);
9112380Sralph 		if (c == (struct cmd *)-1) {
9212380Sralph 			printf("?Ambiguous command\n");
9312380Sralph 			continue;
9412380Sralph 		}
9512380Sralph 		if (c == 0) {
9612380Sralph 			printf("?Invalid command\n");
9712380Sralph 			continue;
9812380Sralph 		}
9912380Sralph 		if (c->c_priv && getuid()) {
10012380Sralph 			printf("?Privileged command\n");
10112380Sralph 			continue;
10212380Sralph 		}
10312380Sralph 		(*c->c_handler)(margc, margv);
10412380Sralph 	}
10512380Sralph 	longjmp(toplevel, 0);
10612380Sralph }
10712380Sralph 
10812380Sralph struct cmd *
10912380Sralph getcmd(name)
11012380Sralph 	register char *name;
11112380Sralph {
11212380Sralph 	register char *p, *q;
11312380Sralph 	register struct cmd *c, *found;
11412380Sralph 	register int nmatches, longest;
11512380Sralph 
11612380Sralph 	longest = 0;
11712380Sralph 	nmatches = 0;
11812380Sralph 	found = 0;
11912380Sralph 	for (c = cmdtab; p = c->c_name; c++) {
12012380Sralph 		for (q = name; *q == *p++; q++)
12112380Sralph 			if (*q == 0)		/* exact match? */
12212380Sralph 				return(c);
12312380Sralph 		if (!*q) {			/* the name was a prefix */
12412380Sralph 			if (q - name > longest) {
12512380Sralph 				longest = q - name;
12612380Sralph 				nmatches = 1;
12712380Sralph 				found = c;
12812380Sralph 			} else if (q - name == longest)
12912380Sralph 				nmatches++;
13012380Sralph 		}
13112380Sralph 	}
13212380Sralph 	if (nmatches > 1)
13312380Sralph 		return((struct cmd *)-1);
13412380Sralph 	return(found);
13512380Sralph }
13612380Sralph 
13712380Sralph /*
13812380Sralph  * Slice a string up into argc/argv.
13912380Sralph  */
14012380Sralph makeargv()
14112380Sralph {
14212380Sralph 	register char *cp;
14312380Sralph 	register char **argp = margv;
14412380Sralph 
14512380Sralph 	margc = 0;
14612380Sralph 	for (cp = cmdline; *cp;) {
14712380Sralph 		while (isspace(*cp))
14812380Sralph 			cp++;
14912380Sralph 		if (*cp == '\0')
15012380Sralph 			break;
15112380Sralph 		*argp++ = cp;
15212380Sralph 		margc += 1;
15312380Sralph 		while (*cp != '\0' && !isspace(*cp))
15412380Sralph 			cp++;
15512380Sralph 		if (*cp == '\0')
15612380Sralph 			break;
15712380Sralph 		*cp++ = '\0';
15812380Sralph 	}
15912380Sralph 	*argp++ = 0;
16012380Sralph }
16112380Sralph 
16212380Sralph #define HELPINDENT (sizeof ("directory"))
16312380Sralph 
16412380Sralph /*
16512380Sralph  * Help command.
16612380Sralph  */
16712380Sralph help(argc, argv)
16812380Sralph 	int argc;
16912380Sralph 	char *argv[];
17012380Sralph {
17112380Sralph 	register struct cmd *c;
17212380Sralph 
17312380Sralph 	if (argc == 1) {
17412380Sralph 		register int i, j, w;
17512380Sralph 		int columns, width = 0, lines;
17612380Sralph 		extern int NCMDS;
17712380Sralph 
17812380Sralph 		printf("Commands may be abbreviated.  Commands are:\n\n");
17912380Sralph 		for (c = cmdtab; c < &cmdtab[NCMDS]; c++) {
18012380Sralph 			int len = strlen(c->c_name);
18112380Sralph 
18212380Sralph 			if (len > width)
18312380Sralph 				width = len;
18412380Sralph 		}
18512380Sralph 		width = (width + 8) &~ 7;
18612380Sralph 		columns = 80 / width;
18712380Sralph 		if (columns == 0)
18812380Sralph 			columns = 1;
18912380Sralph 		lines = (NCMDS + columns - 1) / columns;
19012380Sralph 		for (i = 0; i < lines; i++) {
19112380Sralph 			for (j = 0; j < columns; j++) {
19212380Sralph 				c = cmdtab + j * lines + i;
19312380Sralph 				printf("%s", c->c_name);
19412380Sralph 				if (c + lines >= &cmdtab[NCMDS]) {
19512380Sralph 					printf("\n");
19612380Sralph 					break;
19712380Sralph 				}
19812380Sralph 				w = strlen(c->c_name);
19912380Sralph 				while (w < width) {
20012380Sralph 					w = (w + 8) &~ 7;
20112380Sralph 					putchar('\t');
20212380Sralph 				}
20312380Sralph 			}
20412380Sralph 		}
20512380Sralph 		return;
20612380Sralph 	}
20712380Sralph 	while (--argc > 0) {
20812380Sralph 		register char *arg;
20912380Sralph 		arg = *++argv;
21012380Sralph 		c = getcmd(arg);
21112380Sralph 		if (c == (struct cmd *)-1)
21212380Sralph 			printf("?Ambiguous help command %s\n", arg);
21312380Sralph 		else if (c == (struct cmd *)0)
21412380Sralph 			printf("?Invalid help command %s\n", arg);
21512380Sralph 		else
21612380Sralph 			printf("%-*s\t%s\n", HELPINDENT,
21712380Sralph 				c->c_name, c->c_help);
21812380Sralph 	}
21912380Sralph }
220