Add libedit command line history capability to lpc(8).
This commit is contained in:
parent
43e6e3abd2
commit
53df3fea02
@ -1,4 +1,4 @@
|
||||
# $NetBSD: Makefile,v 1.8 1997/10/10 09:26:38 lukem Exp $
|
||||
# $NetBSD: Makefile,v 1.9 2006/01/12 17:53:03 garbled Exp $
|
||||
# @(#)Makefile 8.1 (Berkeley) 6/6/93
|
||||
|
||||
PROG= lpc
|
||||
@ -7,4 +7,7 @@ SRCS= lpc.c cmds.c cmdtab.c
|
||||
BINGRP= daemon
|
||||
BINMODE=2555
|
||||
|
||||
LDADD+= -ledit -ltermcap
|
||||
DPADD+= ${LIBEDIT} ${LIBTERMCAP}
|
||||
|
||||
.include <bsd.prog.mk>
|
||||
|
@ -1,4 +1,4 @@
|
||||
/* $NetBSD: lpc.c,v 1.17 2005/11/28 03:26:06 christos Exp $ */
|
||||
/* $NetBSD: lpc.c,v 1.18 2006/01/12 17:53:03 garbled Exp $ */
|
||||
|
||||
/*
|
||||
* Copyright (c) 1983, 1993
|
||||
@ -37,7 +37,7 @@ __COPYRIGHT("@(#) Copyright (c) 1983, 1993\n\
|
||||
#if 0
|
||||
static char sccsid[] = "@(#)lpc.c 8.3 (Berkeley) 4/28/95";
|
||||
#else
|
||||
__RCSID("$NetBSD: lpc.c,v 1.17 2005/11/28 03:26:06 christos Exp $");
|
||||
__RCSID("$NetBSD: lpc.c,v 1.18 2006/01/12 17:53:03 garbled Exp $");
|
||||
#endif
|
||||
#endif /* not lint */
|
||||
|
||||
@ -47,6 +47,7 @@ __RCSID("$NetBSD: lpc.c,v 1.17 2005/11/28 03:26:06 christos Exp $");
|
||||
#include <signal.h>
|
||||
#include <setjmp.h>
|
||||
#include <syslog.h>
|
||||
#include <histedit.h>
|
||||
#include <unistd.h>
|
||||
#include <stdlib.h>
|
||||
#include <stdio.h>
|
||||
@ -66,11 +67,10 @@ __RCSID("$NetBSD: lpc.c,v 1.17 2005/11/28 03:26:06 christos Exp $");
|
||||
* lpc -- line printer control program
|
||||
*/
|
||||
|
||||
#define MAX_CMDLINE 200
|
||||
#define MAX_MARGV 20
|
||||
int fromatty;
|
||||
|
||||
char cmdline[MAX_CMDLINE];
|
||||
char *cmdline;
|
||||
int margc;
|
||||
char *margv[MAX_MARGV];
|
||||
int top;
|
||||
@ -78,18 +78,22 @@ uid_t uid, euid;
|
||||
|
||||
jmp_buf toplevel;
|
||||
|
||||
History *hist;
|
||||
HistEvent he;
|
||||
EditLine *elptr;
|
||||
|
||||
static void cmdscanner(int);
|
||||
static struct cmd *getcmd(const char *);
|
||||
static void intr(int);
|
||||
static void makeargv(void);
|
||||
static int ingroup(const char *);
|
||||
int main(int, char *p[]);
|
||||
const char *prompt(void);
|
||||
static int parse(char *, char *p[], int);
|
||||
|
||||
int
|
||||
main(int argc, char *argv[])
|
||||
{
|
||||
struct cmd *c;
|
||||
|
||||
euid = geteuid();
|
||||
uid = getuid();
|
||||
seteuid(uid);
|
||||
@ -97,21 +101,8 @@ main(int argc, char *argv[])
|
||||
openlog("lpd", 0, LOG_LPR);
|
||||
|
||||
if (--argc > 0) {
|
||||
c = getcmd(*++argv);
|
||||
if (c == (struct cmd *)-1) {
|
||||
printf("?Ambiguous command\n");
|
||||
exit(1);
|
||||
}
|
||||
if (c == 0) {
|
||||
printf("?Invalid command\n");
|
||||
exit(1);
|
||||
}
|
||||
if (c->c_priv && getuid() && ingroup(LPR_OPER) == 0) {
|
||||
printf("?Privileged command\n");
|
||||
exit(1);
|
||||
}
|
||||
(*c->c_handler)(argc, argv);
|
||||
exit(0);
|
||||
*argv++;
|
||||
exit(!parse(*argv, argv, argc));
|
||||
}
|
||||
fromatty = isatty(fileno(stdin));
|
||||
top = setjmp(toplevel) == 0;
|
||||
@ -123,48 +114,87 @@ main(int argc, char *argv[])
|
||||
}
|
||||
}
|
||||
|
||||
static int
|
||||
parse(char *arg, char **pargv, int pargc)
|
||||
{
|
||||
struct cmd *c;
|
||||
|
||||
c = getcmd(arg);
|
||||
if (c == (struct cmd *)-1) {
|
||||
printf("?Ambiguous command\n");
|
||||
return(0);
|
||||
}
|
||||
if (c == 0) {
|
||||
printf("?Invalid command\n");
|
||||
return(0);
|
||||
}
|
||||
if (c->c_priv && getuid() && ingroup(LPR_OPER) == 0) {
|
||||
printf("?Privileged command\n");
|
||||
return(0);
|
||||
}
|
||||
(*c->c_handler)(pargc, pargv);
|
||||
return(1);
|
||||
}
|
||||
|
||||
static void
|
||||
intr(int signo)
|
||||
{
|
||||
el_end(elptr);
|
||||
history_end(hist);
|
||||
if (!fromatty)
|
||||
exit(0);
|
||||
longjmp(toplevel, 1);
|
||||
}
|
||||
|
||||
const char *
|
||||
prompt(void)
|
||||
{
|
||||
return ("lpc> ");
|
||||
}
|
||||
|
||||
/*
|
||||
* Command parser.
|
||||
*/
|
||||
static void
|
||||
cmdscanner(int tp)
|
||||
{
|
||||
struct cmd *c;
|
||||
int scratch;
|
||||
const char *elline;
|
||||
|
||||
if (!tp)
|
||||
putchar('\n');
|
||||
hist = history_init();
|
||||
history(hist, &he, H_SETSIZE, 100); /* 100 elt history buffer */
|
||||
|
||||
elptr = el_init(getprogname(), stdin, stdout, stderr);
|
||||
el_set(elptr, EL_EDITOR, "emacs");
|
||||
el_set(elptr, EL_PROMPT, prompt);
|
||||
el_set(elptr, EL_HIST, history, hist);
|
||||
el_source(elptr, NULL);
|
||||
|
||||
for (;;) {
|
||||
if (fromatty) {
|
||||
printf("lpc> ");
|
||||
fflush(stdout);
|
||||
}
|
||||
if (fgets(cmdline, MAX_CMDLINE, stdin) == 0)
|
||||
quit(0, NULL);
|
||||
makeargv();
|
||||
cmdline = NULL;
|
||||
do {
|
||||
if (((elline = el_gets(elptr, &scratch)) != NULL)
|
||||
&& (scratch != 0)) {
|
||||
history(hist, &he, H_ENTER, elline);
|
||||
cmdline = strdup(elline);
|
||||
makeargv();
|
||||
} else {
|
||||
margc = 0;
|
||||
break;
|
||||
}
|
||||
} while (margc == 0);
|
||||
if (margc == 0)
|
||||
break;
|
||||
c = getcmd(margv[0]);
|
||||
if (c == (struct cmd *)-1) {
|
||||
printf("?Ambiguous command\n");
|
||||
quit(0, NULL);
|
||||
if (!parse(cmdline, margv, margc)) {
|
||||
if (cmdline != NULL)
|
||||
free(cmdline);
|
||||
continue;
|
||||
}
|
||||
if (c == 0) {
|
||||
printf("?Invalid command\n");
|
||||
continue;
|
||||
}
|
||||
if (c->c_priv && getuid() && ingroup(LPR_OPER) == 0) {
|
||||
printf("?Privileged command\n");
|
||||
continue;
|
||||
}
|
||||
(*c->c_handler)(margc, margv);
|
||||
fflush(stdout);
|
||||
if (cmdline != NULL)
|
||||
free(cmdline);
|
||||
}
|
||||
longjmp(toplevel, 0);
|
||||
}
|
||||
@ -206,10 +236,11 @@ makeargv(void)
|
||||
char *cp;
|
||||
char **argp = margv;
|
||||
int n = 0;
|
||||
size_t s;
|
||||
|
||||
s = sizeof(char) * strlen(cmdline);
|
||||
margc = 0;
|
||||
for (cp = cmdline; *cp && (cp - cmdline) < sizeof(cmdline) &&
|
||||
n < MAX_MARGV; n++) {
|
||||
for (cp = cmdline; *cp && (cp - cmdline) < s && n < MAX_MARGV; n++) {
|
||||
while (isspace((unsigned char)*cp))
|
||||
cp++;
|
||||
if (*cp == '\0')
|
||||
|
Loading…
Reference in New Issue
Block a user