mirror of
https://github.com/asterisk/asterisk.git
synced 2025-10-13 00:04:53 +00:00
Add ability to use system libedit and update bundled libedit.
The version of libedit that is bundled with asterisk is old and has some bugs. This patch updates the bundled version of libedit within asterisk, and also updates asterisk to use the system libedit instead if one is available (and pkg-config is available). This review integrates several patches from other users specifically kkm and tzafrir. (closes issue #15929) Reported by: kkm Patches: 015929-astcli-editrc-trunk.240324.diff uploaded by kkm (license 888) (issue #16858) Reported by: jw-asterisk (closes issue #17039) Reported by: tzafrir Patches: 0001-allow-using-system-copy-of-libedit.patch uploaded by tzafrir (license 46) Review: https://reviewboard.asterisk.org/r/807/ git-svn-id: https://origsvn.digium.com/svn/asterisk/branches/1.8@280019 65c4cc65-6c06-0410-ace0-fbb531ad65f3
This commit is contained in:
@@ -1,42 +0,0 @@
|
||||
2002-02-25 : Christos Zoulas <christos@netbsd.org>
|
||||
* Bring in constification fixes from NetBSD tree.
|
||||
* Use NetBSD's vis, fgetln
|
||||
|
||||
2002-02-10 : Jason Evans <jasone@freebsd.org>
|
||||
|
||||
* Makefile.in : Append "" arguments to for loops, to avoid syntax errors
|
||||
with some shells that occur if there are no arguments to the for
|
||||
loops.
|
||||
|
||||
2002-02-09 : Jason Evans <jasone@freebsd.org>
|
||||
|
||||
* Install man pages in @prefix@/man/, rather than @prefix@/share/man.
|
||||
|
||||
* Fix the Darwin -install_name S_LDFLAGS argument to default to a prefix
|
||||
of /usr/local if --prefix is not specified.
|
||||
|
||||
2002-02-05 : Jason Evans <jasone@freebsd.org>
|
||||
|
||||
* Convert to using an autoconf-generated config.h, rather than passing
|
||||
-D_HAVE_<foo>=1 definitions on the command line. Include sys.h in
|
||||
config.h, and include config.h in .c files rather than sys.h.
|
||||
|
||||
* Mangle function names for implementations in the np directory in order
|
||||
to avoid namespace collisions with other code that may provide copies
|
||||
of the same unimplemented functions. For example:
|
||||
|
||||
#define fgetln libedit_fgetln
|
||||
|
||||
2002-02-03 : Jason Evans <jasone@freebsd.org>
|
||||
|
||||
* Add autoconf infrastructure, plus a generic Makefile that works with
|
||||
at least BSD make, GNU make and Sun make.
|
||||
|
||||
* Port and/or test on FreeBSD 4.5, FreeBSD-current, NetBSD 1.5 (sparc64
|
||||
and arm32), Apple OS X 10.1.2, Solaris 2.6, and Red Hat Linux 2.6.
|
||||
Add the np directory, which contains implementations of non-portable
|
||||
functions.
|
||||
|
||||
* Add the LIBEDIT_MAJOR and LIBEDIT_MINOR macros to histedit.h, since
|
||||
there is otherwise no straightforward method of programmatically
|
||||
detecting the library version.
|
@@ -1,64 +0,0 @@
|
||||
Building this distribution in many cases is as simple as typing the following
|
||||
while in the root directory of the source tree:
|
||||
|
||||
./configure
|
||||
make
|
||||
|
||||
To install, do the above, then type:
|
||||
|
||||
make install
|
||||
|
||||
Additional build targets of finer granularity include:
|
||||
|
||||
lib_a
|
||||
lib_s
|
||||
install_hdr
|
||||
install_lib
|
||||
install_lib_a
|
||||
install_lib_s
|
||||
install_man
|
||||
test
|
||||
|
||||
Cleanup targets include:
|
||||
|
||||
clean
|
||||
distclean
|
||||
|
||||
Optionally, pass any of the following (not a definitive list) arguments to
|
||||
'configure':
|
||||
|
||||
--prefix=<install-root-dir>
|
||||
Set the base directory in which to install. For example:
|
||||
|
||||
./configure --prefix=/usr/local
|
||||
|
||||
will cause files to be installed into /usr/local/bin, /usr/local/man,
|
||||
/usr/local/include, /usr/local/lib, and /usr/local/share.
|
||||
|
||||
--disable-readline
|
||||
By default, libedit is built and installed such that it works as a
|
||||
drop-in replacement for the readline library. This option turns that
|
||||
behavior off.
|
||||
|
||||
--enable-debug
|
||||
Build debugging code (for libedit development).
|
||||
|
||||
Optionally, define environment variables, including (not exclusively):
|
||||
|
||||
CFLAGS="?"
|
||||
Pass these flags to the compiler. You probably shouldn't define this
|
||||
unless you know what you are doing.
|
||||
|
||||
CPPFLAGS="?"
|
||||
Pass these flags to the C preprocessor. Note that CFLAGS is not passed
|
||||
to 'cpp' when 'configure' is looking for include files, so you must use
|
||||
CPPFLAGS instead if you need to help 'configure' find header files.
|
||||
|
||||
LD_LIBRARY_PATH="?"
|
||||
'ld' uses this colon-separated list to find libraries.
|
||||
|
||||
LDFLAGS="?"
|
||||
Flags passed to 'gcc', which should normally be passed on to 'ld'.
|
||||
|
||||
PATH="?"
|
||||
'configure' uses this to find programs.
|
@@ -1,234 +0,0 @@
|
||||
#
|
||||
# Generic Makefile for libedit.
|
||||
#
|
||||
|
||||
OSTYPE=$(shell uname -s)
|
||||
define cyg_subst_sys
|
||||
if uname -s | grep -i cygwin > /dev/null; then \
|
||||
cat $@ | sed -e s/"sys\.h"/"config.h"/g > $@.copy; \
|
||||
mv --force $@.copy $@; \
|
||||
fi
|
||||
endef
|
||||
|
||||
SHELL = /bin/sh
|
||||
|
||||
CC = @CC@
|
||||
AR = @AR@
|
||||
RANLIB = @RANLIB@
|
||||
CPPFLAGS = @CPPFLAGS@ -I.
|
||||
CFLAGS = @CFLAGS@
|
||||
A_CFLAGS = @A_CFLAGS@
|
||||
S_CFLAGS = @S_CFLAGS@
|
||||
LDFLAGS = @LDFLAGS@
|
||||
S_LDFLAGS = @S_LDFLAGS@
|
||||
LIBS = @LIBS@
|
||||
|
||||
INSTALL = @INSTALL@
|
||||
PREFIX = @prefix@
|
||||
|
||||
ifeq ($(OSTYPE),SunOS)
|
||||
CFLAGS+=-DSOLARIS -I../../include/solaris-compat
|
||||
endif
|
||||
|
||||
# .c files.
|
||||
ACSRCS = @ACSRCS@
|
||||
BCSRCS = @BCSRCS@
|
||||
CCSRCS = @CCSRCS@
|
||||
|
||||
# Generated .c files.
|
||||
AGCSRCS = @AGCSRCS@
|
||||
BGCSRCS = @BGCSRCS@
|
||||
|
||||
# .h files.
|
||||
HDRS = @HDRS@
|
||||
|
||||
# Generated .h files.
|
||||
AGHDRS = @AGHDRS@
|
||||
BGHDRS = @BGHDRS@
|
||||
|
||||
# Installed .h files.
|
||||
IHDRS = @IHDRS@
|
||||
IHDR_LINKS = @IHDR_LINKS@
|
||||
HDR_DIRS = @HDR_DIRS@
|
||||
|
||||
# Man pages.
|
||||
MAN3 = @MAN3@
|
||||
MAN5 = @MAN5@
|
||||
MAN3_LINKS = @MAN3_LINKS@
|
||||
MAN_DIRS = @MAN_DIRS@
|
||||
|
||||
# Library.
|
||||
LIB_DIRS = @LIB_DIRS@
|
||||
LIB_VER = @LIB_VER@
|
||||
LIB_A = @LIB_A@
|
||||
LIB_A_LINKS = @LIB_A_LINKS@
|
||||
LIB_S = @LIB_S@
|
||||
LIB_S_LINKS = @LIB_S_LINKS@
|
||||
|
||||
# Test program.
|
||||
TEST = @TEST@
|
||||
TCSRCS = @TCSRCS@
|
||||
|
||||
# Clear out all paths, then set just one (default path) for the main build
|
||||
# directory.
|
||||
.PATH :
|
||||
.PATH : .
|
||||
|
||||
.SUFFIXES :
|
||||
.SUFFIXES : .c .o .o_a .o_s
|
||||
|
||||
all : lib_a lib_s
|
||||
|
||||
lib_a : $(LIB_A)
|
||||
lib_s : $(LIB_S)
|
||||
|
||||
test : $(TEST)
|
||||
|
||||
install : install_hdr install_lib install_man
|
||||
|
||||
install_hdr :
|
||||
@for i in $(HDR_DIRS) ; do \
|
||||
echo "$(INSTALL) -d $(PREFIX)/$$i/"; \
|
||||
$(INSTALL) -d $(PREFIX)/$$i/; \
|
||||
done
|
||||
@for i in $(IHDRS); do \
|
||||
echo "$(INSTALL) -m 0444 $$i $(PREFIX)/include/`dirname $$i`/"; \
|
||||
$(INSTALL) -m 0444 $$i $(PREFIX)/include/`dirname $$i`/; \
|
||||
done
|
||||
@f=; \
|
||||
for i in $(IHDR_LINKS) ""; do \
|
||||
if test -z "$$f" ; then \
|
||||
f=$$i; \
|
||||
else \
|
||||
echo "rm -f $(PREFIX)/include/$$i"; \
|
||||
rm -f $(PREFIX)/include/$$i; \
|
||||
echo "ln -s $$f $(PREFIX)/include/$$i"; \
|
||||
ln -s $$f $(PREFIX)/include/$$i; \
|
||||
f=; \
|
||||
fi; \
|
||||
done
|
||||
|
||||
install_lib : install_lib_a install_lib_s
|
||||
|
||||
install_lib_common :
|
||||
@for i in $(LIB_DIRS) ; do \
|
||||
echo "$(INSTALL) -d $(PREFIX)/$$i/"; \
|
||||
$(INSTALL) -d $(PREFIX)/$$i/; \
|
||||
done
|
||||
|
||||
install_lib_a : $(LIB_A) install_lib_common
|
||||
$(INSTALL) -m 0644 $(LIB_A) $(PREFIX)/lib/
|
||||
@f=; \
|
||||
for i in $(LIB_A_LINKS) ""; do \
|
||||
if test -z "$$f" ; then \
|
||||
f=$$i; \
|
||||
else \
|
||||
echo "rm -f $(PREFIX)/lib/$$i"; \
|
||||
rm -f $(PREFIX)/lib/$$i; \
|
||||
echo "ln -s $$f $(PREFIX)/lib/$$i"; \
|
||||
ln -s $$f $(PREFIX)/lib/$$i; \
|
||||
f=; \
|
||||
fi; \
|
||||
done
|
||||
|
||||
install_lib_s : $(LIB_S) install_lib_common
|
||||
$(INSTALL) -m 0755 $(LIB_S) $(PREFIX)/lib/
|
||||
@f=; \
|
||||
for i in $(LIB_S_LINKS) ""; do \
|
||||
if test -z "$$f" ; then \
|
||||
f=$$i; \
|
||||
else \
|
||||
echo "rm -f $(PREFIX)/lib/$$i"; \
|
||||
rm -f $(PREFIX)/lib/$$i; \
|
||||
echo "ln -s $$f $(PREFIX)/lib/$$i"; \
|
||||
ln -s $$f $(PREFIX)/lib/$$i; \
|
||||
f=; \
|
||||
fi; \
|
||||
done
|
||||
|
||||
install_man :
|
||||
@for i in $(MAN_DIRS) ; do \
|
||||
echo "$(INSTALL) -d $(PREFIX)/$$i/"; \
|
||||
$(INSTALL) -d $(PREFIX)/$$i/; \
|
||||
done
|
||||
@for i in $(MAN3); do \
|
||||
echo $(INSTALL) -m 0444 $$i $(PREFIX)/man/man3/; \
|
||||
$(INSTALL) -m 0444 $$i $(PREFIX)/man/man3/; \
|
||||
done
|
||||
@f=; \
|
||||
for i in $(MAN3_LINKS) ""; do \
|
||||
if test -z "$$f" ; then \
|
||||
f=$$i; \
|
||||
else \
|
||||
echo "rm -f $(PREFIX)/man/man3/$$i"; \
|
||||
rm -f $(PREFIX)/man/man3/$$i; \
|
||||
echo "ln -s $$f $(PREFIX)/man/man3/$$i"; \
|
||||
ln -s $$f $(PREFIX)/man/man3/$$i; \
|
||||
f=; \
|
||||
fi; \
|
||||
done
|
||||
@for i in $(MAN5); do\
|
||||
echo $(INSTALL) -m 0444 $$i $(PREFIX)/man/man5/; \
|
||||
$(INSTALL) -m 0444 $$i $(PREFIX)/man/man5/; \
|
||||
done
|
||||
|
||||
clean :
|
||||
rm -f $(AGCSRCS) $(BGCSRCS) $(AGHDRS) $(BGHDRS) $(LIB_A) $(LIB_S)
|
||||
rm -f $(BGCSRCS:.c=.o_a) $(CCSRCS:.c=.o_a)
|
||||
rm -f $(BGCSRCS:.c=.o_s) $(CCSRCS:.c=.o_s)
|
||||
rm -f $(TCSRCS:.c=.o) $(TEST)
|
||||
rm -f *.s *.i
|
||||
|
||||
distclean : clean
|
||||
rm -f config.cache config.log config.status config.h makelist Makefile
|
||||
|
||||
#
|
||||
# Internal targets and rules.
|
||||
#
|
||||
|
||||
$(LIB_A) : $(BGCSRCS:.c=.o_a) $(CCSRCS:.c=.o_a)
|
||||
$(AR) cru $@ $?
|
||||
$(RANLIB) $@
|
||||
|
||||
$(LIB_S) : $(BGCSRCS:.c=.o_s) $(CCSRCS:.c=.o_s)
|
||||
$(CC) $(S_LDFLAGS) -o $@ $(BGCSRCS:.c=.o_s) $(CCSRCS:.c=.o_s) $(LIBS)
|
||||
|
||||
$(TEST) : $(TCSRCS:.c=.o) $(LIB_A)
|
||||
$(CC) -o $@ $(TCSRCS:.c=.o) $(LIB_A) $(LIBS)
|
||||
|
||||
common.h : common.c
|
||||
$(SHELL) makelist -h common.c > $@
|
||||
|
||||
emacs.h : emacs.c
|
||||
$(SHELL) makelist -h emacs.c> $@
|
||||
|
||||
vi.h : vi.c
|
||||
$(SHELL) makelist -h vi.c > $@
|
||||
|
||||
fcns.h : $(AGHDRS)
|
||||
$(SHELL) makelist -fh $(AGHDRS) > $@
|
||||
|
||||
fcns.c : $(AGHDRS) fcns.h
|
||||
$(SHELL) makelist -fc $(AGHDRS) > $@
|
||||
$(cyg_subst_sys)
|
||||
|
||||
help.h : $(ACSRCS)
|
||||
$(SHELL) makelist -bh $(ACSRCS) > $@
|
||||
|
||||
help.c : $(ACSRCS) help.h
|
||||
$(SHELL) makelist -bc $(ACSRCS) > $@
|
||||
$(cyg_subst_sys)
|
||||
|
||||
editline.c : $(ACSRCS) $(BCSRCS) $(AGCSRCS)
|
||||
$(SHELL) makelist -e $(ACSRCS) $(BCSRCS) $(AGCSRCS) > $@
|
||||
|
||||
.c.o :
|
||||
$(CC) -c $(A_CFLAGS) $(CFLAGS) $(CPPFLAGS) $< -o $@
|
||||
|
||||
.c.o_a : $(AGHDRS) $(BGHDRS)
|
||||
$(CC) -c $(A_CFLAGS) $(CFLAGS) $(CPPFLAGS) $< -o $@
|
||||
|
||||
.c.o_s : $(AGHDRS) $(BGHDRS)
|
||||
$(CC) -c $(S_CFLAGS) $(CFLAGS) $(CPPFLAGS) $< -o $@
|
||||
|
||||
$(CCSRCS) : $(BGHDRS)
|
@@ -1,13 +0,0 @@
|
||||
This distribution of libedit is expected to work on at least the following
|
||||
platforms. It may also work on additional platforms, but no explicit support
|
||||
for them is built into the configuration system.
|
||||
|
||||
* Apple OS X 10.1.
|
||||
|
||||
* FreeBSD 4.x.
|
||||
|
||||
* NetBSD 1.5.
|
||||
|
||||
* Red Hat Linux 7.2.
|
||||
|
||||
* Sun Solaris 2.6.
|
@@ -1,11 +0,0 @@
|
||||
libedit is a command line editing and history library. It is designed to be
|
||||
used by interactive programs that allow the user to type commands at a terminal
|
||||
prompt.
|
||||
|
||||
The following files may be of direct interest to the user:
|
||||
|
||||
* CHANGES - Software change log.
|
||||
|
||||
* INSTALL - Installation information.
|
||||
|
||||
* PLATFORMS - Supported platforms and platform-specific information.
|
@@ -1,268 +0,0 @@
|
||||
/* $NetBSD: test.c,v 1.9 2000/09/04 23:36:41 lukem Exp $ */
|
||||
|
||||
/*-
|
||||
* Copyright (c) 1992, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* This code is derived from software contributed to Berkeley by
|
||||
* Christos Zoulas of Cornell University.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
* 3. All advertising materials mentioning features or use of this software
|
||||
* must display the following acknowledgement:
|
||||
* This product includes software developed by the University of
|
||||
* California, Berkeley and its contributors.
|
||||
* 4. Neither the name of the University nor the names of its contributors
|
||||
* may be used to endorse or promote products derived from this software
|
||||
* without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
|
||||
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
* ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
|
||||
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
|
||||
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*/
|
||||
|
||||
#include "config.h"
|
||||
#ifndef lint
|
||||
__COPYRIGHT("@(#) Copyright (c) 1992, 1993\n\
|
||||
The Regents of the University of California. All rights reserved.\n");
|
||||
#endif /* not lint */
|
||||
|
||||
#if !defined(lint) && !defined(SCCSID)
|
||||
#if 0
|
||||
static char sccsid[] = "@(#)test.c 8.1 (Berkeley) 6/4/93";
|
||||
#else
|
||||
__RCSID("$NetBSD: test.c,v 1.9 2000/09/04 23:36:41 lukem Exp $");
|
||||
#endif
|
||||
#endif /* not lint && not SCCSID */
|
||||
|
||||
/*
|
||||
* test.c: A little test program
|
||||
*/
|
||||
#include <stdio.h>
|
||||
#include <string.h>
|
||||
#include <signal.h>
|
||||
#include <sys/wait.h>
|
||||
#include <ctype.h>
|
||||
#include <stdlib.h>
|
||||
#include <unistd.h>
|
||||
#include <dirent.h>
|
||||
|
||||
#include "histedit.h"
|
||||
#include "tokenizer.h"
|
||||
|
||||
static int continuation = 0;
|
||||
static EditLine *el = NULL;
|
||||
|
||||
static u_char complete(EditLine *, int);
|
||||
int main(int, char **);
|
||||
static char *prompt(EditLine *);
|
||||
static void sig(int);
|
||||
|
||||
static char *
|
||||
prompt(EditLine *el)
|
||||
{
|
||||
static char a[] = "Edit$";
|
||||
static char b[] = "Edit>";
|
||||
|
||||
return (continuation ? b : a);
|
||||
}
|
||||
|
||||
static void
|
||||
sig(int i)
|
||||
{
|
||||
|
||||
(void) fprintf(stderr, "Got signal %d.\n", i);
|
||||
el_reset(el);
|
||||
}
|
||||
|
||||
static unsigned char
|
||||
complete(EditLine *el, int ch)
|
||||
{
|
||||
DIR *dd = opendir(".");
|
||||
struct dirent *dp;
|
||||
const char* ptr;
|
||||
const LineInfo *lf = el_line(el);
|
||||
int len;
|
||||
|
||||
/*
|
||||
* Find the last word
|
||||
*/
|
||||
for (ptr = lf->cursor - 1; !isspace(*ptr) && ptr > lf->buffer; ptr--)
|
||||
continue;
|
||||
len = lf->cursor - ++ptr;
|
||||
|
||||
for (dp = readdir(dd); dp != NULL; dp = readdir(dd)) {
|
||||
if (len > strlen(dp->d_name))
|
||||
continue;
|
||||
if (strncmp(dp->d_name, ptr, len) == 0) {
|
||||
closedir(dd);
|
||||
if (el_insertstr(el, &dp->d_name[len]) == -1)
|
||||
return (CC_ERROR);
|
||||
else
|
||||
return (CC_REFRESH);
|
||||
}
|
||||
}
|
||||
|
||||
closedir(dd);
|
||||
return (CC_ERROR);
|
||||
}
|
||||
|
||||
int
|
||||
main(int argc, char *argv[])
|
||||
{
|
||||
int num;
|
||||
const char *buf;
|
||||
Tokenizer *tok;
|
||||
#if 0
|
||||
int lastevent = 0;
|
||||
#endif
|
||||
int ncontinuation;
|
||||
History *hist;
|
||||
HistEvent ev;
|
||||
|
||||
(void) signal(SIGINT, sig);
|
||||
(void) signal(SIGQUIT, sig);
|
||||
(void) signal(SIGHUP, sig);
|
||||
(void) signal(SIGTERM, sig);
|
||||
|
||||
hist = history_init(); /* Init the builtin history */
|
||||
/* Remember 100 events */
|
||||
history(hist, &ev, H_SETSIZE, 100);
|
||||
|
||||
tok = tok_init(NULL); /* Initialize the tokenizer */
|
||||
|
||||
/* Initialize editline */
|
||||
el = el_init(*argv, stdin, stdout, stderr);
|
||||
|
||||
el_set(el, EL_EDITOR, "vi"); /* Default editor is vi */
|
||||
el_set(el, EL_SIGNAL, 1); /* Handle signals gracefully */
|
||||
el_set(el, EL_PROMPT, prompt); /* Set the prompt function */
|
||||
|
||||
/* Tell editline to use this history interface */
|
||||
el_set(el, EL_HIST, history, hist);
|
||||
|
||||
/* Add a user-defined function */
|
||||
el_set(el, EL_ADDFN, "ed-complete", "Complete argument", complete);
|
||||
|
||||
/* Bind tab to it */
|
||||
el_set(el, EL_BIND, "^I", "ed-complete", NULL);
|
||||
|
||||
/*
|
||||
* Bind j, k in vi command mode to previous and next line, instead
|
||||
* of previous and next history.
|
||||
*/
|
||||
el_set(el, EL_BIND, "-a", "k", "ed-prev-line", NULL);
|
||||
el_set(el, EL_BIND, "-a", "j", "ed-next-line", NULL);
|
||||
|
||||
/*
|
||||
* Source the user's defaults file.
|
||||
*/
|
||||
el_source(el, NULL);
|
||||
|
||||
while ((buf = el_gets(el, &num)) != NULL && num != 0) {
|
||||
int ac;
|
||||
const char **av;
|
||||
#ifdef DEBUG
|
||||
(void) fprintf(stderr, "got %d %s", num, buf);
|
||||
#endif
|
||||
if (!continuation && num == 1)
|
||||
continue;
|
||||
|
||||
ncontinuation = tok_line(tok, buf, &ac, &av) > 0;
|
||||
#if 0
|
||||
if (continuation) {
|
||||
/*
|
||||
* Append to the right event in case the user
|
||||
* moved around in history.
|
||||
*/
|
||||
if (history(hist, &ev, H_SET, lastevent) == -1)
|
||||
err(1, "%d: %s\n", lastevent, ev.str);
|
||||
history(hist, &ev, H_ADD , buf);
|
||||
} else {
|
||||
history(hist, &ev, H_ENTER, buf);
|
||||
lastevent = ev.num;
|
||||
}
|
||||
#else
|
||||
/* Simpler */
|
||||
history(hist, &ev, continuation ? H_APPEND : H_ENTER, buf);
|
||||
#endif
|
||||
|
||||
continuation = ncontinuation;
|
||||
ncontinuation = 0;
|
||||
|
||||
if (strcmp(av[0], "history") == 0) {
|
||||
int rv;
|
||||
|
||||
switch (ac) {
|
||||
case 1:
|
||||
for (rv = history(hist, &ev, H_LAST); rv != -1;
|
||||
rv = history(hist, &ev, H_PREV))
|
||||
(void) fprintf(stdout, "%4d %s",
|
||||
ev.num, ev.str);
|
||||
break;
|
||||
|
||||
case 2:
|
||||
if (strcmp(av[1], "clear") == 0)
|
||||
history(hist, &ev, H_CLEAR);
|
||||
else
|
||||
goto badhist;
|
||||
break;
|
||||
|
||||
case 3:
|
||||
if (strcmp(av[1], "load") == 0)
|
||||
history(hist, &ev, H_LOAD, av[2]);
|
||||
else if (strcmp(av[1], "save") == 0)
|
||||
history(hist, &ev, H_SAVE, av[2]);
|
||||
break;
|
||||
|
||||
badhist:
|
||||
default:
|
||||
(void) fprintf(stderr,
|
||||
"Bad history arguments\n");
|
||||
break;
|
||||
}
|
||||
} else if (el_parse(el, ac, av) == -1) {
|
||||
switch (fork()) {
|
||||
case 0:
|
||||
execvp(av[0], (char *const *)av);
|
||||
perror(av[0]);
|
||||
_exit(1);
|
||||
/*NOTREACHED*/
|
||||
break;
|
||||
|
||||
case -1:
|
||||
perror("fork");
|
||||
break;
|
||||
|
||||
default:
|
||||
if (wait(&num) == -1)
|
||||
perror("wait");
|
||||
(void) fprintf(stderr, "Exit %x\n", num);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
tok_reset(tok);
|
||||
}
|
||||
|
||||
el_end(el);
|
||||
tok_end(tok);
|
||||
history_end(hist);
|
||||
|
||||
return (0);
|
||||
}
|
@@ -1,695 +0,0 @@
|
||||
/* $NetBSD: chared.c,v 1.15 2002/03/18 16:00:50 christos Exp $ */
|
||||
|
||||
/*-
|
||||
* Copyright (c) 1992, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* This code is derived from software contributed to Berkeley by
|
||||
* Christos Zoulas of Cornell University.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
* 3. All advertising materials mentioning features or use of this software
|
||||
* must display the following acknowledgement:
|
||||
* This product includes software developed by the University of
|
||||
* California, Berkeley and its contributors.
|
||||
* 4. Neither the name of the University nor the names of its contributors
|
||||
* may be used to endorse or promote products derived from this software
|
||||
* without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
|
||||
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
* ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
|
||||
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
|
||||
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*/
|
||||
|
||||
#include "config.h"
|
||||
#if !defined(lint) && !defined(SCCSID)
|
||||
#if 0
|
||||
static char sccsid[] = "@(#)chared.c 8.1 (Berkeley) 6/4/93";
|
||||
#else
|
||||
__RCSID("$NetBSD: chared.c,v 1.15 2002/03/18 16:00:50 christos Exp $");
|
||||
#endif
|
||||
#endif /* not lint && not SCCSID */
|
||||
|
||||
/*
|
||||
* chared.c: Character editor utilities
|
||||
*/
|
||||
#include <stdlib.h>
|
||||
#include "el.h"
|
||||
|
||||
/* value to leave unused in line buffer */
|
||||
#define EL_LEAVE 2
|
||||
|
||||
/* cv_undo():
|
||||
* Handle state for the vi undo command
|
||||
*/
|
||||
protected void
|
||||
cv_undo(EditLine *el,int action, size_t size, char *ptr)
|
||||
{
|
||||
c_undo_t *vu = &el->el_chared.c_undo;
|
||||
vu->action = action;
|
||||
vu->ptr = ptr;
|
||||
vu->isize = size;
|
||||
(void) memcpy(vu->buf, vu->ptr, size);
|
||||
#ifdef DEBUG_UNDO
|
||||
(void) fprintf(el->el_errfile, "Undo buffer \"%s\" size = +%d -%d\n",
|
||||
vu->ptr, vu->isize, vu->dsize);
|
||||
#endif
|
||||
}
|
||||
|
||||
|
||||
/* c_insert():
|
||||
* Insert num characters
|
||||
*/
|
||||
protected void
|
||||
c_insert(EditLine *el, int num)
|
||||
{
|
||||
char *cp;
|
||||
|
||||
if (el->el_line.lastchar + num >= el->el_line.limit)
|
||||
return; /* can't go past end of buffer */
|
||||
|
||||
if (el->el_line.cursor < el->el_line.lastchar) {
|
||||
/* if I must move chars */
|
||||
for (cp = el->el_line.lastchar; cp >= el->el_line.cursor; cp--)
|
||||
cp[num] = *cp;
|
||||
}
|
||||
el->el_line.lastchar += num;
|
||||
}
|
||||
|
||||
|
||||
/* c_delafter():
|
||||
* Delete num characters after the cursor
|
||||
*/
|
||||
protected void
|
||||
c_delafter(EditLine *el, int num)
|
||||
{
|
||||
|
||||
if (el->el_line.cursor + num > el->el_line.lastchar)
|
||||
num = el->el_line.lastchar - el->el_line.cursor;
|
||||
|
||||
if (num > 0) {
|
||||
char *cp;
|
||||
|
||||
if (el->el_map.current != el->el_map.emacs)
|
||||
cv_undo(el, INSERT, (size_t)num, el->el_line.cursor);
|
||||
|
||||
for (cp = el->el_line.cursor; cp <= el->el_line.lastchar; cp++)
|
||||
*cp = cp[num];
|
||||
|
||||
el->el_line.lastchar -= num;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/* c_delbefore():
|
||||
* Delete num characters before the cursor
|
||||
*/
|
||||
protected void
|
||||
c_delbefore(EditLine *el, int num)
|
||||
{
|
||||
|
||||
if (el->el_line.cursor - num < el->el_line.buffer)
|
||||
num = el->el_line.cursor - el->el_line.buffer;
|
||||
|
||||
if (num > 0) {
|
||||
char *cp;
|
||||
|
||||
if (el->el_map.current != el->el_map.emacs)
|
||||
cv_undo(el, INSERT, (size_t)num,
|
||||
el->el_line.cursor - num);
|
||||
|
||||
for (cp = el->el_line.cursor - num;
|
||||
cp <= el->el_line.lastchar;
|
||||
cp++)
|
||||
*cp = cp[num];
|
||||
|
||||
el->el_line.lastchar -= num;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/* ce__isword():
|
||||
* Return if p is part of a word according to emacs
|
||||
*/
|
||||
protected int
|
||||
ce__isword(int p)
|
||||
{
|
||||
return (isalpha(p) || isdigit(p) || strchr("*?_-.[]~=", p) != NULL);
|
||||
}
|
||||
|
||||
|
||||
/* cv__isword():
|
||||
* Return if p is part of a word according to vi
|
||||
*/
|
||||
protected int
|
||||
cv__isword(int p)
|
||||
{
|
||||
return (!isspace(p));
|
||||
}
|
||||
|
||||
|
||||
/* c__prev_word():
|
||||
* Find the previous word
|
||||
*/
|
||||
protected char *
|
||||
c__prev_word(char *p, char *low, int n, int (*wtest)(int))
|
||||
{
|
||||
p--;
|
||||
|
||||
while (n--) {
|
||||
while ((p >= low) && !(*wtest)((unsigned char) *p))
|
||||
p--;
|
||||
while ((p >= low) && (*wtest)((unsigned char) *p))
|
||||
p--;
|
||||
}
|
||||
|
||||
/* cp now points to one character before the word */
|
||||
p++;
|
||||
if (p < low)
|
||||
p = low;
|
||||
/* cp now points where we want it */
|
||||
return (p);
|
||||
}
|
||||
|
||||
|
||||
/* c__next_word():
|
||||
* Find the next word
|
||||
*/
|
||||
protected char *
|
||||
c__next_word(char *p, char *high, int n, int (*wtest)(int))
|
||||
{
|
||||
while (n--) {
|
||||
while ((p < high) && !(*wtest)((unsigned char) *p))
|
||||
p++;
|
||||
while ((p < high) && (*wtest)((unsigned char) *p))
|
||||
p++;
|
||||
}
|
||||
if (p > high)
|
||||
p = high;
|
||||
/* p now points where we want it */
|
||||
return (p);
|
||||
}
|
||||
|
||||
/* cv_next_word():
|
||||
* Find the next word vi style
|
||||
*/
|
||||
protected char *
|
||||
cv_next_word(EditLine *el, char *p, char *high, int n, int (*wtest)(int))
|
||||
{
|
||||
int test;
|
||||
|
||||
while (n--) {
|
||||
test = (*wtest)((unsigned char) *p);
|
||||
while ((p < high) && (*wtest)((unsigned char) *p) == test)
|
||||
p++;
|
||||
/*
|
||||
* vi historically deletes with cw only the word preserving the
|
||||
* trailing whitespace! This is not what 'w' does..
|
||||
*/
|
||||
if (el->el_chared.c_vcmd.action != (DELETE|INSERT))
|
||||
while ((p < high) && isspace((unsigned char) *p))
|
||||
p++;
|
||||
}
|
||||
|
||||
/* p now points where we want it */
|
||||
if (p > high)
|
||||
return (high);
|
||||
else
|
||||
return (p);
|
||||
}
|
||||
|
||||
|
||||
/* cv_prev_word():
|
||||
* Find the previous word vi style
|
||||
*/
|
||||
protected char *
|
||||
cv_prev_word(EditLine *el, char *p, char *low, int n, int (*wtest)(int))
|
||||
{
|
||||
int test;
|
||||
|
||||
while (n--) {
|
||||
p--;
|
||||
/*
|
||||
* vi historically deletes with cb only the word preserving the
|
||||
* leading whitespace! This is not what 'b' does..
|
||||
*/
|
||||
if (el->el_chared.c_vcmd.action != (DELETE|INSERT))
|
||||
while ((p > low) && isspace((unsigned char) *p))
|
||||
p--;
|
||||
test = (*wtest)((unsigned char) *p);
|
||||
while ((p >= low) && (*wtest)((unsigned char) *p) == test)
|
||||
p--;
|
||||
p++;
|
||||
while (isspace((unsigned char) *p))
|
||||
p++;
|
||||
}
|
||||
|
||||
/* p now points where we want it */
|
||||
if (p < low)
|
||||
return (low);
|
||||
else
|
||||
return (p);
|
||||
}
|
||||
|
||||
|
||||
#ifdef notdef
|
||||
/* c__number():
|
||||
* Ignore character p points to, return number appearing after that.
|
||||
* A '$' by itself means a big number; "$-" is for negative; '^' means 1.
|
||||
* Return p pointing to last char used.
|
||||
*/
|
||||
protected char *
|
||||
c__number(
|
||||
char *p, /* character position */
|
||||
int *num, /* Return value */
|
||||
int dval) /* dval is the number to subtract from like $-3 */
|
||||
{
|
||||
int i;
|
||||
int sign = 1;
|
||||
|
||||
if (*++p == '^') {
|
||||
*num = 1;
|
||||
return (p);
|
||||
}
|
||||
if (*p == '$') {
|
||||
if (*++p != '-') {
|
||||
*num = 0x7fffffff; /* Handle $ */
|
||||
return (--p);
|
||||
}
|
||||
sign = -1; /* Handle $- */
|
||||
++p;
|
||||
}
|
||||
for (i = 0; isdigit((unsigned char) *p); i = 10 * i + *p++ - '0')
|
||||
continue;
|
||||
*num = (sign < 0 ? dval - i : i);
|
||||
return (--p);
|
||||
}
|
||||
#endif
|
||||
|
||||
/* cv_delfini():
|
||||
* Finish vi delete action
|
||||
*/
|
||||
protected void
|
||||
cv_delfini(EditLine *el)
|
||||
{
|
||||
int size;
|
||||
int oaction;
|
||||
|
||||
if (el->el_chared.c_vcmd.action & INSERT)
|
||||
el->el_map.current = el->el_map.key;
|
||||
|
||||
oaction = el->el_chared.c_vcmd.action;
|
||||
el->el_chared.c_vcmd.action = NOP;
|
||||
|
||||
if (el->el_chared.c_vcmd.pos == 0)
|
||||
return;
|
||||
|
||||
|
||||
if (el->el_line.cursor > el->el_chared.c_vcmd.pos) {
|
||||
size = (int) (el->el_line.cursor - el->el_chared.c_vcmd.pos);
|
||||
c_delbefore(el, size);
|
||||
el->el_line.cursor = el->el_chared.c_vcmd.pos;
|
||||
re_refresh_cursor(el);
|
||||
} else if (el->el_line.cursor < el->el_chared.c_vcmd.pos) {
|
||||
size = (int)(el->el_chared.c_vcmd.pos - el->el_line.cursor);
|
||||
c_delafter(el, size);
|
||||
} else {
|
||||
size = 1;
|
||||
c_delafter(el, size);
|
||||
}
|
||||
switch (oaction) {
|
||||
case DELETE|INSERT:
|
||||
el->el_chared.c_undo.action = DELETE|INSERT;
|
||||
break;
|
||||
case DELETE:
|
||||
el->el_chared.c_undo.action = INSERT;
|
||||
break;
|
||||
case NOP:
|
||||
case INSERT:
|
||||
default:
|
||||
EL_ABORT((el->el_errfile, "Bad oaction %d\n", oaction));
|
||||
break;
|
||||
}
|
||||
|
||||
|
||||
el->el_chared.c_undo.ptr = el->el_line.cursor;
|
||||
el->el_chared.c_undo.dsize = size;
|
||||
}
|
||||
|
||||
|
||||
#ifdef notdef
|
||||
/* ce__endword():
|
||||
* Go to the end of this word according to emacs
|
||||
*/
|
||||
protected char *
|
||||
ce__endword(char *p, char *high, int n)
|
||||
{
|
||||
p++;
|
||||
|
||||
while (n--) {
|
||||
while ((p < high) && isspace((unsigned char) *p))
|
||||
p++;
|
||||
while ((p < high) && !isspace((unsigned char) *p))
|
||||
p++;
|
||||
}
|
||||
|
||||
p--;
|
||||
return (p);
|
||||
}
|
||||
#endif
|
||||
|
||||
|
||||
/* cv__endword():
|
||||
* Go to the end of this word according to vi
|
||||
*/
|
||||
protected char *
|
||||
cv__endword(char *p, char *high, int n)
|
||||
{
|
||||
p++;
|
||||
|
||||
while (n--) {
|
||||
while ((p < high) && isspace((unsigned char) *p))
|
||||
p++;
|
||||
|
||||
if (isalnum((unsigned char) *p))
|
||||
while ((p < high) && isalnum((unsigned char) *p))
|
||||
p++;
|
||||
else
|
||||
while ((p < high) && !(isspace((unsigned char) *p) ||
|
||||
isalnum((unsigned char) *p)))
|
||||
p++;
|
||||
}
|
||||
p--;
|
||||
return (p);
|
||||
}
|
||||
|
||||
/* ch_init():
|
||||
* Initialize the character editor
|
||||
*/
|
||||
protected int
|
||||
ch_init(EditLine *el)
|
||||
{
|
||||
el->el_line.buffer = (char *) el_malloc(EL_BUFSIZ);
|
||||
if (el->el_line.buffer == NULL)
|
||||
return (-1);
|
||||
|
||||
(void) memset(el->el_line.buffer, 0, EL_BUFSIZ);
|
||||
el->el_line.cursor = el->el_line.buffer;
|
||||
el->el_line.lastchar = el->el_line.buffer;
|
||||
el->el_line.limit = &el->el_line.buffer[EL_BUFSIZ - 2];
|
||||
|
||||
el->el_chared.c_undo.buf = (char *) el_malloc(EL_BUFSIZ);
|
||||
if (el->el_chared.c_undo.buf == NULL)
|
||||
return (-1);
|
||||
(void) memset(el->el_chared.c_undo.buf, 0, EL_BUFSIZ);
|
||||
el->el_chared.c_undo.action = NOP;
|
||||
el->el_chared.c_undo.isize = 0;
|
||||
el->el_chared.c_undo.dsize = 0;
|
||||
el->el_chared.c_undo.ptr = el->el_line.buffer;
|
||||
|
||||
el->el_chared.c_vcmd.action = NOP;
|
||||
el->el_chared.c_vcmd.pos = el->el_line.buffer;
|
||||
el->el_chared.c_vcmd.ins = el->el_line.buffer;
|
||||
|
||||
el->el_chared.c_kill.buf = (char *) el_malloc(EL_BUFSIZ);
|
||||
if (el->el_chared.c_kill.buf == NULL)
|
||||
return (-1);
|
||||
(void) memset(el->el_chared.c_kill.buf, 0, EL_BUFSIZ);
|
||||
el->el_chared.c_kill.mark = el->el_line.buffer;
|
||||
el->el_chared.c_kill.last = el->el_chared.c_kill.buf;
|
||||
|
||||
el->el_map.current = el->el_map.key;
|
||||
|
||||
el->el_state.inputmode = MODE_INSERT; /* XXX: save a default */
|
||||
el->el_state.doingarg = 0;
|
||||
el->el_state.metanext = 0;
|
||||
el->el_state.argument = 1;
|
||||
el->el_state.lastcmd = ED_UNASSIGNED;
|
||||
|
||||
el->el_chared.c_macro.nline = NULL;
|
||||
el->el_chared.c_macro.level = -1;
|
||||
el->el_chared.c_macro.macro = (char **) el_malloc(EL_MAXMACRO *
|
||||
sizeof(char *));
|
||||
if (el->el_chared.c_macro.macro == NULL)
|
||||
return (-1);
|
||||
return (0);
|
||||
}
|
||||
|
||||
/* ch_reset():
|
||||
* Reset the character editor
|
||||
*/
|
||||
protected void
|
||||
ch_reset(EditLine *el)
|
||||
{
|
||||
el->el_line.cursor = el->el_line.buffer;
|
||||
el->el_line.lastchar = el->el_line.buffer;
|
||||
|
||||
el->el_chared.c_undo.action = NOP;
|
||||
el->el_chared.c_undo.isize = 0;
|
||||
el->el_chared.c_undo.dsize = 0;
|
||||
el->el_chared.c_undo.ptr = el->el_line.buffer;
|
||||
|
||||
el->el_chared.c_vcmd.action = NOP;
|
||||
el->el_chared.c_vcmd.pos = el->el_line.buffer;
|
||||
el->el_chared.c_vcmd.ins = el->el_line.buffer;
|
||||
|
||||
el->el_chared.c_kill.mark = el->el_line.buffer;
|
||||
|
||||
el->el_map.current = el->el_map.key;
|
||||
|
||||
el->el_state.inputmode = MODE_INSERT; /* XXX: save a default */
|
||||
el->el_state.doingarg = 0;
|
||||
el->el_state.metanext = 0;
|
||||
el->el_state.argument = 1;
|
||||
el->el_state.lastcmd = ED_UNASSIGNED;
|
||||
|
||||
el->el_chared.c_macro.level = -1;
|
||||
|
||||
el->el_history.eventno = 0;
|
||||
}
|
||||
|
||||
/* ch_enlargebufs():
|
||||
* Enlarge line buffer to be able to hold twice as much characters.
|
||||
* Returns 1 if successful, 0 if not.
|
||||
*/
|
||||
protected int
|
||||
ch_enlargebufs(el, addlen)
|
||||
EditLine *el;
|
||||
size_t addlen;
|
||||
{
|
||||
size_t sz, newsz;
|
||||
char *newbuffer, *oldbuf, *oldkbuf;
|
||||
|
||||
sz = el->el_line.limit - el->el_line.buffer + EL_LEAVE;
|
||||
newsz = sz * 2;
|
||||
/*
|
||||
* If newly required length is longer than current buffer, we need
|
||||
* to make the buffer big enough to hold both old and new stuff.
|
||||
*/
|
||||
if (addlen > sz) {
|
||||
while(newsz - sz < addlen)
|
||||
newsz *= 2;
|
||||
}
|
||||
|
||||
/*
|
||||
* Reallocate line buffer.
|
||||
*/
|
||||
newbuffer = el_realloc(el->el_line.buffer, newsz);
|
||||
if (!newbuffer)
|
||||
return 0;
|
||||
|
||||
/* zero the newly added memory, leave old data in */
|
||||
(void) memset(&newbuffer[sz], 0, newsz - sz);
|
||||
|
||||
oldbuf = el->el_line.buffer;
|
||||
|
||||
el->el_line.buffer = newbuffer;
|
||||
el->el_line.cursor = newbuffer + (el->el_line.cursor - oldbuf);
|
||||
el->el_line.lastchar = newbuffer + (el->el_line.lastchar - oldbuf);
|
||||
el->el_line.limit = &newbuffer[newsz - EL_LEAVE];
|
||||
|
||||
/*
|
||||
* Reallocate kill buffer.
|
||||
*/
|
||||
newbuffer = el_realloc(el->el_chared.c_kill.buf, newsz);
|
||||
if (!newbuffer)
|
||||
return 0;
|
||||
|
||||
/* zero the newly added memory, leave old data in */
|
||||
(void) memset(&newbuffer[sz], 0, newsz - sz);
|
||||
|
||||
oldkbuf = el->el_chared.c_kill.buf;
|
||||
|
||||
el->el_chared.c_kill.buf = newbuffer;
|
||||
el->el_chared.c_kill.last = newbuffer +
|
||||
(el->el_chared.c_kill.last - oldkbuf);
|
||||
el->el_chared.c_kill.mark = el->el_line.buffer +
|
||||
(el->el_chared.c_kill.mark - oldbuf);
|
||||
|
||||
/*
|
||||
* Reallocate undo buffer.
|
||||
*/
|
||||
newbuffer = el_realloc(el->el_chared.c_undo.buf, newsz);
|
||||
if (!newbuffer)
|
||||
return 0;
|
||||
|
||||
/* zero the newly added memory, leave old data in */
|
||||
(void) memset(&newbuffer[sz], 0, newsz - sz);
|
||||
|
||||
el->el_chared.c_undo.ptr = el->el_line.buffer +
|
||||
(el->el_chared.c_undo.ptr - oldbuf);
|
||||
el->el_chared.c_undo.buf = newbuffer;
|
||||
|
||||
if (!hist_enlargebuf(el, sz, newsz))
|
||||
return 0;
|
||||
|
||||
return 1;
|
||||
}
|
||||
|
||||
/* ch_end():
|
||||
* Free the data structures used by the editor
|
||||
*/
|
||||
protected void
|
||||
ch_end(EditLine *el)
|
||||
{
|
||||
el_free((ptr_t) el->el_line.buffer);
|
||||
el->el_line.buffer = NULL;
|
||||
el->el_line.limit = NULL;
|
||||
el_free((ptr_t) el->el_chared.c_undo.buf);
|
||||
el->el_chared.c_undo.buf = NULL;
|
||||
el_free((ptr_t) el->el_chared.c_kill.buf);
|
||||
el->el_chared.c_kill.buf = NULL;
|
||||
el_free((ptr_t) el->el_chared.c_macro.macro);
|
||||
el->el_chared.c_macro.macro = NULL;
|
||||
ch_reset(el);
|
||||
}
|
||||
|
||||
|
||||
/* el_insertstr():
|
||||
* Insert string at cursorI
|
||||
*/
|
||||
public int
|
||||
el_insertstr(EditLine *el, const char *s)
|
||||
{
|
||||
size_t len;
|
||||
|
||||
if ((len = strlen(s)) == 0)
|
||||
return (-1);
|
||||
if (el->el_line.lastchar + len >= el->el_line.limit) {
|
||||
if (!ch_enlargebufs(el, len))
|
||||
return (-1);
|
||||
}
|
||||
|
||||
c_insert(el, (int)len);
|
||||
while (*s)
|
||||
*el->el_line.cursor++ = *s++;
|
||||
return (0);
|
||||
}
|
||||
|
||||
|
||||
/* el_deletestr():
|
||||
* Delete num characters before the cursor
|
||||
*/
|
||||
public void
|
||||
el_deletestr(EditLine *el, int n)
|
||||
{
|
||||
if (n <= 0)
|
||||
return;
|
||||
|
||||
if (el->el_line.cursor < &el->el_line.buffer[n])
|
||||
return;
|
||||
|
||||
c_delbefore(el, n); /* delete before dot */
|
||||
el->el_line.cursor -= n;
|
||||
if (el->el_line.cursor < el->el_line.buffer)
|
||||
el->el_line.cursor = el->el_line.buffer;
|
||||
}
|
||||
|
||||
/* c_gets():
|
||||
* Get a string
|
||||
*/
|
||||
protected int
|
||||
c_gets(EditLine *el, char *buf)
|
||||
{
|
||||
char ch;
|
||||
int len = 0;
|
||||
|
||||
for (ch = 0; ch == 0;) {
|
||||
if (el_getc(el, &ch) != 1)
|
||||
return (ed_end_of_file(el, 0));
|
||||
switch (ch) {
|
||||
case 0010: /* Delete and backspace */
|
||||
case 0177:
|
||||
if (len > 1) {
|
||||
*el->el_line.cursor-- = '\0';
|
||||
el->el_line.lastchar = el->el_line.cursor;
|
||||
buf[len--] = '\0';
|
||||
} else {
|
||||
el->el_line.buffer[0] = '\0';
|
||||
el->el_line.lastchar = el->el_line.buffer;
|
||||
el->el_line.cursor = el->el_line.buffer;
|
||||
return (CC_REFRESH);
|
||||
}
|
||||
re_refresh(el);
|
||||
ch = 0;
|
||||
break;
|
||||
|
||||
case 0033: /* ESC */
|
||||
case '\r': /* Newline */
|
||||
case '\n':
|
||||
break;
|
||||
|
||||
default:
|
||||
if (len >= EL_BUFSIZ)
|
||||
term_beep(el);
|
||||
else {
|
||||
buf[len++] = ch;
|
||||
*el->el_line.cursor++ = ch;
|
||||
el->el_line.lastchar = el->el_line.cursor;
|
||||
}
|
||||
re_refresh(el);
|
||||
ch = 0;
|
||||
break;
|
||||
}
|
||||
}
|
||||
buf[len] = ch;
|
||||
return (len);
|
||||
}
|
||||
|
||||
|
||||
/* c_hpos():
|
||||
* Return the current horizontal position of the cursor
|
||||
*/
|
||||
protected int
|
||||
c_hpos(EditLine *el)
|
||||
{
|
||||
char *ptr;
|
||||
|
||||
/*
|
||||
* Find how many characters till the beginning of this line.
|
||||
*/
|
||||
if (el->el_line.cursor == el->el_line.buffer)
|
||||
return (0);
|
||||
else {
|
||||
for (ptr = el->el_line.cursor - 1;
|
||||
ptr >= el->el_line.buffer && *ptr != '\n';
|
||||
ptr--)
|
||||
continue;
|
||||
return (el->el_line.cursor - ptr - 1);
|
||||
}
|
||||
}
|
@@ -1,159 +0,0 @@
|
||||
/* $NetBSD: chared.h,v 1.8 2002/03/18 16:00:51 christos Exp $ */
|
||||
|
||||
/*-
|
||||
* Copyright (c) 1992, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* This code is derived from software contributed to Berkeley by
|
||||
* Christos Zoulas of Cornell University.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
* 3. All advertising materials mentioning features or use of this software
|
||||
* must display the following acknowledgement:
|
||||
* This product includes software developed by the University of
|
||||
* California, Berkeley and its contributors.
|
||||
* 4. Neither the name of the University nor the names of its contributors
|
||||
* may be used to endorse or promote products derived from this software
|
||||
* without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
|
||||
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
* ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
|
||||
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
|
||||
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* @(#)chared.h 8.1 (Berkeley) 6/4/93
|
||||
*/
|
||||
|
||||
/*
|
||||
* el.chared.h: Character editor interface
|
||||
*/
|
||||
#ifndef _h_el_chared
|
||||
#define _h_el_chared
|
||||
|
||||
#include <ctype.h>
|
||||
#include <string.h>
|
||||
|
||||
#include "histedit.h"
|
||||
|
||||
#define EL_MAXMACRO 10
|
||||
|
||||
/*
|
||||
* This is a issue of basic "vi" look-and-feel. Defining VI_MOVE works
|
||||
* like real vi: i.e. the transition from command<->insert modes moves
|
||||
* the cursor.
|
||||
*
|
||||
* On the other hand we really don't want to move the cursor, because
|
||||
* all the editing commands don't include the character under the cursor.
|
||||
* Probably the best fix is to make all the editing commands aware of
|
||||
* this fact.
|
||||
*/
|
||||
#define VI_MOVE
|
||||
|
||||
|
||||
typedef struct c_macro_t {
|
||||
int level;
|
||||
char **macro;
|
||||
char *nline;
|
||||
} c_macro_t;
|
||||
|
||||
/*
|
||||
* Undo information for both vi and emacs
|
||||
*/
|
||||
typedef struct c_undo_t {
|
||||
int action;
|
||||
size_t isize;
|
||||
size_t dsize;
|
||||
char *ptr;
|
||||
char *buf;
|
||||
} c_undo_t;
|
||||
|
||||
/*
|
||||
* Current action information for vi
|
||||
*/
|
||||
typedef struct c_vcmd_t {
|
||||
int action;
|
||||
char *pos;
|
||||
char *ins;
|
||||
} c_vcmd_t;
|
||||
|
||||
/*
|
||||
* Kill buffer for emacs
|
||||
*/
|
||||
typedef struct c_kill_t {
|
||||
char *buf;
|
||||
char *last;
|
||||
char *mark;
|
||||
} c_kill_t;
|
||||
|
||||
/*
|
||||
* Note that we use both data structures because the user can bind
|
||||
* commands from both editors!
|
||||
*/
|
||||
typedef struct el_chared_t {
|
||||
c_undo_t c_undo;
|
||||
c_kill_t c_kill;
|
||||
c_vcmd_t c_vcmd;
|
||||
c_macro_t c_macro;
|
||||
} el_chared_t;
|
||||
|
||||
|
||||
#define STReof "^D\b\b"
|
||||
#define STRQQ "\"\""
|
||||
|
||||
#define isglob(a) (strchr("*[]?", (a)) != NULL)
|
||||
#define isword(a) (isprint(a))
|
||||
|
||||
#define NOP 0x00
|
||||
#define DELETE 0x01
|
||||
#define INSERT 0x02
|
||||
#define CHANGE 0x04
|
||||
|
||||
#define CHAR_FWD 0
|
||||
#define CHAR_BACK 1
|
||||
|
||||
#define MODE_INSERT 0
|
||||
#define MODE_REPLACE 1
|
||||
#define MODE_REPLACE_1 2
|
||||
|
||||
#include "common.h"
|
||||
#include "vi.h"
|
||||
#include "emacs.h"
|
||||
#include "search.h"
|
||||
#include "fcns.h"
|
||||
|
||||
|
||||
protected int cv__isword(int);
|
||||
protected void cv_delfini(EditLine *);
|
||||
protected char *cv__endword(char *, char *, int);
|
||||
protected int ce__isword(int);
|
||||
protected void cv_undo(EditLine *, int, size_t, char *);
|
||||
protected char *cv_next_word(EditLine*, char *, char *, int, int (*)(int));
|
||||
protected char *cv_prev_word(EditLine*, char *, char *, int, int (*)(int));
|
||||
protected char *c__next_word(char *, char *, int, int (*)(int));
|
||||
protected char *c__prev_word(char *, char *, int, int (*)(int));
|
||||
protected void c_insert(EditLine *, int);
|
||||
protected void c_delbefore(EditLine *, int);
|
||||
protected void c_delafter(EditLine *, int);
|
||||
protected int c_gets(EditLine *, char *);
|
||||
protected int c_hpos(EditLine *);
|
||||
|
||||
protected int ch_init(EditLine *);
|
||||
protected void ch_reset(EditLine *);
|
||||
protected int ch_enlargebufs(EditLine *, size_t);
|
||||
protected void ch_end(EditLine *);
|
||||
|
||||
#endif /* _h_el_chared */
|
@@ -1,951 +0,0 @@
|
||||
/* $NetBSD: common.c,v 1.11 2002/03/18 16:00:51 christos Exp $ */
|
||||
|
||||
/*-
|
||||
* Copyright (c) 1992, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* This code is derived from software contributed to Berkeley by
|
||||
* Christos Zoulas of Cornell University.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
* 3. All advertising materials mentioning features or use of this software
|
||||
* must display the following acknowledgement:
|
||||
* This product includes software developed by the University of
|
||||
* California, Berkeley and its contributors.
|
||||
* 4. Neither the name of the University nor the names of its contributors
|
||||
* may be used to endorse or promote products derived from this software
|
||||
* without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
|
||||
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
* ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
|
||||
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
|
||||
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*/
|
||||
|
||||
#include "config.h"
|
||||
#if !defined(lint) && !defined(SCCSID)
|
||||
#if 0
|
||||
static char sccsid[] = "@(#)common.c 8.1 (Berkeley) 6/4/93";
|
||||
#else
|
||||
__RCSID("$NetBSD: common.c,v 1.11 2002/03/18 16:00:51 christos Exp $");
|
||||
#endif
|
||||
#endif /* not lint && not SCCSID */
|
||||
|
||||
/*
|
||||
* common.c: Common Editor functions
|
||||
*/
|
||||
#include "el.h"
|
||||
|
||||
/* ed_end_of_file():
|
||||
* Indicate end of file
|
||||
* [^D]
|
||||
*/
|
||||
protected el_action_t
|
||||
/*ARGSUSED*/
|
||||
ed_end_of_file(EditLine *el, int c)
|
||||
{
|
||||
|
||||
re_goto_bottom(el);
|
||||
*el->el_line.lastchar = '\0';
|
||||
return (CC_EOF);
|
||||
}
|
||||
|
||||
|
||||
/* ed_insert():
|
||||
* Add character to the line
|
||||
* Insert a character [bound to all insert keys]
|
||||
*/
|
||||
protected el_action_t
|
||||
ed_insert(EditLine *el, int c)
|
||||
{
|
||||
int i;
|
||||
|
||||
if (c == '\0')
|
||||
return (CC_ERROR);
|
||||
|
||||
if (el->el_line.lastchar + el->el_state.argument >=
|
||||
el->el_line.limit) {
|
||||
/* end of buffer space, try to allocate more */
|
||||
if (!ch_enlargebufs(el, (size_t) el->el_state.argument))
|
||||
return CC_ERROR; /* error allocating more */
|
||||
}
|
||||
|
||||
if (el->el_state.argument == 1) {
|
||||
if (el->el_state.inputmode != MODE_INSERT) {
|
||||
el->el_chared.c_undo.buf[el->el_chared.c_undo.isize++] =
|
||||
*el->el_line.cursor;
|
||||
el->el_chared.c_undo.buf[el->el_chared.c_undo.isize] =
|
||||
'\0';
|
||||
c_delafter(el, 1);
|
||||
}
|
||||
c_insert(el, 1);
|
||||
|
||||
*el->el_line.cursor++ = c;
|
||||
el->el_state.doingarg = 0; /* just in case */
|
||||
re_fastaddc(el); /* fast refresh for one char. */
|
||||
} else {
|
||||
if (el->el_state.inputmode != MODE_INSERT) {
|
||||
for (i = 0; i < el->el_state.argument; i++)
|
||||
el->el_chared.c_undo.buf[el->el_chared.c_undo.isize++] =
|
||||
el->el_line.cursor[i];
|
||||
|
||||
el->el_chared.c_undo.buf[el->el_chared.c_undo.isize] =
|
||||
'\0';
|
||||
c_delafter(el, el->el_state.argument);
|
||||
}
|
||||
c_insert(el, el->el_state.argument);
|
||||
|
||||
while (el->el_state.argument--)
|
||||
*el->el_line.cursor++ = c;
|
||||
re_refresh(el);
|
||||
}
|
||||
|
||||
if (el->el_state.inputmode == MODE_REPLACE_1)
|
||||
(void) vi_command_mode(el, 0);
|
||||
|
||||
return (CC_NORM);
|
||||
}
|
||||
|
||||
|
||||
/* ed_delete_prev_word():
|
||||
* Delete from beginning of current word to cursor
|
||||
* [M-^?] [^W]
|
||||
*/
|
||||
protected el_action_t
|
||||
/*ARGSUSED*/
|
||||
ed_delete_prev_word(EditLine *el, int c)
|
||||
{
|
||||
char *cp, *p, *kp;
|
||||
|
||||
if (el->el_line.cursor == el->el_line.buffer)
|
||||
return (CC_ERROR);
|
||||
|
||||
cp = c__prev_word(el->el_line.cursor, el->el_line.buffer,
|
||||
el->el_state.argument, ce__isword);
|
||||
|
||||
for (p = cp, kp = el->el_chared.c_kill.buf; p < el->el_line.cursor; p++)
|
||||
*kp++ = *p;
|
||||
el->el_chared.c_kill.last = kp;
|
||||
|
||||
c_delbefore(el, el->el_line.cursor - cp); /* delete before dot */
|
||||
el->el_line.cursor = cp;
|
||||
if (el->el_line.cursor < el->el_line.buffer)
|
||||
el->el_line.cursor = el->el_line.buffer; /* bounds check */
|
||||
return (CC_REFRESH);
|
||||
}
|
||||
|
||||
|
||||
/* ed_delete_next_char():
|
||||
* Delete character under cursor
|
||||
* [^D] [x]
|
||||
*/
|
||||
protected el_action_t
|
||||
/*ARGSUSED*/
|
||||
ed_delete_next_char(EditLine *el, int c)
|
||||
{
|
||||
#ifdef notdef /* XXX */
|
||||
#define EL el->el_line
|
||||
(void) fprintf(el->el_errlfile,
|
||||
"\nD(b: %x(%s) c: %x(%s) last: %x(%s) limit: %x(%s)\n",
|
||||
EL.buffer, EL.buffer, EL.cursor, EL.cursor, EL.lastchar,
|
||||
EL.lastchar, EL.limit, EL.limit);
|
||||
#endif
|
||||
if (el->el_line.cursor == el->el_line.lastchar) {
|
||||
/* if I'm at the end */
|
||||
if (el->el_map.type == MAP_VI) {
|
||||
if (el->el_line.cursor == el->el_line.buffer) {
|
||||
/* if I'm also at the beginning */
|
||||
#ifdef KSHVI
|
||||
return (CC_ERROR);
|
||||
#else
|
||||
term_overwrite(el, STReof, 4);
|
||||
/* then do a EOF */
|
||||
term__flush();
|
||||
return (CC_EOF);
|
||||
#endif
|
||||
} else {
|
||||
#ifdef KSHVI
|
||||
el->el_line.cursor--;
|
||||
#else
|
||||
return (CC_ERROR);
|
||||
#endif
|
||||
}
|
||||
} else {
|
||||
if (el->el_line.cursor != el->el_line.buffer)
|
||||
el->el_line.cursor--;
|
||||
else
|
||||
return (CC_ERROR);
|
||||
}
|
||||
}
|
||||
c_delafter(el, el->el_state.argument); /* delete after dot */
|
||||
if (el->el_line.cursor >= el->el_line.lastchar &&
|
||||
el->el_line.cursor > el->el_line.buffer)
|
||||
/* bounds check */
|
||||
el->el_line.cursor = el->el_line.lastchar - 1;
|
||||
return (CC_REFRESH);
|
||||
}
|
||||
|
||||
|
||||
/* ed_kill_line():
|
||||
* Cut to the end of line
|
||||
* [^K] [^K]
|
||||
*/
|
||||
protected el_action_t
|
||||
/*ARGSUSED*/
|
||||
ed_kill_line(EditLine *el, int c)
|
||||
{
|
||||
char *kp, *cp;
|
||||
|
||||
cp = el->el_line.cursor;
|
||||
kp = el->el_chared.c_kill.buf;
|
||||
while (cp < el->el_line.lastchar)
|
||||
*kp++ = *cp++; /* copy it */
|
||||
el->el_chared.c_kill.last = kp;
|
||||
/* zap! -- delete to end */
|
||||
el->el_line.lastchar = el->el_line.cursor;
|
||||
return (CC_REFRESH);
|
||||
}
|
||||
|
||||
|
||||
/* ed_move_to_end():
|
||||
* Move cursor to the end of line
|
||||
* [^E] [^E]
|
||||
*/
|
||||
protected el_action_t
|
||||
/*ARGSUSED*/
|
||||
ed_move_to_end(EditLine *el, int c)
|
||||
{
|
||||
|
||||
el->el_line.cursor = el->el_line.lastchar;
|
||||
if (el->el_map.type == MAP_VI) {
|
||||
#ifdef VI_MOVE
|
||||
el->el_line.cursor--;
|
||||
#endif
|
||||
if (el->el_chared.c_vcmd.action & DELETE) {
|
||||
cv_delfini(el);
|
||||
return (CC_REFRESH);
|
||||
}
|
||||
}
|
||||
return (CC_CURSOR);
|
||||
}
|
||||
|
||||
|
||||
/* ed_move_to_beg():
|
||||
* Move cursor to the beginning of line
|
||||
* [^A] [^A]
|
||||
*/
|
||||
protected el_action_t
|
||||
/*ARGSUSED*/
|
||||
ed_move_to_beg(EditLine *el, int c)
|
||||
{
|
||||
|
||||
el->el_line.cursor = el->el_line.buffer;
|
||||
|
||||
if (el->el_map.type == MAP_VI) {
|
||||
/* We want FIRST non space character */
|
||||
while (isspace((unsigned char) *el->el_line.cursor))
|
||||
el->el_line.cursor++;
|
||||
if (el->el_chared.c_vcmd.action & DELETE) {
|
||||
cv_delfini(el);
|
||||
return (CC_REFRESH);
|
||||
}
|
||||
}
|
||||
return (CC_CURSOR);
|
||||
}
|
||||
|
||||
|
||||
/* ed_transpose_chars():
|
||||
* Exchange the character to the left of the cursor with the one under it
|
||||
* [^T] [^T]
|
||||
*/
|
||||
protected el_action_t
|
||||
ed_transpose_chars(EditLine *el, int c)
|
||||
{
|
||||
|
||||
if (el->el_line.cursor < el->el_line.lastchar) {
|
||||
if (el->el_line.lastchar <= &el->el_line.buffer[1])
|
||||
return (CC_ERROR);
|
||||
else
|
||||
el->el_line.cursor++;
|
||||
}
|
||||
if (el->el_line.cursor > &el->el_line.buffer[1]) {
|
||||
/* must have at least two chars entered */
|
||||
c = el->el_line.cursor[-2];
|
||||
el->el_line.cursor[-2] = el->el_line.cursor[-1];
|
||||
el->el_line.cursor[-1] = c;
|
||||
return (CC_REFRESH);
|
||||
} else
|
||||
return (CC_ERROR);
|
||||
}
|
||||
|
||||
|
||||
/* ed_next_char():
|
||||
* Move to the right one character
|
||||
* [^F] [^F]
|
||||
*/
|
||||
protected el_action_t
|
||||
/*ARGSUSED*/
|
||||
ed_next_char(EditLine *el, int c)
|
||||
{
|
||||
|
||||
if (el->el_line.cursor >= el->el_line.lastchar)
|
||||
return (CC_ERROR);
|
||||
|
||||
el->el_line.cursor += el->el_state.argument;
|
||||
if (el->el_line.cursor > el->el_line.lastchar)
|
||||
el->el_line.cursor = el->el_line.lastchar;
|
||||
|
||||
if (el->el_map.type == MAP_VI)
|
||||
if (el->el_chared.c_vcmd.action & DELETE) {
|
||||
cv_delfini(el);
|
||||
return (CC_REFRESH);
|
||||
}
|
||||
return (CC_CURSOR);
|
||||
}
|
||||
|
||||
|
||||
/* ed_prev_word():
|
||||
* Move to the beginning of the current word
|
||||
* [M-b] [b]
|
||||
*/
|
||||
protected el_action_t
|
||||
/*ARGSUSED*/
|
||||
ed_prev_word(EditLine *el, int c)
|
||||
{
|
||||
|
||||
if (el->el_line.cursor == el->el_line.buffer)
|
||||
return (CC_ERROR);
|
||||
|
||||
el->el_line.cursor = c__prev_word(el->el_line.cursor,
|
||||
el->el_line.buffer,
|
||||
el->el_state.argument,
|
||||
ce__isword);
|
||||
|
||||
if (el->el_map.type == MAP_VI)
|
||||
if (el->el_chared.c_vcmd.action & DELETE) {
|
||||
cv_delfini(el);
|
||||
return (CC_REFRESH);
|
||||
}
|
||||
return (CC_CURSOR);
|
||||
}
|
||||
|
||||
|
||||
/* ed_prev_char():
|
||||
* Move to the left one character
|
||||
* [^B] [^B]
|
||||
*/
|
||||
protected el_action_t
|
||||
/*ARGSUSED*/
|
||||
ed_prev_char(EditLine *el, int c)
|
||||
{
|
||||
|
||||
if (el->el_line.cursor > el->el_line.buffer) {
|
||||
el->el_line.cursor -= el->el_state.argument;
|
||||
if (el->el_line.cursor < el->el_line.buffer)
|
||||
el->el_line.cursor = el->el_line.buffer;
|
||||
|
||||
if (el->el_map.type == MAP_VI)
|
||||
if (el->el_chared.c_vcmd.action & DELETE) {
|
||||
cv_delfini(el);
|
||||
return (CC_REFRESH);
|
||||
}
|
||||
return (CC_CURSOR);
|
||||
} else
|
||||
return (CC_ERROR);
|
||||
}
|
||||
|
||||
|
||||
/* ed_quoted_insert():
|
||||
* Add the next character typed verbatim
|
||||
* [^V] [^V]
|
||||
*/
|
||||
protected el_action_t
|
||||
ed_quoted_insert(EditLine *el, int c)
|
||||
{
|
||||
int num;
|
||||
char tc;
|
||||
|
||||
tty_quotemode(el);
|
||||
num = el_getc(el, &tc);
|
||||
c = (unsigned char) tc;
|
||||
tty_noquotemode(el);
|
||||
if (num == 1)
|
||||
return (ed_insert(el, c));
|
||||
else
|
||||
return (ed_end_of_file(el, 0));
|
||||
}
|
||||
|
||||
|
||||
/* ed_digit():
|
||||
* Adds to argument or enters a digit
|
||||
*/
|
||||
protected el_action_t
|
||||
ed_digit(EditLine *el, int c)
|
||||
{
|
||||
|
||||
if (!isdigit(c))
|
||||
return (CC_ERROR);
|
||||
|
||||
if (el->el_state.doingarg) {
|
||||
/* if doing an arg, add this in... */
|
||||
if (el->el_state.lastcmd == EM_UNIVERSAL_ARGUMENT)
|
||||
el->el_state.argument = c - '0';
|
||||
else {
|
||||
if (el->el_state.argument > 1000000)
|
||||
return (CC_ERROR);
|
||||
el->el_state.argument =
|
||||
(el->el_state.argument * 10) + (c - '0');
|
||||
}
|
||||
return (CC_ARGHACK);
|
||||
} else {
|
||||
if (el->el_line.lastchar + 1 >= el->el_line.limit) {
|
||||
if (!ch_enlargebufs(el, 1))
|
||||
return (CC_ERROR);
|
||||
}
|
||||
|
||||
if (el->el_state.inputmode != MODE_INSERT) {
|
||||
el->el_chared.c_undo.buf[el->el_chared.c_undo.isize++] =
|
||||
*el->el_line.cursor;
|
||||
el->el_chared.c_undo.buf[el->el_chared.c_undo.isize] =
|
||||
'\0';
|
||||
c_delafter(el, 1);
|
||||
}
|
||||
c_insert(el, 1);
|
||||
*el->el_line.cursor++ = c;
|
||||
el->el_state.doingarg = 0;
|
||||
re_fastaddc(el);
|
||||
}
|
||||
return (CC_NORM);
|
||||
}
|
||||
|
||||
|
||||
/* ed_argument_digit():
|
||||
* Digit that starts argument
|
||||
* For ESC-n
|
||||
*/
|
||||
protected el_action_t
|
||||
ed_argument_digit(EditLine *el, int c)
|
||||
{
|
||||
|
||||
if (!isdigit(c))
|
||||
return (CC_ERROR);
|
||||
|
||||
if (el->el_state.doingarg) {
|
||||
if (el->el_state.argument > 1000000)
|
||||
return (CC_ERROR);
|
||||
el->el_state.argument = (el->el_state.argument * 10) +
|
||||
(c - '0');
|
||||
} else { /* else starting an argument */
|
||||
el->el_state.argument = c - '0';
|
||||
el->el_state.doingarg = 1;
|
||||
}
|
||||
return (CC_ARGHACK);
|
||||
}
|
||||
|
||||
|
||||
/* ed_unassigned():
|
||||
* Indicates unbound character
|
||||
* Bound to keys that are not assigned
|
||||
*/
|
||||
protected el_action_t
|
||||
/*ARGSUSED*/
|
||||
ed_unassigned(EditLine *el, int c)
|
||||
{
|
||||
|
||||
term_beep(el);
|
||||
term__flush();
|
||||
return (CC_NORM);
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
** TTY key handling.
|
||||
**/
|
||||
|
||||
/* ed_tty_sigint():
|
||||
* Tty interrupt character
|
||||
* [^C]
|
||||
*/
|
||||
protected el_action_t
|
||||
/*ARGSUSED*/
|
||||
ed_tty_sigint(EditLine *el, int c)
|
||||
{
|
||||
|
||||
return (CC_NORM);
|
||||
}
|
||||
|
||||
|
||||
/* ed_tty_dsusp():
|
||||
* Tty delayed suspend character
|
||||
* [^Y]
|
||||
*/
|
||||
protected el_action_t
|
||||
/*ARGSUSED*/
|
||||
ed_tty_dsusp(EditLine *el, int c)
|
||||
{
|
||||
|
||||
return (CC_NORM);
|
||||
}
|
||||
|
||||
|
||||
/* ed_tty_flush_output():
|
||||
* Tty flush output characters
|
||||
* [^O]
|
||||
*/
|
||||
protected el_action_t
|
||||
/*ARGSUSED*/
|
||||
ed_tty_flush_output(EditLine *el, int c)
|
||||
{
|
||||
|
||||
return (CC_NORM);
|
||||
}
|
||||
|
||||
|
||||
/* ed_tty_sigquit():
|
||||
* Tty quit character
|
||||
* [^\]
|
||||
*/
|
||||
protected el_action_t
|
||||
/*ARGSUSED*/
|
||||
ed_tty_sigquit(EditLine *el, int c)
|
||||
{
|
||||
|
||||
return (CC_NORM);
|
||||
}
|
||||
|
||||
|
||||
/* ed_tty_sigtstp():
|
||||
* Tty suspend character
|
||||
* [^Z]
|
||||
*/
|
||||
protected el_action_t
|
||||
/*ARGSUSED*/
|
||||
ed_tty_sigtstp(EditLine *el, int c)
|
||||
{
|
||||
|
||||
return (CC_NORM);
|
||||
}
|
||||
|
||||
|
||||
/* ed_tty_stop_output():
|
||||
* Tty disallow output characters
|
||||
* [^S]
|
||||
*/
|
||||
protected el_action_t
|
||||
/*ARGSUSED*/
|
||||
ed_tty_stop_output(EditLine *el, int c)
|
||||
{
|
||||
|
||||
return (CC_NORM);
|
||||
}
|
||||
|
||||
|
||||
/* ed_tty_start_output():
|
||||
* Tty allow output characters
|
||||
* [^Q]
|
||||
*/
|
||||
protected el_action_t
|
||||
/*ARGSUSED*/
|
||||
ed_tty_start_output(EditLine *el, int c)
|
||||
{
|
||||
|
||||
return (CC_NORM);
|
||||
}
|
||||
|
||||
|
||||
/* ed_newline():
|
||||
* Execute command
|
||||
* [^J]
|
||||
*/
|
||||
protected el_action_t
|
||||
/*ARGSUSED*/
|
||||
ed_newline(EditLine *el, int c)
|
||||
{
|
||||
|
||||
re_goto_bottom(el);
|
||||
*el->el_line.lastchar++ = '\n';
|
||||
*el->el_line.lastchar = '\0';
|
||||
if (el->el_map.type == MAP_VI)
|
||||
el->el_chared.c_vcmd.ins = el->el_line.buffer;
|
||||
return (CC_NEWLINE);
|
||||
}
|
||||
|
||||
|
||||
/* ed_delete_prev_char():
|
||||
* Delete the character to the left of the cursor
|
||||
* [^?]
|
||||
*/
|
||||
protected el_action_t
|
||||
/*ARGSUSED*/
|
||||
ed_delete_prev_char(EditLine *el, int c)
|
||||
{
|
||||
|
||||
if (el->el_line.cursor <= el->el_line.buffer)
|
||||
return (CC_ERROR);
|
||||
|
||||
c_delbefore(el, el->el_state.argument);
|
||||
el->el_line.cursor -= el->el_state.argument;
|
||||
if (el->el_line.cursor < el->el_line.buffer)
|
||||
el->el_line.cursor = el->el_line.buffer;
|
||||
return (CC_REFRESH);
|
||||
}
|
||||
|
||||
|
||||
/* ed_clear_screen():
|
||||
* Clear screen leaving current line at the top
|
||||
* [^L]
|
||||
*/
|
||||
protected el_action_t
|
||||
/*ARGSUSED*/
|
||||
ed_clear_screen(EditLine *el, int c)
|
||||
{
|
||||
|
||||
term_clear_screen(el); /* clear the whole real screen */
|
||||
re_clear_display(el); /* reset everything */
|
||||
return (CC_REFRESH);
|
||||
}
|
||||
|
||||
|
||||
/* ed_redisplay():
|
||||
* Redisplay everything
|
||||
* ^R
|
||||
*/
|
||||
protected el_action_t
|
||||
/*ARGSUSED*/
|
||||
ed_redisplay(EditLine *el, int c)
|
||||
{
|
||||
|
||||
return (CC_REDISPLAY);
|
||||
}
|
||||
|
||||
|
||||
/* ed_start_over():
|
||||
* Erase current line and start from scratch
|
||||
* [^G]
|
||||
*/
|
||||
protected el_action_t
|
||||
/*ARGSUSED*/
|
||||
ed_start_over(EditLine *el, int c)
|
||||
{
|
||||
|
||||
ch_reset(el);
|
||||
return (CC_REFRESH);
|
||||
}
|
||||
|
||||
|
||||
/* ed_sequence_lead_in():
|
||||
* First character in a bound sequence
|
||||
* Placeholder for external keys
|
||||
*/
|
||||
protected el_action_t
|
||||
/*ARGSUSED*/
|
||||
ed_sequence_lead_in(EditLine *el, int c)
|
||||
{
|
||||
|
||||
return (CC_NORM);
|
||||
}
|
||||
|
||||
|
||||
/* ed_prev_history():
|
||||
* Move to the previous history line
|
||||
* [^P] [k]
|
||||
*/
|
||||
protected el_action_t
|
||||
/*ARGSUSED*/
|
||||
ed_prev_history(EditLine *el, int c)
|
||||
{
|
||||
char beep = 0;
|
||||
|
||||
el->el_chared.c_undo.action = NOP;
|
||||
*el->el_line.lastchar = '\0'; /* just in case */
|
||||
|
||||
if (el->el_history.eventno == 0) { /* save the current buffer
|
||||
* away */
|
||||
(void) strncpy(el->el_history.buf, el->el_line.buffer,
|
||||
EL_BUFSIZ - 1);
|
||||
el->el_history.last = el->el_history.buf +
|
||||
(el->el_line.lastchar - el->el_line.buffer);
|
||||
}
|
||||
el->el_history.eventno += el->el_state.argument;
|
||||
|
||||
if (hist_get(el) == CC_ERROR) {
|
||||
beep = 1;
|
||||
/* el->el_history.eventno was fixed by first call */
|
||||
(void) hist_get(el);
|
||||
}
|
||||
re_refresh(el);
|
||||
if (beep)
|
||||
return (CC_ERROR);
|
||||
else
|
||||
return (CC_NORM); /* was CC_UP_HIST */
|
||||
}
|
||||
|
||||
|
||||
/* ed_next_history():
|
||||
* Move to the next history line
|
||||
* [^N] [j]
|
||||
*/
|
||||
protected el_action_t
|
||||
/*ARGSUSED*/
|
||||
ed_next_history(EditLine *el, int c)
|
||||
{
|
||||
|
||||
el->el_chared.c_undo.action = NOP;
|
||||
*el->el_line.lastchar = '\0'; /* just in case */
|
||||
|
||||
el->el_history.eventno -= el->el_state.argument;
|
||||
|
||||
if (el->el_history.eventno < 0) {
|
||||
el->el_history.eventno = 0;
|
||||
return (CC_ERROR);/* make it beep */
|
||||
}
|
||||
return (hist_get(el));
|
||||
}
|
||||
|
||||
|
||||
/* ed_search_prev_history():
|
||||
* Search previous in history for a line matching the current
|
||||
* next search history [M-P] [K]
|
||||
*/
|
||||
protected el_action_t
|
||||
/*ARGSUSED*/
|
||||
ed_search_prev_history(EditLine *el, int c)
|
||||
{
|
||||
const char *hp;
|
||||
int h;
|
||||
bool_t found = 0;
|
||||
|
||||
el->el_chared.c_vcmd.action = NOP;
|
||||
el->el_chared.c_undo.action = NOP;
|
||||
*el->el_line.lastchar = '\0'; /* just in case */
|
||||
if (el->el_history.eventno < 0) {
|
||||
#ifdef DEBUG_EDIT
|
||||
(void) fprintf(el->el_errfile,
|
||||
"e_prev_search_hist(): eventno < 0;\n");
|
||||
#endif
|
||||
el->el_history.eventno = 0;
|
||||
return (CC_ERROR);
|
||||
}
|
||||
if (el->el_history.eventno == 0) {
|
||||
(void) strncpy(el->el_history.buf, el->el_line.buffer,
|
||||
EL_BUFSIZ - 1);
|
||||
el->el_history.last = el->el_history.buf +
|
||||
(el->el_line.lastchar - el->el_line.buffer);
|
||||
}
|
||||
if (el->el_history.ref == NULL)
|
||||
return (CC_ERROR);
|
||||
|
||||
hp = HIST_FIRST(el);
|
||||
if (hp == NULL)
|
||||
return (CC_ERROR);
|
||||
|
||||
c_setpat(el); /* Set search pattern !! */
|
||||
|
||||
for (h = 1; h <= el->el_history.eventno; h++)
|
||||
hp = HIST_NEXT(el);
|
||||
|
||||
while (hp != NULL) {
|
||||
#ifdef SDEBUG
|
||||
(void) fprintf(el->el_errfile, "Comparing with \"%s\"\n", hp);
|
||||
#endif
|
||||
if ((strncmp(hp, el->el_line.buffer, (size_t)
|
||||
(el->el_line.lastchar - el->el_line.buffer)) ||
|
||||
hp[el->el_line.lastchar - el->el_line.buffer]) &&
|
||||
c_hmatch(el, hp)) {
|
||||
found++;
|
||||
break;
|
||||
}
|
||||
h++;
|
||||
hp = HIST_NEXT(el);
|
||||
}
|
||||
|
||||
if (!found) {
|
||||
#ifdef SDEBUG
|
||||
(void) fprintf(el->el_errfile, "not found\n");
|
||||
#endif
|
||||
return (CC_ERROR);
|
||||
}
|
||||
el->el_history.eventno = h;
|
||||
|
||||
return (hist_get(el));
|
||||
}
|
||||
|
||||
|
||||
/* ed_search_next_history():
|
||||
* Search next in history for a line matching the current
|
||||
* [M-N] [J]
|
||||
*/
|
||||
protected el_action_t
|
||||
/*ARGSUSED*/
|
||||
ed_search_next_history(EditLine *el, int c)
|
||||
{
|
||||
const char *hp;
|
||||
int h;
|
||||
bool_t found = 0;
|
||||
|
||||
el->el_chared.c_vcmd.action = NOP;
|
||||
el->el_chared.c_undo.action = NOP;
|
||||
*el->el_line.lastchar = '\0'; /* just in case */
|
||||
|
||||
if (el->el_history.eventno == 0)
|
||||
return (CC_ERROR);
|
||||
|
||||
if (el->el_history.ref == NULL)
|
||||
return (CC_ERROR);
|
||||
|
||||
hp = HIST_FIRST(el);
|
||||
if (hp == NULL)
|
||||
return (CC_ERROR);
|
||||
|
||||
c_setpat(el); /* Set search pattern !! */
|
||||
|
||||
for (h = 1; h < el->el_history.eventno && hp; h++) {
|
||||
#ifdef SDEBUG
|
||||
(void) fprintf(el->el_errfile, "Comparing with \"%s\"\n", hp);
|
||||
#endif
|
||||
if ((strncmp(hp, el->el_line.buffer, (size_t)
|
||||
(el->el_line.lastchar - el->el_line.buffer)) ||
|
||||
hp[el->el_line.lastchar - el->el_line.buffer]) &&
|
||||
c_hmatch(el, hp))
|
||||
found = h;
|
||||
hp = HIST_NEXT(el);
|
||||
}
|
||||
|
||||
if (!found) { /* is it the current history number? */
|
||||
if (!c_hmatch(el, el->el_history.buf)) {
|
||||
#ifdef SDEBUG
|
||||
(void) fprintf(el->el_errfile, "not found\n");
|
||||
#endif
|
||||
return (CC_ERROR);
|
||||
}
|
||||
}
|
||||
el->el_history.eventno = found;
|
||||
|
||||
return (hist_get(el));
|
||||
}
|
||||
|
||||
|
||||
/* ed_prev_line():
|
||||
* Move up one line
|
||||
* Could be [k] [^p]
|
||||
*/
|
||||
protected el_action_t
|
||||
/*ARGSUSED*/
|
||||
ed_prev_line(EditLine *el, int c)
|
||||
{
|
||||
char *ptr;
|
||||
int nchars = c_hpos(el);
|
||||
|
||||
/*
|
||||
* Move to the line requested
|
||||
*/
|
||||
if (*(ptr = el->el_line.cursor) == '\n')
|
||||
ptr--;
|
||||
|
||||
for (; ptr >= el->el_line.buffer; ptr--)
|
||||
if (*ptr == '\n' && --el->el_state.argument <= 0)
|
||||
break;
|
||||
|
||||
if (el->el_state.argument > 0)
|
||||
return (CC_ERROR);
|
||||
|
||||
/*
|
||||
* Move to the beginning of the line
|
||||
*/
|
||||
for (ptr--; ptr >= el->el_line.buffer && *ptr != '\n'; ptr--)
|
||||
continue;
|
||||
|
||||
/*
|
||||
* Move to the character requested
|
||||
*/
|
||||
for (ptr++;
|
||||
nchars-- > 0 && ptr < el->el_line.lastchar && *ptr != '\n';
|
||||
ptr++)
|
||||
continue;
|
||||
|
||||
el->el_line.cursor = ptr;
|
||||
return (CC_CURSOR);
|
||||
}
|
||||
|
||||
|
||||
/* ed_next_line():
|
||||
* Move down one line
|
||||
* Could be [j] [^n]
|
||||
*/
|
||||
protected el_action_t
|
||||
/*ARGSUSED*/
|
||||
ed_next_line(EditLine *el, int c)
|
||||
{
|
||||
char *ptr;
|
||||
int nchars = c_hpos(el);
|
||||
|
||||
/*
|
||||
* Move to the line requested
|
||||
*/
|
||||
for (ptr = el->el_line.cursor; ptr < el->el_line.lastchar; ptr++)
|
||||
if (*ptr == '\n' && --el->el_state.argument <= 0)
|
||||
break;
|
||||
|
||||
if (el->el_state.argument > 0)
|
||||
return (CC_ERROR);
|
||||
|
||||
/*
|
||||
* Move to the character requested
|
||||
*/
|
||||
for (ptr++;
|
||||
nchars-- > 0 && ptr < el->el_line.lastchar && *ptr != '\n';
|
||||
ptr++)
|
||||
continue;
|
||||
|
||||
el->el_line.cursor = ptr;
|
||||
return (CC_CURSOR);
|
||||
}
|
||||
|
||||
|
||||
/* ed_command():
|
||||
* Editline extended command
|
||||
* [M-X] [:]
|
||||
*/
|
||||
protected el_action_t
|
||||
/*ARGSUSED*/
|
||||
ed_command(EditLine *el, int c)
|
||||
{
|
||||
char tmpbuf[EL_BUFSIZ];
|
||||
int tmplen;
|
||||
|
||||
el->el_line.buffer[0] = '\0';
|
||||
el->el_line.lastchar = el->el_line.buffer;
|
||||
el->el_line.cursor = el->el_line.buffer;
|
||||
|
||||
c_insert(el, 3); /* prompt + ": " */
|
||||
*el->el_line.cursor++ = '\n';
|
||||
*el->el_line.cursor++ = ':';
|
||||
*el->el_line.cursor++ = ' ';
|
||||
re_refresh(el);
|
||||
|
||||
tmplen = c_gets(el, tmpbuf);
|
||||
tmpbuf[tmplen] = '\0';
|
||||
|
||||
el->el_line.buffer[0] = '\0';
|
||||
el->el_line.lastchar = el->el_line.buffer;
|
||||
el->el_line.cursor = el->el_line.buffer;
|
||||
|
||||
if (parse_line(el, tmpbuf) == -1)
|
||||
return (CC_ERROR);
|
||||
else
|
||||
return (CC_REFRESH);
|
||||
}
|
1449
main/editline/config.guess
vendored
1449
main/editline/config.guess
vendored
File diff suppressed because it is too large
Load Diff
@@ -1,21 +0,0 @@
|
||||
#undef SUNOS
|
||||
#undef CYGWIN
|
||||
|
||||
#undef HAVE_SYS_CDEFS_H
|
||||
#undef HAVE_TERMCAP_H
|
||||
#undef HAVE_CURSES_H
|
||||
#undef HAVE_NCURSES_H
|
||||
#undef HAVE_TERM_H
|
||||
#undef HAVE_VIS_H
|
||||
#undef HAVE_ISSETUGID
|
||||
|
||||
#undef HAVE_STRLCAT
|
||||
#undef HAVE_STRLCPY
|
||||
#undef HAVE_FGETLN
|
||||
#undef HAVE_STRVIS
|
||||
#undef HAVE_STRUNVIS
|
||||
|
||||
#include "sys.h"
|
||||
#ifdef CYGWIN
|
||||
# include "cygdef.h"
|
||||
#endif
|
1412
main/editline/config.sub
vendored
1412
main/editline/config.sub
vendored
File diff suppressed because it is too large
Load Diff
2464
main/editline/configure
vendored
2464
main/editline/configure
vendored
File diff suppressed because it is too large
Load Diff
@@ -1,278 +0,0 @@
|
||||
dnl
|
||||
dnl Process this file with autoconf to produce a configure script.
|
||||
dnl
|
||||
AC_INIT(Makefile.in)
|
||||
|
||||
dnl If CFLAGS isn't defined and using gcc, set CFLAGS to something reasonable.
|
||||
dnl Otherwise, just prevent autoconf from molesting CFLAGS.
|
||||
CFLAGS=$CFLAGS
|
||||
AC_PROG_CC
|
||||
if test "x$CFLAGS" = "x" ; then
|
||||
no_CFLAGS="yes"
|
||||
fi
|
||||
if test "x$no_CFLAGS" = "xyes" -a "x$GCC" = "xyes" ; then
|
||||
CFLAGS="-Wall -pipe -g3"
|
||||
fi
|
||||
A_CFLAGS=""
|
||||
AC_SUBST(A_CFLAGS)
|
||||
S_CFLAGS="-fPIC -DPIC"
|
||||
AC_SUBST(S_CFLAGS)
|
||||
AC_PROG_CPP
|
||||
AC_PROG_AWK
|
||||
|
||||
dnl Platform-specific settings. The ABI can probably be determined
|
||||
dnl programmatically, but doing so is error-prone, which makes it generally
|
||||
dnl not worth the trouble.
|
||||
AC_CANONICAL_HOST
|
||||
case "${host}" in
|
||||
*-*-darwin*)
|
||||
CFLAGS="$CFLAGS -fno-common -no-cpp-precomp"
|
||||
ABI="macho"
|
||||
;;
|
||||
*-*-freebsd*)
|
||||
ABI="elf"
|
||||
;;
|
||||
*-*-linux* | *cygwin*)
|
||||
if echo ${host} | grep -q cygwin ; then \
|
||||
echo "cygwin detected"; \
|
||||
S_CFLAGS=""; \
|
||||
echo "/* cygdef.h. Generated automatically by configure. */
|
||||
#ifndef _CYGDEF_H_
|
||||
#define _CYGDEF_H_ 1
|
||||
#include <sys/ioctl.h>
|
||||
#define __linux__ 1
|
||||
|
||||
|
||||
typedef void (*sig_t)(int);
|
||||
|
||||
|
||||
#endif /* _CYGDEF_H_ */" > cygdef.h; \
|
||||
echo "
|
||||
#define CYGWIN 1
|
||||
" > confdefs.h; \
|
||||
fi
|
||||
ABI="elf"
|
||||
;;
|
||||
*-*-netbsd*)
|
||||
AC_MSG_CHECKING(ABI)
|
||||
AC_EGREP_CPP(yes,
|
||||
[#ifdef __ELF__
|
||||
yes
|
||||
#endif
|
||||
],
|
||||
ABI="elf",
|
||||
ABI="aout")
|
||||
AC_MSG_RESULT($ABI)
|
||||
;;
|
||||
*-*-solaris2*)
|
||||
ABI="elf"
|
||||
AC_DEFINE(SUNOS)
|
||||
;;
|
||||
*)
|
||||
AC_MSG_RESULT(Unsupported operating system: ${host})
|
||||
ABI="elf"
|
||||
;;
|
||||
esac
|
||||
|
||||
AC_PROG_INSTALL
|
||||
AC_PROG_RANLIB
|
||||
AC_PATH_PROGS(AR, ar gar, , $PATH)
|
||||
|
||||
dnl Search for termcap access routines in termcap, tinfo, curses, and ncurses.
|
||||
AC_CHECK_LIB(termcap, tgetent, , \
|
||||
AC_CHECK_LIB(tinfo, tgetent, , \
|
||||
AC_CHECK_LIB(curses, tgetent, , \
|
||||
AC_CHECK_LIB(ncurses, tgetent, , \
|
||||
AC_MSG_ERROR(termcap support not found)))))
|
||||
|
||||
dnl Use termcap.h if it exists; otherwise we need both term.h and [n]curses.h.
|
||||
AC_CHECK_HEADERS(termcap.h, , \
|
||||
AC_CHECK_HEADERS(term.h, , \
|
||||
AC_MSG_RESULT(Need term.h since termcap.h is missing))
|
||||
AC_CHECK_HEADERS(curses.h, , \
|
||||
AC_CHECK_HEADERS(ncurses.h, , \
|
||||
AC_MSG_RESULT(Need curses.h or ncurses.h))))
|
||||
|
||||
AC_CHECK_HEADERS(sys/cdefs.h vis.h)
|
||||
|
||||
AC_CHECK_FUNCS(issetugid)
|
||||
AC_CHECK_FUNCS(fgetln, , CCSRCS="$CCSRCS np/fgetln.c")
|
||||
AC_CHECK_FUNCS(strvis, , CCSRCS="$CCSRCS np/vis.c")
|
||||
AC_CHECK_FUNCS(strunvis, , CCSRCS="$CCSRCS np/unvis.c")
|
||||
AC_CHECK_FUNCS(strlcpy, , CCSRCS="$CCSRCS np/strlcpy.c")
|
||||
AC_CHECK_FUNCS(strlcat, , CCSRCS="$CCSRCS np/strlcat.c")
|
||||
|
||||
AC_EGREP_CPP(yes,
|
||||
[#include <sys/cdefs.h>
|
||||
#ifdef __RCSID
|
||||
yes
|
||||
#endif
|
||||
], , [CPPFLAGS="$CPPFLAGS '-D__RCSID(x)='"])
|
||||
|
||||
AC_EGREP_CPP(yes,
|
||||
[#include <sys/cdefs.h>
|
||||
#ifdef __COPYRIGHT
|
||||
yes
|
||||
#endif
|
||||
], , [CPPFLAGS="$CPPFLAGS '-D__COPYRIGHT(x)='"])
|
||||
|
||||
AC_EGREP_CPP(yes,
|
||||
[#include <sys/cdefs.h>
|
||||
#ifdef __RENAME
|
||||
yes
|
||||
#endif
|
||||
], , [CPPFLAGS="$CPPFLAGS '-D__RENAME(x)='"])
|
||||
|
||||
AC_EGREP_CPP(yes,
|
||||
[#include <sys/cdefs.h>
|
||||
#ifdef _DIAGASSERT
|
||||
yes
|
||||
#endif
|
||||
], , [CPPFLAGS="$CPPFLAGS '-D_DIAGASSERT(x)='"])
|
||||
|
||||
dnl Enable readline compatibility by default.
|
||||
AC_ARG_ENABLE(readline, [ --disable-readline Disable readline compatibility],
|
||||
if test "x$enable_readline" != "xyes" ; then
|
||||
enable_readline="no"
|
||||
fi
|
||||
,
|
||||
enable_readline="yes"
|
||||
)
|
||||
|
||||
dnl Optionally enable debugging.
|
||||
AC_ARG_ENABLE(debug, [ --enable-debug Enable debugging code],
|
||||
if test "x$enable_debug" != "xyes" ; then
|
||||
enable_debug="no"
|
||||
fi
|
||||
,
|
||||
enable_debug="no"
|
||||
)
|
||||
if test "x$enable_debug" = "xyes" ; then
|
||||
CPPFLAGS="$CPPFLAGS -DDEBUG_TTY -DDEBUG_KEY -DDEBUG_READ -DDEBUG"
|
||||
CPPFLAGS="$CPPFLAGS -DDEBUG_REFRESH -DDEBUG_PASTE"
|
||||
else
|
||||
CFLAGS="$CFLAGS -O"
|
||||
fi
|
||||
|
||||
|
||||
dnl
|
||||
dnl File lists. This is done here instead of in the Makefile in order to avoid
|
||||
dnl the need for conditionals.
|
||||
dnl
|
||||
|
||||
dnl .c files.
|
||||
ACSRCS="common.c emacs.c vi.c"
|
||||
BCSRCS="chared.c el.c hist.c key.c map.c parse.c prompt.c read.c refresh.c search.c sig.c term.c tty.c"
|
||||
CCSRCS="$CCSRCS history.c tokenizer.c"
|
||||
|
||||
dnl Generated .c files.
|
||||
AGCSRCS="fcns.c help.c"
|
||||
BGCSRCS="editline.c"
|
||||
|
||||
dnl .h files.
|
||||
HDRS="chared.h el.h hist.h key.h map.h parse.h prompt.h refresh.h search.h sig.h sys.h term.h tokenizer.h tty.h"
|
||||
|
||||
dnl Installed .h files.
|
||||
IHDRS="histedit.h"
|
||||
|
||||
dnl Installed headers for readline compatibility.
|
||||
IHDR_LINKS=
|
||||
|
||||
dnl Generated .h files.
|
||||
AGHDRS="common.h emacs.h vi.h"
|
||||
BGHDRS="fcns.h help.h"
|
||||
|
||||
dnl Header installation directories.
|
||||
HDR_DIRS="include"
|
||||
|
||||
dnl Man pages.
|
||||
MAN3="editline.3"
|
||||
MAN5="editrc.5"
|
||||
|
||||
MAN3_LINKS=
|
||||
for i in el_init.3 el_end.3 el_reset.3 el_gets.3 el_getc.3 el_push.3 \
|
||||
el_parse.3 el_set.3 el_get.3 el_source.3 el_resize.3 el_line.3 \
|
||||
el_insertstr.3 el_deletestr.3 history_init.3 history_end.3 \
|
||||
history.3 ; do
|
||||
MAN3_LINKS="$MAN3_LINKS editline.3 $i"
|
||||
done
|
||||
|
||||
dnl Man page installation directories.
|
||||
MAN_DIRS="man/man3 man/man5"
|
||||
|
||||
dnl Library settings.
|
||||
LIB_DIRS="lib"
|
||||
LIB_MAJOR="2"
|
||||
LIB_MINOR="6"
|
||||
LIB_A="libedit.a"
|
||||
LIB_A_LINKS=
|
||||
|
||||
if test "x$ABI" = "xelf" ; then
|
||||
LIB_S="libedit.so.$LIB_MAJOR"
|
||||
LIB_S_LINK="libedit.so"
|
||||
LIB_S_LINKS="$LIB_S $LIB_S_LINK"
|
||||
S_LDFLAGS="-shared"
|
||||
elif test "x$ABI" = "xaout" ; then
|
||||
LIB_S="libedit.so.$LIB_MAJOR.$LIB_MINOR"
|
||||
LIB_S_LINKS=
|
||||
S_LDFLAGS="-shared"
|
||||
elif test "x$ABI" = "xmacho" ; then
|
||||
S_LDFLAGS="-shared"
|
||||
LIB_S="libedit.$LIB_MAJOR.dylib"
|
||||
LIB_S_LINK="libedit.dylib"
|
||||
LIB_S_LINKS="$LIB_S $LIB_S_LINK"
|
||||
if test "x$prefix" = "xNONE" ; then
|
||||
S_LDFLAGS="-undefined suppress -flat_namespace -dynamiclib -compatibility_version $LIB_MAJOR -current_version $LIB_MAJOR -install_name /usr/local/lib/$LIB_S"
|
||||
else
|
||||
S_LDFLAGS="-undefined suppress -flat_namespace -dynamiclib -compatibility_version $LIB_MAJOR -current_version $LIB_MAJOR -install_name $prefix/lib/$LIB_S"
|
||||
fi
|
||||
fi
|
||||
|
||||
dnl Test program.
|
||||
TEST="TEST/test"
|
||||
TCSRCS="TEST/test.c"
|
||||
|
||||
dnl Add files to the lists if readline compatibility is enabled.
|
||||
if test "x$enable_readline" = "xyes" ; then
|
||||
CCSRCS="$CCSRCS readline.c"
|
||||
IHDRS="$IHDRS readline/readline.h"
|
||||
IHDR_LINKS="readline.h readline/history.h"
|
||||
HDR_DIRS="$HDR_DIRS include/readline"
|
||||
LIB_A_LINKS="$LIB_A_LINKS libedit.a libreadline.a"
|
||||
if test "x$ABI" = "xelf" ; then
|
||||
LIB_S_LINKS="$LIB_S_LINKS $LIB_S_LINK libreadline.so"
|
||||
elif test "x$ABI" = "xaout" ; then
|
||||
LIB_S_LINKS="$LIB_S_LINKS $LIB_S libreadline.so.$LIB_MAJOR.$LIB_MINOR"
|
||||
elif test "x$ABI" = "xmacho" ; then
|
||||
LIB_S_LINKS="$LIB_S_LINKS $LIB_S_LINK libreadline.dylib"
|
||||
fi
|
||||
fi
|
||||
|
||||
AC_SUBST(ACSRCS)
|
||||
AC_SUBST(BCSRCS)
|
||||
AC_SUBST(CCSRCS)
|
||||
AC_SUBST(AGCSRCS)
|
||||
AC_SUBST(BGCSRCS)
|
||||
AC_SUBST(HDRS)
|
||||
AC_SUBST(IHDRS)
|
||||
AC_SUBST(IHDR_LINKS)
|
||||
AC_SUBST(AGHDRS)
|
||||
AC_SUBST(BGHDRS)
|
||||
AC_SUBST(HDR_DIRS)
|
||||
AC_SUBST(MAN3)
|
||||
AC_SUBST(MAN5)
|
||||
AC_SUBST(MAN3_LINKS)
|
||||
AC_SUBST(MAN_DIRS)
|
||||
AC_SUBST(LIB_DIRS)
|
||||
AC_SUBST(LIB_VER)
|
||||
AC_SUBST(LIB_A)
|
||||
AC_SUBST(LIB_A_LINKS)
|
||||
AC_SUBST(LIB_S)
|
||||
AC_SUBST(LIB_S_LINKS)
|
||||
AC_SUBST(S_LDFLAGS)
|
||||
AC_SUBST(TEST)
|
||||
AC_SUBST(TCSRCS)
|
||||
|
||||
AC_CONFIG_HEADER(config.h)
|
||||
AC_OUTPUT([Makefile makelist])
|
||||
|
@@ -1,646 +0,0 @@
|
||||
.\" $NetBSD: editline.3,v 1.25 2002/01/15 02:46:22 wiz Exp $
|
||||
.\"
|
||||
.\" Copyright (c) 1997-1999 The NetBSD Foundation, Inc.
|
||||
.\" All rights reserved.
|
||||
.\"
|
||||
.\" This file was contributed to The NetBSD Foundation by Luke Mewburn.
|
||||
.\"
|
||||
.\" Redistribution and use in source and binary forms, with or without
|
||||
.\" modification, are permitted provided that the following conditions
|
||||
.\" are met:
|
||||
.\" 1. Redistributions of source code must retain the above copyright
|
||||
.\" notice, this list of conditions and the following disclaimer.
|
||||
.\" 2. Redistributions in binary form must reproduce the above copyright
|
||||
.\" notice, this list of conditions and the following disclaimer in the
|
||||
.\" documentation and/or other materials provided with the distribution.
|
||||
.\" 3. All advertising materials mentioning features or use of this software
|
||||
.\" must display the following acknowledgement:
|
||||
.\" This product includes software developed by the NetBSD
|
||||
.\" Foundation, Inc. and its contributors.
|
||||
.\" 4. Neither the name of The NetBSD Foundation nor the names of its
|
||||
.\" contributors may be used to endorse or promote products derived
|
||||
.\" from this software without specific prior written permission.
|
||||
.\"
|
||||
.\" THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS
|
||||
.\" ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
|
||||
.\" TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
|
||||
.\" PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS
|
||||
.\" BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
|
||||
.\" CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
|
||||
.\" SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
|
||||
.\" INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
|
||||
.\" CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
|
||||
.\" ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
|
||||
.\" POSSIBILITY OF SUCH DAMAGE.
|
||||
.\"
|
||||
.Dd November 12, 1999
|
||||
.Os
|
||||
.Dt EDITLINE 3
|
||||
.Sh NAME
|
||||
.Nm editline ,
|
||||
.Nm el_init ,
|
||||
.Nm el_end ,
|
||||
.Nm el_reset ,
|
||||
.Nm el_gets ,
|
||||
.Nm el_getc ,
|
||||
.Nm el_push ,
|
||||
.Nm el_parse ,
|
||||
.Nm el_set ,
|
||||
.Nm el_source ,
|
||||
.Nm el_resize ,
|
||||
.Nm el_line ,
|
||||
.Nm el_insertstr ,
|
||||
.Nm el_deletestr ,
|
||||
.Nm history_init ,
|
||||
.Nm history_end ,
|
||||
.Nm history
|
||||
.Nd line editor and history functions
|
||||
.Sh LIBRARY
|
||||
.Lb libedit
|
||||
.Sh SYNOPSIS
|
||||
.Fd #include <histedit.h>
|
||||
.Ft EditLine *
|
||||
.Fn el_init "const char *prog" "FILE *fin" "FILE *fout" "FILE *ferr"
|
||||
.Ft void
|
||||
.Fn el_end "EditLine *e"
|
||||
.Ft void
|
||||
.Fn el_reset "EditLine *e"
|
||||
.Ft const char *
|
||||
.Fn el_gets "EditLine *e" "int *count"
|
||||
.Ft int
|
||||
.Fn el_getc "EditLine *e" "char *ch"
|
||||
.Ft void
|
||||
.Fn el_push "EditLine *e" "const char *str"
|
||||
.Ft int
|
||||
.Fn el_parse "EditLine *e" "int argc" "char *argv[]"
|
||||
.Ft int
|
||||
.Fn el_set "EditLine *e" "int op" "..."
|
||||
.Ft int
|
||||
.Fn el_get "EditLine *e" "int op" "void *result"
|
||||
.Ft int
|
||||
.Fn el_source "EditLine *e" "const char *file"
|
||||
.Ft void
|
||||
.Fn el_resize "EditLine *e"
|
||||
.Ft const LineInfo *
|
||||
.Fn el_line "EditLine *e"
|
||||
.Ft int
|
||||
.Fn el_insertstr "EditLine *e" "const char *str"
|
||||
.Ft void
|
||||
.Fn el_deletestr "EditLine *e" "int count"
|
||||
.Ft History *
|
||||
.Fn history_init
|
||||
.Ft void
|
||||
.Fn history_end "History *h"
|
||||
.Ft int
|
||||
.Fn history "History *h" "HistEvent *ev" "int op" "..."
|
||||
.Sh DESCRIPTION
|
||||
The
|
||||
.Nm
|
||||
library provides generic line editing and history functions,
|
||||
similar to those found in
|
||||
.Xr sh 1 .
|
||||
.Pp
|
||||
These functions are available in the
|
||||
.Nm libedit
|
||||
library (which needs the
|
||||
.Nm libtermcap
|
||||
library).
|
||||
Programs should be linked with
|
||||
.Fl ledit ltermcap .
|
||||
.Sh LINE EDITING FUNCTIONS
|
||||
The line editing functions use a common data structure,
|
||||
.Fa EditLine ,
|
||||
which is created by
|
||||
.Fn el_init
|
||||
and freed by
|
||||
.Fn el_end .
|
||||
.Pp
|
||||
The following functions are available:
|
||||
.Bl -tag -width 4n
|
||||
.It Fn el_init
|
||||
Initialise the line editor, and return a data structure
|
||||
to be used by all other line editing functions.
|
||||
.Fa prog
|
||||
is the name of the invoking program, used when reading the
|
||||
.Xr editrc 5
|
||||
file to determine which settings to use.
|
||||
.Fa fin ,
|
||||
.Fa fout
|
||||
and
|
||||
.Fa ferr
|
||||
are the input, output, and error streams (respectively) to use.
|
||||
In this documentation, references to
|
||||
.Dq the tty
|
||||
are actually to this input/output stream combination.
|
||||
.It Fn el_end
|
||||
Clean up and finish with
|
||||
.Fa e ,
|
||||
assumed to have been created with
|
||||
.Fn el_init .
|
||||
.It Fn el_reset
|
||||
Reset the tty and the parser.
|
||||
This should be called after an error which may have upset the tty's
|
||||
state.
|
||||
.It Fn el_gets
|
||||
Read a line from the tty.
|
||||
.Fa count
|
||||
is modified to contain the number of characters read.
|
||||
Returns the line read if successful, or
|
||||
.Dv NULL
|
||||
if no characters were read or if an error occurred.
|
||||
.It Fn el_getc
|
||||
Read a character from the tty.
|
||||
.Fa ch
|
||||
is modified to contain the character read.
|
||||
Returns the number of characters read if successful, -1 otherwise.
|
||||
.It Fn el_push
|
||||
Pushes
|
||||
.Fa str
|
||||
back onto the input stream.
|
||||
This is used by the macro expansion mechanism.
|
||||
Refer to the description of
|
||||
.Ic bind
|
||||
.Fl s
|
||||
in
|
||||
.Xr editrc 5
|
||||
for more information.
|
||||
.It Fn el_parse
|
||||
Parses the
|
||||
.Fa argv
|
||||
array (which is
|
||||
.Fa argc
|
||||
elements in size)
|
||||
to execute builtin
|
||||
.Nm
|
||||
commands.
|
||||
If the command is prefixed with
|
||||
.Dq prog :
|
||||
then
|
||||
.Fn el_parse
|
||||
will only execute the command if
|
||||
.Dq prog
|
||||
matches the
|
||||
.Fa prog
|
||||
argument supplied to
|
||||
.Fn el_init .
|
||||
The return value is
|
||||
-1 if the command is unknown,
|
||||
0 if there was no error or
|
||||
.Dq prog
|
||||
didn't match, or
|
||||
1 if the command returned an error.
|
||||
Refer to
|
||||
.Xr editrc 5
|
||||
for more information.
|
||||
.It Fn el_set
|
||||
Set
|
||||
.Nm
|
||||
parameters.
|
||||
.Fa op
|
||||
determines which parameter to set, and each operation has its
|
||||
own parameter list.
|
||||
.Pp
|
||||
The following values for
|
||||
.Fa op
|
||||
are supported, along with the required argument list:
|
||||
.Bl -tag -width 4n
|
||||
.It Dv EL_PROMPT , Fa "char *(*f)(EditLine *)"
|
||||
Define prompt printing function as
|
||||
.Fa f ,
|
||||
which is to return a string that contains the prompt.
|
||||
.It Dv EL_RPROMPT , Fa "char *(*f)(EditLine *)"
|
||||
Define right side prompt printing function as
|
||||
.Fa f ,
|
||||
which is to return a string that contains the prompt.
|
||||
.It Dv EL_TERMINAL , Fa "const char *type"
|
||||
Define terminal type of the tty to be
|
||||
.Fa type ,
|
||||
or to
|
||||
.Ev TERM
|
||||
if
|
||||
.Fa type
|
||||
is
|
||||
.Dv NULL .
|
||||
.It Dv EL_EDITOR , Fa "const char *mode"
|
||||
Set editing mode to
|
||||
.Fa mode ,
|
||||
which must be one of
|
||||
.Dq emacs
|
||||
or
|
||||
.Dq vi .
|
||||
.It Dv EL_SIGNAL , Fa "int flag"
|
||||
If
|
||||
.Fa flag
|
||||
is non-zero,
|
||||
.Nm
|
||||
will install its own signal handler for the following signals when
|
||||
reading command input:
|
||||
.Dv SIGCONT ,
|
||||
.Dv SIGHUP ,
|
||||
.Dv SIGINT ,
|
||||
.Dv SIGQUIT ,
|
||||
.Dv SIGSTOP ,
|
||||
.Dv SIGTERM ,
|
||||
.Dv SIGTSTP ,
|
||||
and
|
||||
.Dv SIGWINCH .
|
||||
Otherwise, the current signal handlers will be used.
|
||||
.It Dv EL_BIND , Xo
|
||||
.Fa "const char *" ,
|
||||
.Fa "..." ,
|
||||
.Dv NULL
|
||||
.Xc
|
||||
Perform the
|
||||
.Ic bind
|
||||
builtin command.
|
||||
Refer to
|
||||
.Xr editrc 5
|
||||
for more information.
|
||||
.It Dv EL_ECHOTC , Xo
|
||||
.Fa "const char *" ,
|
||||
.Fa "..." ,
|
||||
.Dv NULL
|
||||
.Xc
|
||||
Perform the
|
||||
.Ic echotc
|
||||
builtin command.
|
||||
Refer to
|
||||
.Xr editrc 5
|
||||
for more information.
|
||||
.It Dv EL_SETTC , Xo
|
||||
.Fa "const char *" ,
|
||||
.Fa "..." ,
|
||||
.Dv NULL
|
||||
.Xc
|
||||
Perform the
|
||||
.Ic settc
|
||||
builtin command.
|
||||
Refer to
|
||||
.Xr editrc 5
|
||||
for more information.
|
||||
.It Dv EL_SETTY , Xo
|
||||
.Fa "const char *" ,
|
||||
.Fa "..." ,
|
||||
.Dv NULL
|
||||
.Xc
|
||||
Perform the
|
||||
.Ic setty
|
||||
builtin command.
|
||||
Refer to
|
||||
.Xr editrc 5
|
||||
for more information.
|
||||
.It Dv EL_TELLTC , Xo
|
||||
.Fa "const char *" ,
|
||||
.Fa "..." ,
|
||||
.Dv NULL
|
||||
.Xc
|
||||
Perform the
|
||||
.Ic telltc
|
||||
builtin command.
|
||||
Refer to
|
||||
.Xr editrc 5
|
||||
for more information.
|
||||
.It Dv EL_ADDFN , Xo
|
||||
.Fa "const char *name" ,
|
||||
.Fa "const char *help" ,
|
||||
.Fa "unsigned char (*func)(EditLine *e, int ch)
|
||||
.Xc
|
||||
Add a user defined function,
|
||||
.Fn func ,
|
||||
referred to as
|
||||
.Fa name
|
||||
which is invoked when a key which is bound to
|
||||
.Fa name
|
||||
is entered.
|
||||
.Fa help
|
||||
is a description of
|
||||
.Fa name .
|
||||
At invocation time,
|
||||
.Fa ch
|
||||
is the key which caused the invocation.
|
||||
The return value of
|
||||
.Fn func
|
||||
should be one of:
|
||||
.Bl -tag -width "CC_REDISPLAY"
|
||||
.It Dv CC_NORM
|
||||
Add a normal character.
|
||||
.It Dv CC_NEWLINE
|
||||
End of line was entered.
|
||||
.It Dv CC_EOF
|
||||
EOF was entered.
|
||||
.It Dv CC_ARGHACK
|
||||
Expecting further command input as arguments, do nothing visually.
|
||||
.It Dv CC_REFRESH
|
||||
Refresh display.
|
||||
.It Dv CC_REFRESH_BEEP
|
||||
Refresh display, and beep.
|
||||
.It Dv CC_CURSOR
|
||||
Cursor moved, so update and perform
|
||||
.Dv CC_REFRESH .
|
||||
.It Dv CC_REDISPLAY
|
||||
Redisplay entire input line.
|
||||
This is useful if a key binding outputs extra information.
|
||||
.It Dv CC_ERROR
|
||||
An error occurred.
|
||||
Beep, and flush tty.
|
||||
.It Dv CC_FATAL
|
||||
Fatal error, reset tty to known state.
|
||||
.El
|
||||
.It Dv EL_HIST , Xo
|
||||
.Fa "History *(*func)(History *, int op, ...)" ,
|
||||
.Fa "const char *ptr"
|
||||
.Xc
|
||||
Defines which history function to use, which is usually
|
||||
.Fn history .
|
||||
.Fa ptr
|
||||
should be the value returned by
|
||||
.Fn history_init .
|
||||
.It Dv EL_EDITMODE , Fa "int flag"
|
||||
If
|
||||
.Fa flag
|
||||
is non-zero,
|
||||
editing is enabled (the default).
|
||||
Note that this is only an indication, and does not
|
||||
affect the operation of
|
||||
.Nm "" .
|
||||
At this time, it is the caller's responsibility to
|
||||
check this
|
||||
(using
|
||||
.Fn el_get )
|
||||
to determine if editing should be enabled or not.
|
||||
.It Dv EL_GETCFN , Fa "int (*f)(EditLine *, char *c)"
|
||||
Define the character reading function as
|
||||
.Fa f ,
|
||||
which is to return the number of characters read and store them in
|
||||
.Fa c .
|
||||
This function is called internally by
|
||||
.Fn el_gets
|
||||
and
|
||||
.Fn el_getc .
|
||||
The builtin function can be set or restored with the special function
|
||||
name ``EL_BUILTIN_GETCFN''.
|
||||
.It Dv EL_CLIENTDATA , Fa "void *data"
|
||||
Register
|
||||
.Fa data
|
||||
to be associated with this EditLine structure. It can be retrieved with
|
||||
the corresponding
|
||||
.Fn el_get
|
||||
call.
|
||||
.El
|
||||
.It Fn el_get
|
||||
Get
|
||||
.Nm
|
||||
parameters.
|
||||
.Fa op
|
||||
determines which parameter to retrieve into
|
||||
.Fa result .
|
||||
.Pp
|
||||
The following values for
|
||||
.Fa op
|
||||
are supported, along with actual type of
|
||||
.Fa result :
|
||||
.Bl -tag -width 4n
|
||||
.It Dv EL_PROMPT , Fa "char *(*f)(EditLine *)"
|
||||
Return a pointer to the function that displays the prompt.
|
||||
.It Dv EL_RPROMPT , Fa "char *(*f)(EditLine *)"
|
||||
Return a pointer to the function that displays the rightside prompt.
|
||||
.It Dv EL_EDITOR , Fa "const char *"
|
||||
Return the name of the editor, which will be one of
|
||||
.Dq emacs
|
||||
or
|
||||
.Dq vi .
|
||||
.It Dv EL_SIGNAL , Fa "int *"
|
||||
Return non-zero if
|
||||
.Nm
|
||||
has installed private signal handlers (see
|
||||
.Fn el_get
|
||||
above).
|
||||
.It Dv EL_EDITMODE, Fa "int *"
|
||||
Return non-zero if editing is enabled.
|
||||
.It Dv EL_GETCFN, Fa "int (**f)(EditLine *, char *)"
|
||||
Return a pointer to the function that read characters, which is equal to
|
||||
``EL_BUILTIN_GETCFN'' in the case of the default builtin function.
|
||||
.It Dv EL_CLIENTDATA , Fa "void **data"
|
||||
Retrieve
|
||||
.Fa data
|
||||
previously registered with the corresponding
|
||||
.Fn el_set
|
||||
call.
|
||||
.El
|
||||
.It Fn el_source
|
||||
Initialise
|
||||
.Nm
|
||||
by reading the contents of
|
||||
.Fa file .
|
||||
.Fn el_parse
|
||||
is called for each line in
|
||||
.Fa file .
|
||||
If
|
||||
.Fa file
|
||||
is
|
||||
.Dv NULL ,
|
||||
try
|
||||
.Pa $PWD/.editrc
|
||||
then
|
||||
.Pa $HOME/.editrc .
|
||||
Refer to
|
||||
.Xr editrc 5
|
||||
for details on the format of
|
||||
.Fa file .
|
||||
.It Fn el_resize
|
||||
Must be called if the terminal size changes.
|
||||
If
|
||||
.Dv EL_SIGNAL
|
||||
has been set with
|
||||
.Fn el_set ,
|
||||
then this is done automatically.
|
||||
Otherwise, it's the responsibility of the application to call
|
||||
.Fn el_resize
|
||||
on the appropriate occasions.
|
||||
.It Fn el_line
|
||||
Return the editing information for the current line in a
|
||||
.Fa LineInfo
|
||||
structure, which is defined as follows:
|
||||
.Bd -literal
|
||||
typedef struct lineinfo {
|
||||
const char *buffer; /* address of buffer */
|
||||
const char *cursor; /* address of cursor */
|
||||
const char *lastchar; /* address of last character */
|
||||
} LineInfo;
|
||||
.Ed
|
||||
.It Fn el_insertstr
|
||||
Insert
|
||||
.Fa str
|
||||
into the line at the cursor.
|
||||
Returns -1 if
|
||||
.Fa str
|
||||
is empty or won't fit, and 0 otherwise.
|
||||
.It Fn el_deletestr
|
||||
Delete
|
||||
.Fa num
|
||||
characters before the cursor.
|
||||
.El
|
||||
.Sh HISTORY LIST FUNCTIONS
|
||||
The history functions use a common data structure,
|
||||
.Fa History ,
|
||||
which is created by
|
||||
.Fn history_init
|
||||
and freed by
|
||||
.Fn history_end .
|
||||
.Pp
|
||||
The following functions are available:
|
||||
.Bl -tag -width 4n
|
||||
.It Fn history_init
|
||||
Initialise the history list, and return a data structure
|
||||
to be used by all other history list functions.
|
||||
.It Fn history_end
|
||||
Clean up and finish with
|
||||
.Fa h ,
|
||||
assumed to have been created with
|
||||
.Fn history_init .
|
||||
.It Fn history
|
||||
Perform operation
|
||||
.Fa op
|
||||
on the history list, with optional arguments as needed by the
|
||||
operation.
|
||||
.Fa ev
|
||||
is changed accordingly to operation.
|
||||
The following values for
|
||||
.Fa op
|
||||
are supported, along with the required argument list:
|
||||
.Bl -tag -width 4n
|
||||
.It Dv H_SETSIZE , Fa "int size"
|
||||
Set size of history to
|
||||
.Fa size
|
||||
elements.
|
||||
.It Dv H_GETSIZE
|
||||
Get number of events currently in history.
|
||||
.It Dv H_END
|
||||
Cleans up and finishes with
|
||||
.Fa h ,
|
||||
assumed to be created with
|
||||
.Fn history_init .
|
||||
.It Dv H_CLEAR
|
||||
Clear the history.
|
||||
.It Dv H_FUNC , Xo
|
||||
.Fa "void *ptr" ,
|
||||
.Fa "history_gfun_t first" ,
|
||||
.Fa "history_gfun_t next" ,
|
||||
.Fa "history_gfun_t last" ,
|
||||
.Fa "history_gfun_t prev" ,
|
||||
.Fa "history_gfun_t curr" ,
|
||||
.Fa "history_sfun_t set" ,
|
||||
.Fa "history_vfun_t clear" ,
|
||||
.Fa "history_efun_t enter" ,
|
||||
.Fa "history_efun_t add"
|
||||
.Xc
|
||||
Define functions to perform various history operations.
|
||||
.Fa ptr
|
||||
is the argument given to a function when it's invoked.
|
||||
.It Dv H_FIRST
|
||||
Return the first element in the history.
|
||||
.It Dv H_LAST
|
||||
Return the last element in the history.
|
||||
.It Dv H_PREV
|
||||
Return the previous element in the history.
|
||||
.It Dv H_NEXT
|
||||
Return the next element in the history.
|
||||
.It Dv H_CURR
|
||||
Return the current element in the history.
|
||||
.It Dv H_SET
|
||||
Set the cursor to point to the requested element.
|
||||
.It Dv H_ADD , Fa "const char *str"
|
||||
Append
|
||||
.Fa str
|
||||
to the current element of the history, or create an element with
|
||||
.It Dv H_APPEND , Fa "const char *str"
|
||||
Append
|
||||
.Fa str
|
||||
to the last new element of the history.
|
||||
.It Dv H_ENTER , Fa "const char *str"
|
||||
Add
|
||||
.Fa str
|
||||
as a new element to the history, and, if necessary,
|
||||
removing the oldest entry to keep the list to the created size.
|
||||
.It Dv H_PREV_STR , Fa "const char *str"
|
||||
Return the closest previous event that starts with
|
||||
.Fa str .
|
||||
.It Dv H_NEXT_STR , Fa "const char *str"
|
||||
Return the closest next event that starts with
|
||||
.Fa str .
|
||||
.It Dv H_PREV_EVENT , Fa "int e"
|
||||
Return the previous event numbered
|
||||
.Fa e .
|
||||
.It Dv H_NEXT_EVENT , Fa "int e"
|
||||
Return the next event numbered
|
||||
.Fa e .
|
||||
.It Dv H_LOAD , Fa "const char *file"
|
||||
Load the history list stored in
|
||||
.Fa file .
|
||||
.It Dv H_SAVE , Fa "const char *file"
|
||||
Save the history list to
|
||||
.Fa file .
|
||||
.El
|
||||
.Pp
|
||||
.Fn history
|
||||
returns 0 if the operation
|
||||
.Fa op
|
||||
succeeds. Otherwise, -1 is returned and
|
||||
.Fa ev
|
||||
is updated to contain more details about the error.
|
||||
.El
|
||||
.\"XXX.Sh EXAMPLES
|
||||
.\"XXX: provide some examples
|
||||
.Sh SEE ALSO
|
||||
.Xr sh 1 ,
|
||||
.Xr signal 3 ,
|
||||
.Xr termcap 3 ,
|
||||
.Xr editrc 5
|
||||
.Sh HISTORY
|
||||
The
|
||||
.Nm
|
||||
library first appeared in
|
||||
.Bx 4.4 .
|
||||
.Dv CC_REDISPLAY
|
||||
appeared in
|
||||
.Nx 1.3 .
|
||||
.Dv CC_REFRESH_BEEP ,
|
||||
.Dv EL_EDITMODE
|
||||
and the readline emulation appeared in
|
||||
.Nx 1.4 .
|
||||
.Dv EL_RPROMPT
|
||||
appeared in
|
||||
.Nx 1.5 .
|
||||
.Sh AUTHORS
|
||||
The
|
||||
.Nm
|
||||
library was written by Christos Zoulas.
|
||||
Luke Mewburn wrote this manual and implemented
|
||||
.Dv CC_REDISPLAY ,
|
||||
.Dv CC_REFRESH_BEEP ,
|
||||
.Dv EL_EDITMODE ,
|
||||
and
|
||||
.Dv EL_RPROMPT .
|
||||
Jaromir Dolecek implemented the readline emulation.
|
||||
.Sh BUGS
|
||||
The tokenization functions are not publicly defined in
|
||||
.Fd <histedit.h> .
|
||||
.Pp
|
||||
At this time, it is the responsibility of the caller to
|
||||
check the result of the
|
||||
.Dv EL_EDITMODE
|
||||
operation of
|
||||
.Fn el_get
|
||||
(after an
|
||||
.Fn el_source
|
||||
or
|
||||
.Fn el_parse )
|
||||
to determine if
|
||||
.Nm
|
||||
should be used for further input.
|
||||
I.e.,
|
||||
.Dv EL_EDITMODE
|
||||
is purely an indication of the result of the most recent
|
||||
.Xr editrc 5
|
||||
.Ic edit
|
||||
command.
|
@@ -1,491 +0,0 @@
|
||||
.\" $NetBSD: editrc.5,v 1.12 2002/01/15 02:46:44 wiz Exp $
|
||||
.\"
|
||||
.\" Copyright (c) 1997-2000 The NetBSD Foundation, Inc.
|
||||
.\" All rights reserved.
|
||||
.\"
|
||||
.\" This file was contributed to The NetBSD Foundation by Luke Mewburn.
|
||||
.\"
|
||||
.\" Redistribution and use in source and binary forms, with or without
|
||||
.\" modification, are permitted provided that the following conditions
|
||||
.\" are met:
|
||||
.\" 1. Redistributions of source code must retain the above copyright
|
||||
.\" notice, this list of conditions and the following disclaimer.
|
||||
.\" 2. Redistributions in binary form must reproduce the above copyright
|
||||
.\" notice, this list of conditions and the following disclaimer in the
|
||||
.\" documentation and/or other materials provided with the distribution.
|
||||
.\" 3. All advertising materials mentioning features or use of this software
|
||||
.\" must display the following acknowledgement:
|
||||
.\" This product includes software developed by the NetBSD
|
||||
.\" Foundation, Inc. and its contributors.
|
||||
.\" 4. Neither the name of The NetBSD Foundation nor the names of its
|
||||
.\" contributors may be used to endorse or promote products derived
|
||||
.\" from this software without specific prior written permission.
|
||||
.\"
|
||||
.\" THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS
|
||||
.\" ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
|
||||
.\" TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
|
||||
.\" PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS
|
||||
.\" BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
|
||||
.\" CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
|
||||
.\" SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
|
||||
.\" INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
|
||||
.\" CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
|
||||
.\" ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
|
||||
.\" POSSIBILITY OF SUCH DAMAGE.
|
||||
.\"
|
||||
.Dd November 8, 2000
|
||||
.Os
|
||||
.Dt EDITRC 5
|
||||
.Sh NAME
|
||||
.Nm editrc
|
||||
.Nd configuration file for editline library
|
||||
.Sh SYNOPSIS
|
||||
.Nm
|
||||
.Sh DESCRIPTION
|
||||
The
|
||||
.Nm
|
||||
file defines various settings to be used by the
|
||||
.Xr editline 3
|
||||
library.
|
||||
.Pp
|
||||
The format of each line is:
|
||||
.Dl [prog:]command [arg [...]]
|
||||
.Pp
|
||||
.Ar command
|
||||
is one of the
|
||||
.Xr editline 3
|
||||
builtin commands.
|
||||
Refer to
|
||||
.Sx BUILTIN COMMANDS
|
||||
for more information.
|
||||
.Pp
|
||||
.Ar prog
|
||||
is the program name string that a program defines when it calls
|
||||
.Xr el_init 3
|
||||
to setup
|
||||
.Xr editline 3 ,
|
||||
which is usually
|
||||
.Va argv[0] .
|
||||
.Ar command
|
||||
will be executed for any program which matches
|
||||
.Ar prog .
|
||||
.Pp
|
||||
.Ar prog
|
||||
may also be a
|
||||
.Xr regex 3
|
||||
style
|
||||
regular expression, in which case
|
||||
.Ar command
|
||||
will be executed for any program that matches the regular expression.
|
||||
.Pp
|
||||
If
|
||||
.Ar prog
|
||||
is absent,
|
||||
.Ar command
|
||||
is executed for all programs.
|
||||
.Sh BUILTIN COMMANDS
|
||||
The
|
||||
.Nm editline
|
||||
library has some builtin commands, which affect the way
|
||||
that the line editing and history functions operate.
|
||||
These are based on similar named builtins present in the
|
||||
.Xr tcsh 1
|
||||
shell.
|
||||
.Pp
|
||||
The following builtin commands are available:
|
||||
.Bl -tag -width 4n
|
||||
.It Ic bind Xo
|
||||
.Op Fl a
|
||||
.Op Fl e
|
||||
.Op Fl k
|
||||
.Op Fl l
|
||||
.Op Fl r
|
||||
.Op Fl s
|
||||
.Op Fl v
|
||||
.Op Ar key Op Ar command
|
||||
.Xc
|
||||
Without options, list all bound keys, and the editor command to which
|
||||
each is bound.
|
||||
If
|
||||
.Ar key
|
||||
is supplied, show the bindings for
|
||||
.Ar key .
|
||||
If
|
||||
.Ar key command
|
||||
is supplied, bind
|
||||
.Ar command
|
||||
to
|
||||
.Ar key .
|
||||
Options include:
|
||||
.Bl -tag -width 4n
|
||||
.It Fl e
|
||||
Bind all keys to the standard GNU Emacs-like bindings.
|
||||
.It Fl v
|
||||
Bind all keys to the standard
|
||||
.Xr vi 1 -like
|
||||
bindings.
|
||||
.It Fl a
|
||||
List or change key bindings in the
|
||||
.Xr vi 1
|
||||
mode alternate (command mode) key map.
|
||||
.It Fl k
|
||||
.Ar key
|
||||
is interpreted as a symbolic arrow key name, which may be one of
|
||||
.Sq up ,
|
||||
.Sq down ,
|
||||
.Sq left
|
||||
or
|
||||
.Sq right .
|
||||
.It Fl l
|
||||
List all editor commands and a short description of each.
|
||||
.It Fl r
|
||||
Remove a key's binding.
|
||||
.It Fl s
|
||||
.Ar command
|
||||
is taken as a literal string and treated as terminal input when
|
||||
.Ar key
|
||||
is typed.
|
||||
Bound keys in
|
||||
.Ar command
|
||||
are themselves reinterpreted, and this continues for ten levels of
|
||||
interpretation.
|
||||
.El
|
||||
.Pp
|
||||
.Ar command
|
||||
may be one of the commands documented in
|
||||
.Sx "EDITOR COMMANDS"
|
||||
below, or another key.
|
||||
.Pp
|
||||
.Ar key
|
||||
and
|
||||
.Ar command
|
||||
can contain control characters of the form
|
||||
.Sm off
|
||||
.Sq No ^ Ar character
|
||||
.Sm on
|
||||
.Po
|
||||
e.g.
|
||||
.Sq ^A
|
||||
.Pc ,
|
||||
and the following backslashed escape sequences:
|
||||
.Pp
|
||||
.Bl -tag -compact -offset indent -width 4n
|
||||
.It Ic \ea
|
||||
Bell
|
||||
.It Ic \eb
|
||||
Backspace
|
||||
.It Ic \ee
|
||||
Escape
|
||||
.It Ic \ef
|
||||
Formfeed
|
||||
.It Ic \en
|
||||
Newline
|
||||
.It Ic \er
|
||||
Carriage return
|
||||
.It Ic \et
|
||||
Horizontal tab
|
||||
.It Ic \ev
|
||||
Vertical tab
|
||||
.Sm off
|
||||
.It Sy \e Ar nnn
|
||||
.Sm on
|
||||
The ASCII character corresponding to the octal number
|
||||
.Ar nnn .
|
||||
.El
|
||||
.Pp
|
||||
.Sq \e
|
||||
nullifies the special meaning of the following character,
|
||||
if it has any, notably
|
||||
.Sq \e
|
||||
and
|
||||
.Sq ^ .
|
||||
.It Ic echotc Xo
|
||||
.Op Fl sv
|
||||
.Ar arg
|
||||
.Ar ...
|
||||
.Xc
|
||||
Exercise terminal capabilities given in
|
||||
.Ar arg Ar ... .
|
||||
If
|
||||
.Ar arg
|
||||
is
|
||||
.Sq baud ,
|
||||
.Sq cols ,
|
||||
.Sq lines ,
|
||||
.Sq rows ,
|
||||
.Sq meta or
|
||||
.Sq tabs ,
|
||||
the value of that capability is printed, with
|
||||
.Dq yes
|
||||
or
|
||||
.Dq no
|
||||
indicating that the terminal does or does not have that capability.
|
||||
.Pp
|
||||
.Fl s
|
||||
returns an emptry string for non-existent capabilities, rather than
|
||||
causing an error.
|
||||
.Fl v
|
||||
causes messages to be verbose.
|
||||
.It Ic edit Op Li on | Li off
|
||||
Enable or disable the
|
||||
.Nm editline
|
||||
functionality in a program.
|
||||
.It Ic history
|
||||
List the history.
|
||||
.It Ic telltc
|
||||
List the values of all the terminal capabilities (see
|
||||
.Xr termcap 5 ) .
|
||||
.It Ic settc Ar cap Ar val
|
||||
Set the terminal capability
|
||||
.Ar cap
|
||||
to
|
||||
.Ar val ,
|
||||
as defined in
|
||||
.Xr termcap 5 .
|
||||
No sanity checking is done.
|
||||
.It Ic setty Xo
|
||||
.Op Fl a
|
||||
.Op Fl d
|
||||
.Op Fl q
|
||||
.Op Fl x
|
||||
.Op Ar +mode
|
||||
.Op Ar -mode
|
||||
.Op Ar mode
|
||||
.Xc
|
||||
Control which tty modes that
|
||||
.Nm
|
||||
won't allow the user to change.
|
||||
.Fl d ,
|
||||
.Fl q
|
||||
or
|
||||
.Fl x
|
||||
tells
|
||||
.Ic setty
|
||||
to act on the
|
||||
.Sq edit ,
|
||||
.Sq quote
|
||||
or
|
||||
.Sq execute
|
||||
set of tty modes respectively; defaulting to
|
||||
.Fl x .
|
||||
.Pp
|
||||
Without other arguments,
|
||||
.Ic setty
|
||||
lists the modes in the chosen set which are fixed on
|
||||
.Po
|
||||
.Sq +mode
|
||||
.Pc
|
||||
or off
|
||||
.Po
|
||||
.Sq -mode
|
||||
.Pc .
|
||||
.Fl a
|
||||
lists all tty modes in the chosen set regardless of the setting.
|
||||
With
|
||||
.Ar +mode ,
|
||||
.Ar -mode
|
||||
or
|
||||
.Ar mode ,
|
||||
fixes
|
||||
.Ar mode
|
||||
on or off or removes control of
|
||||
.Ar mode
|
||||
in the chosen set.
|
||||
.El
|
||||
.Sh EDITOR COMMANDS
|
||||
The following editor commands are available for use in key bindings:
|
||||
.\" Section automatically generated with makelist
|
||||
.Bl -tag -width 4n
|
||||
.It Ic vi-paste-next
|
||||
Vi paste previous deletion to the right of the cursor.
|
||||
.It Ic vi-paste-prev
|
||||
Vi paste previous deletion to the left of the cursor.
|
||||
.It Ic vi-prev-space-word
|
||||
Vi move to the previous space delimited word.
|
||||
.It Ic vi-prev-word
|
||||
Vi move to the previous word.
|
||||
.It Ic vi-next-space-word
|
||||
Vi move to the next space delimited word.
|
||||
.It Ic vi-next-word
|
||||
Vi move to the next word.
|
||||
.It Ic vi-change-case
|
||||
Vi change case of character under the cursor and advance one character.
|
||||
.It Ic vi-change-meta
|
||||
Vi change prefix command.
|
||||
.It Ic vi-insert-at-bol
|
||||
Vi enter insert mode at the beginning of line.
|
||||
.It Ic vi-replace-char
|
||||
Vi replace character under the cursor with the next character typed.
|
||||
.It Ic vi-replace-mode
|
||||
Vi enter replace mode.
|
||||
.It Ic vi-substitute-char
|
||||
Vi replace character under the cursor and enter insert mode.
|
||||
.It Ic vi-substitute-line
|
||||
Vi substitute entire line.
|
||||
.It Ic vi-change-to-eol
|
||||
Vi change to end of line.
|
||||
.It Ic vi-insert
|
||||
Vi enter insert mode.
|
||||
.It Ic vi-add
|
||||
Vi enter insert mode after the cursor.
|
||||
.It Ic vi-add-at-eol
|
||||
Vi enter insert mode at end of line.
|
||||
.It Ic vi-delete-meta
|
||||
Vi delete prefix command.
|
||||
.It Ic vi-end-word
|
||||
Vi move to the end of the current space delimited word.
|
||||
.It Ic vi-to-end-word
|
||||
Vi move to the end of the current word.
|
||||
.It Ic vi-undo
|
||||
Vi undo last change.
|
||||
.It Ic vi-command-mode
|
||||
Vi enter command mode (use alternative key bindings).
|
||||
.It Ic vi-zero
|
||||
Vi move to the beginning of line.
|
||||
.It Ic vi-delete-prev-char
|
||||
Vi move to previous character (backspace).
|
||||
.It Ic vi-list-or-eof
|
||||
Vi list choices for completion or indicate end of file if empty line.
|
||||
.It Ic vi-kill-line-prev
|
||||
Vi cut from beginning of line to cursor.
|
||||
.It Ic vi-search-prev
|
||||
Vi search history previous.
|
||||
.It Ic vi-search-next
|
||||
Vi search history next.
|
||||
.It Ic vi-repeat-search-next
|
||||
Vi repeat current search in the same search direction.
|
||||
.It Ic vi-repeat-search-prev
|
||||
Vi repeat current search in the opposite search direction.
|
||||
.It Ic vi-next-char
|
||||
Vi move to the character specified next.
|
||||
.It Ic vi-prev-char
|
||||
Vi move to the character specified previous.
|
||||
.It Ic vi-to-next-char
|
||||
Vi move up to the character specified next.
|
||||
.It Ic vi-to-prev-char
|
||||
Vi move up to the character specified previous.
|
||||
.It Ic vi-repeat-next-char
|
||||
Vi repeat current character search in the same search direction.
|
||||
.It Ic vi-repeat-prev-char
|
||||
Vi repeat current character search in the opposite search direction.
|
||||
.It Ic em-delete-or-list
|
||||
Delete character under cursor or list completions if at end of line.
|
||||
.It Ic em-delete-next-word
|
||||
Cut from cursor to end of current word.
|
||||
.It Ic em-yank
|
||||
Paste cut buffer at cursor position.
|
||||
.It Ic em-kill-line
|
||||
Cut the entire line and save in cut buffer.
|
||||
.It Ic em-kill-region
|
||||
Cut area between mark and cursor and save in cut buffer.
|
||||
.It Ic em-copy-region
|
||||
Copy area between mark and cursor to cut buffer.
|
||||
.It Ic em-gosmacs-traspose
|
||||
Exchange the two characters before the cursor.
|
||||
.It Ic em-next-word
|
||||
Move next to end of current word.
|
||||
.It Ic em-upper-case
|
||||
Uppercase the characters from cursor to end of current word.
|
||||
.It Ic em-capitol-case
|
||||
Capitalize the characters from cursor to end of current word.
|
||||
.It Ic em-lower-case
|
||||
Lowercase the characters from cursor to end of current word.
|
||||
.It Ic em-set-mark
|
||||
Set the mark at cursor.
|
||||
.It Ic em-exchange-mark
|
||||
Exchange the cursor and mark.
|
||||
.It Ic em-universal-argument
|
||||
Universal argument (argument times 4).
|
||||
.It Ic em-meta-next
|
||||
Add 8th bit to next character typed.
|
||||
.It Ic em-toggle-overwrite
|
||||
Switch from insert to overwrite mode or vice versa.
|
||||
.It Ic em-copy-prev-word
|
||||
Copy current word to cursor.
|
||||
.It Ic em-inc-search-next
|
||||
Emacs incremental next search.
|
||||
.It Ic em-inc-search-prev
|
||||
Emacs incremental reverse search.
|
||||
.It Ic ed-end-of-file
|
||||
Indicate end of file.
|
||||
.It Ic ed-insert
|
||||
Add character to the line.
|
||||
.It Ic ed-delete-prev-word
|
||||
Delete from beginning of current word to cursor.
|
||||
.It Ic ed-delete-next-char
|
||||
Delete character under cursor.
|
||||
.It Ic ed-kill-line
|
||||
Cut to the end of line.
|
||||
.It Ic ed-move-to-end
|
||||
Move cursor to the end of line.
|
||||
.It Ic ed-move-to-beg
|
||||
Move cursor to the beginning of line.
|
||||
.It Ic ed-transpose-chars
|
||||
Exchange the character to the left of the cursor with the one under it.
|
||||
.It Ic ed-next-char
|
||||
Move to the right one character.
|
||||
.It Ic ed-prev-word
|
||||
Move to the beginning of the current word.
|
||||
.It Ic ed-prev-char
|
||||
Move to the left one character.
|
||||
.It Ic ed-quoted-insert
|
||||
Add the next character typed verbatim.
|
||||
.It Ic ed-digit
|
||||
Adds to argument or enters a digit.
|
||||
.It Ic ed-argument-digit
|
||||
Digit that starts argument.
|
||||
.It Ic ed-unassigned
|
||||
Indicates unbound character.
|
||||
.It Ic ed-tty-sigint
|
||||
Tty interrupt character.
|
||||
.It Ic ed-tty-dsusp
|
||||
Tty delayed suspend character.
|
||||
.It Ic ed-tty-flush-output
|
||||
Tty flush output characters.
|
||||
.It Ic ed-tty-sigquit
|
||||
Tty quit character.
|
||||
.It Ic ed-tty-sigtstp
|
||||
Tty suspend character.
|
||||
.It Ic ed-tty-stop-output
|
||||
Tty disallow output characters.
|
||||
.It Ic ed-tty-start-output
|
||||
Tty allow output characters.
|
||||
.It Ic ed-newline
|
||||
Execute command.
|
||||
.It Ic ed-delete-prev-char
|
||||
Delete the character to the left of the cursor.
|
||||
.It Ic ed-clear-screen
|
||||
Clear screen leaving current line at the top.
|
||||
.It Ic ed-redisplay
|
||||
Redisplay everything.
|
||||
.It Ic ed-start-over
|
||||
Erase current line and start from scratch.
|
||||
.It Ic ed-sequence-lead-in
|
||||
First character in a bound sequence.
|
||||
.It Ic ed-prev-history
|
||||
Move to the previous history line.
|
||||
.It Ic ed-next-history
|
||||
Move to the next history line.
|
||||
.It Ic ed-search-prev-history
|
||||
Search previous in history for a line matching the current.
|
||||
.It Ic ed-search-next-history
|
||||
Search next in history for a line matching the current.
|
||||
.It Ic ed-prev-line
|
||||
Move up one line.
|
||||
.It Ic ed-next-line
|
||||
Move down one line.
|
||||
.It Ic ed-command
|
||||
Editline extended command.
|
||||
.El
|
||||
.\" End of section automatically generated with makelist
|
||||
.Sh SEE ALSO
|
||||
.Xr editline 3 ,
|
||||
.Xr regex 3 ,
|
||||
.Xr termcap 5
|
||||
.Sh AUTHORS
|
||||
The
|
||||
.Nm editline
|
||||
library was written by Christos Zoulas,
|
||||
and this manual was written by Luke Mewburn,
|
||||
with some sections inspired by
|
||||
.Xr tcsh 1 .
|
@@ -1,509 +0,0 @@
|
||||
/* $NetBSD: el.c,v 1.29 2002/03/18 16:00:52 christos Exp $ */
|
||||
|
||||
/*-
|
||||
* Copyright (c) 1992, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* This code is derived from software contributed to Berkeley by
|
||||
* Christos Zoulas of Cornell University.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
* 3. All advertising materials mentioning features or use of this software
|
||||
* must display the following acknowledgement:
|
||||
* This product includes software developed by the University of
|
||||
* California, Berkeley and its contributors.
|
||||
* 4. Neither the name of the University nor the names of its contributors
|
||||
* may be used to endorse or promote products derived from this software
|
||||
* without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
|
||||
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
* ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
|
||||
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
|
||||
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*/
|
||||
|
||||
#include "config.h"
|
||||
#if !defined(lint) && !defined(SCCSID)
|
||||
#if 0
|
||||
static char sccsid[] = "@(#)el.c 8.2 (Berkeley) 1/3/94";
|
||||
#else
|
||||
__RCSID("$NetBSD: el.c,v 1.29 2002/03/18 16:00:52 christos Exp $");
|
||||
#endif
|
||||
#endif /* not lint && not SCCSID */
|
||||
|
||||
/*
|
||||
* el.c: EditLine interface functions
|
||||
*/
|
||||
#include <sys/types.h>
|
||||
#include <sys/param.h>
|
||||
#include <string.h>
|
||||
#include <stdlib.h>
|
||||
#include <stdarg.h>
|
||||
#include "el.h"
|
||||
|
||||
/* el_init():
|
||||
* Initialize editline and set default parameters.
|
||||
*/
|
||||
public EditLine *
|
||||
el_init(const char *prog, FILE *fin, FILE *fout, FILE *ferr)
|
||||
{
|
||||
|
||||
EditLine *el = (EditLine *) el_malloc(sizeof(EditLine));
|
||||
|
||||
if (el == NULL)
|
||||
return (NULL);
|
||||
|
||||
memset(el, 0, sizeof(EditLine));
|
||||
|
||||
el->el_infd = fileno(fin);
|
||||
el->el_outfile = fout;
|
||||
el->el_errfile = ferr;
|
||||
el->el_prog = strdup(prog);
|
||||
|
||||
/*
|
||||
* Initialize all the modules. Order is important!!!
|
||||
*/
|
||||
el->el_flags = 0;
|
||||
|
||||
if (term_init(el) == -1) {
|
||||
free(el->el_prog);
|
||||
el_free(el);
|
||||
return NULL;
|
||||
}
|
||||
(void) key_init(el);
|
||||
(void) map_init(el);
|
||||
if (tty_init(el) == -1)
|
||||
el->el_flags |= NO_TTY;
|
||||
(void) ch_init(el);
|
||||
(void) search_init(el);
|
||||
(void) hist_init(el);
|
||||
(void) prompt_init(el);
|
||||
(void) sig_init(el);
|
||||
(void) read_init(el);
|
||||
|
||||
return (el);
|
||||
}
|
||||
|
||||
|
||||
/* el_end():
|
||||
* Clean up.
|
||||
*/
|
||||
public void
|
||||
el_end(EditLine *el)
|
||||
{
|
||||
|
||||
if (el == NULL)
|
||||
return;
|
||||
|
||||
el_reset(el);
|
||||
|
||||
term_end(el);
|
||||
key_end(el);
|
||||
map_end(el);
|
||||
tty_end(el);
|
||||
ch_end(el);
|
||||
search_end(el);
|
||||
hist_end(el);
|
||||
prompt_end(el);
|
||||
sig_end(el);
|
||||
|
||||
if (el->el_prog)
|
||||
el_free((ptr_t) el->el_prog);
|
||||
el_free((ptr_t) el);
|
||||
}
|
||||
|
||||
|
||||
/* el_reset():
|
||||
* Reset the tty and the parser
|
||||
*/
|
||||
public void
|
||||
el_reset(EditLine *el)
|
||||
{
|
||||
|
||||
tty_cookedmode(el);
|
||||
ch_reset(el); /* XXX: Do we want that? */
|
||||
}
|
||||
|
||||
|
||||
/* el_set():
|
||||
* set the editline parameters
|
||||
*/
|
||||
public int
|
||||
el_set(EditLine *el, int op, ...)
|
||||
{
|
||||
va_list va;
|
||||
int rv = 0;
|
||||
|
||||
if (el == NULL)
|
||||
return (-1);
|
||||
va_start(va, op);
|
||||
|
||||
switch (op) {
|
||||
case EL_PROMPT:
|
||||
case EL_RPROMPT:
|
||||
rv = prompt_set(el, va_arg(va, el_pfunc_t), op);
|
||||
break;
|
||||
|
||||
case EL_TERMINAL:
|
||||
rv = term_set(el, va_arg(va, char *));
|
||||
break;
|
||||
|
||||
case EL_EDITOR:
|
||||
rv = map_set_editor(el, va_arg(va, char *));
|
||||
break;
|
||||
|
||||
case EL_SIGNAL:
|
||||
if (va_arg(va, int))
|
||||
el->el_flags |= HANDLE_SIGNALS;
|
||||
else
|
||||
el->el_flags &= ~HANDLE_SIGNALS;
|
||||
break;
|
||||
|
||||
case EL_BIND:
|
||||
case EL_TELLTC:
|
||||
case EL_SETTC:
|
||||
case EL_ECHOTC:
|
||||
case EL_SETTY:
|
||||
{
|
||||
const char *argv[20];
|
||||
int i;
|
||||
|
||||
for (i = 1; i < 20; i++)
|
||||
if ((argv[i] = va_arg(va, char *)) == NULL)
|
||||
break;
|
||||
|
||||
switch (op) {
|
||||
case EL_BIND:
|
||||
argv[0] = "bind";
|
||||
rv = map_bind(el, i, argv);
|
||||
break;
|
||||
|
||||
case EL_TELLTC:
|
||||
argv[0] = "telltc";
|
||||
rv = term_telltc(el, i, argv);
|
||||
break;
|
||||
|
||||
case EL_SETTC:
|
||||
argv[0] = "settc";
|
||||
rv = term_settc(el, i, argv);
|
||||
break;
|
||||
|
||||
case EL_ECHOTC:
|
||||
argv[0] = "echotc";
|
||||
rv = term_echotc(el, i, argv);
|
||||
break;
|
||||
|
||||
case EL_SETTY:
|
||||
argv[0] = "setty";
|
||||
rv = tty_stty(el, i, argv);
|
||||
break;
|
||||
|
||||
default:
|
||||
rv = -1;
|
||||
EL_ABORT((el->el_errfile, "Bad op %d\n", op));
|
||||
break;
|
||||
}
|
||||
break;
|
||||
}
|
||||
|
||||
case EL_ADDFN:
|
||||
{
|
||||
char *name = va_arg(va, char *);
|
||||
char *help = va_arg(va, char *);
|
||||
el_func_t func = va_arg(va, el_func_t);
|
||||
|
||||
rv = map_addfunc(el, name, help, func);
|
||||
break;
|
||||
}
|
||||
|
||||
case EL_HIST:
|
||||
{
|
||||
hist_fun_t func = va_arg(va, hist_fun_t);
|
||||
ptr_t ptr = va_arg(va, char *);
|
||||
|
||||
rv = hist_set(el, func, ptr);
|
||||
break;
|
||||
}
|
||||
|
||||
case EL_EDITMODE:
|
||||
if (va_arg(va, int))
|
||||
el->el_flags &= ~EDIT_DISABLED;
|
||||
else
|
||||
el->el_flags |= EDIT_DISABLED;
|
||||
rv = 0;
|
||||
break;
|
||||
|
||||
case EL_GETCFN:
|
||||
{
|
||||
el_rfunc_t rc = va_arg(va, el_rfunc_t);
|
||||
rv = el_read_setfn(el, rc);
|
||||
break;
|
||||
}
|
||||
|
||||
case EL_CLIENTDATA:
|
||||
el->el_data = va_arg(va, void *);
|
||||
break;
|
||||
|
||||
default:
|
||||
rv = -1;
|
||||
break;
|
||||
}
|
||||
|
||||
va_end(va);
|
||||
return (rv);
|
||||
}
|
||||
|
||||
|
||||
/* el_get():
|
||||
* retrieve the editline parameters
|
||||
*/
|
||||
public int
|
||||
el_get(EditLine *el, int op, void *ret)
|
||||
{
|
||||
int rv;
|
||||
|
||||
if (el == NULL || ret == NULL)
|
||||
return (-1);
|
||||
switch (op) {
|
||||
case EL_PROMPT:
|
||||
case EL_RPROMPT:
|
||||
rv = prompt_get(el, (el_pfunc_t *) & ret, op);
|
||||
break;
|
||||
|
||||
case EL_EDITOR:
|
||||
rv = map_get_editor(el, (const char **) &ret);
|
||||
break;
|
||||
|
||||
case EL_SIGNAL:
|
||||
*((int *) ret) = (el->el_flags & HANDLE_SIGNALS);
|
||||
rv = 0;
|
||||
break;
|
||||
|
||||
case EL_EDITMODE:
|
||||
*((int *) ret) = (!(el->el_flags & EDIT_DISABLED));
|
||||
rv = 0;
|
||||
break;
|
||||
|
||||
#if 0 /* XXX */
|
||||
case EL_TERMINAL:
|
||||
rv = term_get(el, (const char *) &ret);
|
||||
break;
|
||||
|
||||
case EL_BIND:
|
||||
case EL_TELLTC:
|
||||
case EL_SETTC:
|
||||
case EL_ECHOTC:
|
||||
case EL_SETTY:
|
||||
{
|
||||
char *argv[20];
|
||||
int i;
|
||||
|
||||
for (i = 1; i < 20; i++)
|
||||
if ((argv[i] = va_arg(va, char *)) == NULL)
|
||||
break;
|
||||
|
||||
switch (op) {
|
||||
case EL_BIND:
|
||||
argv[0] = "bind";
|
||||
rv = map_bind(el, i, argv);
|
||||
break;
|
||||
|
||||
case EL_TELLTC:
|
||||
argv[0] = "telltc";
|
||||
rv = term_telltc(el, i, argv);
|
||||
break;
|
||||
|
||||
case EL_SETTC:
|
||||
argv[0] = "settc";
|
||||
rv = term_settc(el, i, argv);
|
||||
break;
|
||||
|
||||
case EL_ECHOTC:
|
||||
argv[0] = "echotc";
|
||||
rv = term_echotc(el, i, argv);
|
||||
break;
|
||||
|
||||
case EL_SETTY:
|
||||
argv[0] = "setty";
|
||||
rv = tty_stty(el, i, argv);
|
||||
break;
|
||||
|
||||
default:
|
||||
rv = -1;
|
||||
EL_ABORT((el->errfile, "Bad op %d\n", op));
|
||||
break;
|
||||
}
|
||||
break;
|
||||
}
|
||||
|
||||
case EL_ADDFN:
|
||||
{
|
||||
char *name = va_arg(va, char *);
|
||||
char *help = va_arg(va, char *);
|
||||
el_func_t func = va_arg(va, el_func_t);
|
||||
|
||||
rv = map_addfunc(el, name, help, func);
|
||||
break;
|
||||
}
|
||||
|
||||
case EL_HIST:
|
||||
{
|
||||
hist_fun_t func = va_arg(va, hist_fun_t);
|
||||
ptr_t ptr = va_arg(va, char *);
|
||||
rv = hist_set(el, func, ptr);
|
||||
}
|
||||
break;
|
||||
#endif /* XXX */
|
||||
|
||||
case EL_GETCFN:
|
||||
*((el_rfunc_t *)ret) = el_read_getfn(el);
|
||||
rv = 0;
|
||||
break;
|
||||
|
||||
case EL_CLIENTDATA:
|
||||
*((void **)ret) = el->el_data;
|
||||
rv = 0;
|
||||
break;
|
||||
|
||||
default:
|
||||
rv = -1;
|
||||
}
|
||||
|
||||
return (rv);
|
||||
}
|
||||
|
||||
|
||||
/* el_line():
|
||||
* Return editing info
|
||||
*/
|
||||
public const LineInfo *
|
||||
el_line(EditLine *el)
|
||||
{
|
||||
|
||||
return (const LineInfo *) (void *) &el->el_line;
|
||||
}
|
||||
|
||||
|
||||
/* el_source():
|
||||
* Source a file
|
||||
*/
|
||||
public int
|
||||
el_source(EditLine *el, const char *fname)
|
||||
{
|
||||
FILE *fp;
|
||||
size_t len;
|
||||
char *ptr;
|
||||
|
||||
fp = NULL;
|
||||
if (fname == NULL) {
|
||||
#ifdef HAVE_ISSETUGID
|
||||
static const char elpath[] = "/.editrc";
|
||||
char path[MAXPATHLEN];
|
||||
|
||||
if (issetugid())
|
||||
return (-1);
|
||||
if ((ptr = getenv("HOME")) == NULL)
|
||||
return (-1);
|
||||
if (strlcpy(path, ptr, sizeof(path)) >= sizeof(path))
|
||||
return (-1);
|
||||
if (strlcat(path, elpath, sizeof(path)) >= sizeof(path))
|
||||
return (-1);
|
||||
fname = path;
|
||||
#else
|
||||
/*
|
||||
* If issetugid() is missing, always return an error, in order
|
||||
* to keep from inadvertently opening up the user to a security
|
||||
* hole.
|
||||
*/
|
||||
return (-1);
|
||||
#endif
|
||||
}
|
||||
if (fp == NULL)
|
||||
fp = fopen(fname, "r");
|
||||
if (fp == NULL)
|
||||
return (-1);
|
||||
|
||||
while ((ptr = fgetln(fp, &len)) != NULL) {
|
||||
if (len > 0 && ptr[len - 1] == '\n')
|
||||
--len;
|
||||
ptr[len] = '\0';
|
||||
if (parse_line(el, ptr) == -1) {
|
||||
(void) fclose(fp);
|
||||
return (-1);
|
||||
}
|
||||
}
|
||||
|
||||
(void) fclose(fp);
|
||||
return (0);
|
||||
}
|
||||
|
||||
|
||||
/* el_resize():
|
||||
* Called from program when terminal is resized
|
||||
*/
|
||||
public void
|
||||
el_resize(EditLine *el)
|
||||
{
|
||||
int lins, cols;
|
||||
sigset_t oset, nset;
|
||||
|
||||
(void) sigemptyset(&nset);
|
||||
(void) sigaddset(&nset, SIGWINCH);
|
||||
(void) sigprocmask(SIG_BLOCK, &nset, &oset);
|
||||
|
||||
/* get the correct window size */
|
||||
if (term_get_size(el, &lins, &cols))
|
||||
term_change_size(el, lins, cols);
|
||||
|
||||
(void) sigprocmask(SIG_SETMASK, &oset, NULL);
|
||||
}
|
||||
|
||||
|
||||
/* el_beep():
|
||||
* Called from the program to beep
|
||||
*/
|
||||
public void
|
||||
el_beep(EditLine *el)
|
||||
{
|
||||
|
||||
term_beep(el);
|
||||
}
|
||||
|
||||
|
||||
/* el_editmode()
|
||||
* Set the state of EDIT_DISABLED from the `edit' command.
|
||||
*/
|
||||
protected int
|
||||
/*ARGSUSED*/
|
||||
el_editmode(EditLine *el, int argc, const char **argv)
|
||||
{
|
||||
const char *how;
|
||||
|
||||
if (argv == NULL || argc != 2 || argv[1] == NULL)
|
||||
return (-1);
|
||||
|
||||
how = argv[1];
|
||||
if (strcmp(how, "on") == 0)
|
||||
el->el_flags &= ~EDIT_DISABLED;
|
||||
else if (strcmp(how, "off") == 0)
|
||||
el->el_flags |= EDIT_DISABLED;
|
||||
else {
|
||||
(void) fprintf(el->el_errfile, "edit: Bad value `%s'.\n", how);
|
||||
return (-1);
|
||||
}
|
||||
return (0);
|
||||
}
|
@@ -1,145 +0,0 @@
|
||||
/* $NetBSD: el.h,v 1.11 2002/03/18 16:00:52 christos Exp $ */
|
||||
|
||||
/*-
|
||||
* Copyright (c) 1992, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* This code is derived from software contributed to Berkeley by
|
||||
* Christos Zoulas of Cornell University.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
* 3. All advertising materials mentioning features or use of this software
|
||||
* must display the following acknowledgement:
|
||||
* This product includes software developed by the University of
|
||||
* California, Berkeley and its contributors.
|
||||
* 4. Neither the name of the University nor the names of its contributors
|
||||
* may be used to endorse or promote products derived from this software
|
||||
* without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
|
||||
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
* ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
|
||||
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
|
||||
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* @(#)el.h 8.1 (Berkeley) 6/4/93
|
||||
*/
|
||||
|
||||
/*
|
||||
* el.h: Internal structures.
|
||||
*/
|
||||
#ifndef _h_el
|
||||
#define _h_el
|
||||
/*
|
||||
* Local defaults
|
||||
*/
|
||||
#define KSHVI
|
||||
#define VIDEFAULT
|
||||
#define ANCHOR
|
||||
|
||||
#include <stdio.h>
|
||||
#include <sys/types.h>
|
||||
|
||||
#define EL_BUFSIZ 1024 /* Maximum line size */
|
||||
|
||||
#define HANDLE_SIGNALS 1<<0
|
||||
#define NO_TTY 1<<1
|
||||
#define EDIT_DISABLED 1<<2
|
||||
|
||||
typedef int bool_t; /* True or not */
|
||||
|
||||
typedef unsigned char el_action_t; /* Index to command array */
|
||||
|
||||
typedef struct coord_t { /* Position on the screen */
|
||||
int h;
|
||||
int v;
|
||||
} coord_t;
|
||||
|
||||
typedef struct el_line_t {
|
||||
char *buffer; /* Input line */
|
||||
char *cursor; /* Cursor position */
|
||||
char *lastchar; /* Last character */
|
||||
const char *limit; /* Max position */
|
||||
} el_line_t;
|
||||
|
||||
/*
|
||||
* Editor state
|
||||
*/
|
||||
typedef struct el_state_t {
|
||||
int inputmode; /* What mode are we in? */
|
||||
int doingarg; /* Are we getting an argument? */
|
||||
int argument; /* Numeric argument */
|
||||
int metanext; /* Is the next char a meta char */
|
||||
el_action_t lastcmd; /* Previous command */
|
||||
} el_state_t;
|
||||
|
||||
/*
|
||||
* Until we come up with something better...
|
||||
*/
|
||||
#define el_malloc(a) malloc(a)
|
||||
#define el_realloc(a,b) realloc(a, b)
|
||||
#define el_free(a) free(a)
|
||||
|
||||
#include "tty.h"
|
||||
#include "prompt.h"
|
||||
#include "key.h"
|
||||
#include "term.h"
|
||||
#include "refresh.h"
|
||||
#include "chared.h"
|
||||
#include "common.h"
|
||||
#include "search.h"
|
||||
#include "hist.h"
|
||||
#include "map.h"
|
||||
#include "parse.h"
|
||||
#include "sig.h"
|
||||
#include "help.h"
|
||||
#include "read.h"
|
||||
|
||||
struct editline {
|
||||
char *el_prog; /* the program name */
|
||||
FILE *el_outfile; /* Stdio stuff */
|
||||
FILE *el_errfile; /* Stdio stuff */
|
||||
int el_infd; /* Input file descriptor */
|
||||
int el_flags; /* Various flags. */
|
||||
coord_t el_cursor; /* Cursor location */
|
||||
char **el_display; /* Real screen image = what is there */
|
||||
char **el_vdisplay; /* Virtual screen image = what we see */
|
||||
void *el_data; /* Client data */
|
||||
el_line_t el_line; /* The current line information */
|
||||
el_state_t el_state; /* Current editor state */
|
||||
el_term_t el_term; /* Terminal dependent stuff */
|
||||
el_tty_t el_tty; /* Tty dependent stuff */
|
||||
el_refresh_t el_refresh; /* Refresh stuff */
|
||||
el_prompt_t el_prompt; /* Prompt stuff */
|
||||
el_prompt_t el_rprompt; /* Prompt stuff */
|
||||
el_chared_t el_chared; /* Characted editor stuff */
|
||||
el_map_t el_map; /* Key mapping stuff */
|
||||
el_key_t el_key; /* Key binding stuff */
|
||||
el_history_t el_history; /* History stuff */
|
||||
el_search_t el_search; /* Search stuff */
|
||||
el_signal_t el_signal; /* Signal handling stuff */
|
||||
el_read_t el_read; /* Character reading stuff */
|
||||
};
|
||||
|
||||
protected int el_editmode(EditLine *, int, const char **);
|
||||
|
||||
#ifdef DEBUG
|
||||
#define EL_ABORT(a) (void) (fprintf(el->el_errfile, "%s, %d: ", \
|
||||
__FILE__, __LINE__), fprintf a, abort())
|
||||
#else
|
||||
#define EL_ABORT(a) abort()
|
||||
#endif
|
||||
#endif /* _h_el */
|
@@ -1,488 +0,0 @@
|
||||
/* $NetBSD: emacs.c,v 1.10 2002/03/18 16:00:52 christos Exp $ */
|
||||
|
||||
/*-
|
||||
* Copyright (c) 1992, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* This code is derived from software contributed to Berkeley by
|
||||
* Christos Zoulas of Cornell University.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
* 3. All advertising materials mentioning features or use of this software
|
||||
* must display the following acknowledgement:
|
||||
* This product includes software developed by the University of
|
||||
* California, Berkeley and its contributors.
|
||||
* 4. Neither the name of the University nor the names of its contributors
|
||||
* may be used to endorse or promote products derived from this software
|
||||
* without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
|
||||
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
* ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
|
||||
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
|
||||
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*/
|
||||
|
||||
#include "config.h"
|
||||
#if !defined(lint) && !defined(SCCSID)
|
||||
#if 0
|
||||
static char sccsid[] = "@(#)emacs.c 8.1 (Berkeley) 6/4/93";
|
||||
#else
|
||||
__RCSID("$NetBSD: emacs.c,v 1.10 2002/03/18 16:00:52 christos Exp $");
|
||||
#endif
|
||||
#endif /* not lint && not SCCSID */
|
||||
|
||||
/*
|
||||
* emacs.c: Emacs functions
|
||||
*/
|
||||
#include "el.h"
|
||||
|
||||
/* em_delete_or_list():
|
||||
* Delete character under cursor or list completions if at end of line
|
||||
* [^D]
|
||||
*/
|
||||
protected el_action_t
|
||||
/*ARGSUSED*/
|
||||
em_delete_or_list(EditLine *el, int c)
|
||||
{
|
||||
|
||||
if (el->el_line.cursor == el->el_line.lastchar) {
|
||||
/* if I'm at the end */
|
||||
if (el->el_line.cursor == el->el_line.buffer) {
|
||||
/* and the beginning */
|
||||
term_overwrite(el, STReof, 4); /* then do a EOF */
|
||||
term__flush();
|
||||
return (CC_EOF);
|
||||
} else {
|
||||
/*
|
||||
* Here we could list completions, but it is an
|
||||
* error right now
|
||||
*/
|
||||
term_beep(el);
|
||||
return (CC_ERROR);
|
||||
}
|
||||
} else {
|
||||
c_delafter(el, el->el_state.argument); /* delete after dot */
|
||||
if (el->el_line.cursor > el->el_line.lastchar)
|
||||
el->el_line.cursor = el->el_line.lastchar;
|
||||
/* bounds check */
|
||||
return (CC_REFRESH);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/* em_delete_next_word():
|
||||
* Cut from cursor to end of current word
|
||||
* [M-d]
|
||||
*/
|
||||
protected el_action_t
|
||||
/*ARGSUSED*/
|
||||
em_delete_next_word(EditLine *el, int c)
|
||||
{
|
||||
char *cp, *p, *kp;
|
||||
|
||||
if (el->el_line.cursor == el->el_line.lastchar)
|
||||
return (CC_ERROR);
|
||||
|
||||
cp = c__next_word(el->el_line.cursor, el->el_line.lastchar,
|
||||
el->el_state.argument, ce__isword);
|
||||
|
||||
for (p = el->el_line.cursor, kp = el->el_chared.c_kill.buf; p < cp; p++)
|
||||
/* save the text */
|
||||
*kp++ = *p;
|
||||
el->el_chared.c_kill.last = kp;
|
||||
|
||||
c_delafter(el, cp - el->el_line.cursor); /* delete after dot */
|
||||
if (el->el_line.cursor > el->el_line.lastchar)
|
||||
el->el_line.cursor = el->el_line.lastchar;
|
||||
/* bounds check */
|
||||
return (CC_REFRESH);
|
||||
}
|
||||
|
||||
|
||||
/* em_yank():
|
||||
* Paste cut buffer at cursor position
|
||||
* [^Y]
|
||||
*/
|
||||
protected el_action_t
|
||||
/*ARGSUSED*/
|
||||
em_yank(EditLine *el, int c)
|
||||
{
|
||||
char *kp, *cp;
|
||||
|
||||
if (el->el_chared.c_kill.last == el->el_chared.c_kill.buf) {
|
||||
if (!ch_enlargebufs(el, 1))
|
||||
return (CC_ERROR);
|
||||
}
|
||||
|
||||
if (el->el_line.lastchar +
|
||||
(el->el_chared.c_kill.last - el->el_chared.c_kill.buf) >=
|
||||
el->el_line.limit)
|
||||
return (CC_ERROR);
|
||||
|
||||
el->el_chared.c_kill.mark = el->el_line.cursor;
|
||||
cp = el->el_line.cursor;
|
||||
|
||||
/* open the space, */
|
||||
c_insert(el, el->el_chared.c_kill.last - el->el_chared.c_kill.buf);
|
||||
/* copy the chars */
|
||||
for (kp = el->el_chared.c_kill.buf; kp < el->el_chared.c_kill.last; kp++)
|
||||
*cp++ = *kp;
|
||||
|
||||
/* if an arg, cursor at beginning else cursor at end */
|
||||
if (el->el_state.argument == 1)
|
||||
el->el_line.cursor = cp;
|
||||
|
||||
return (CC_REFRESH);
|
||||
}
|
||||
|
||||
|
||||
/* em_kill_line():
|
||||
* Cut the entire line and save in cut buffer
|
||||
* [^U]
|
||||
*/
|
||||
protected el_action_t
|
||||
/*ARGSUSED*/
|
||||
em_kill_line(EditLine *el, int c)
|
||||
{
|
||||
char *kp, *cp;
|
||||
|
||||
cp = el->el_line.buffer;
|
||||
kp = el->el_chared.c_kill.buf;
|
||||
while (cp < el->el_line.lastchar)
|
||||
*kp++ = *cp++; /* copy it */
|
||||
el->el_chared.c_kill.last = kp;
|
||||
/* zap! -- delete all of it */
|
||||
el->el_line.lastchar = el->el_line.buffer;
|
||||
el->el_line.cursor = el->el_line.buffer;
|
||||
return (CC_REFRESH);
|
||||
}
|
||||
|
||||
|
||||
/* em_kill_region():
|
||||
* Cut area between mark and cursor and save in cut buffer
|
||||
* [^W]
|
||||
*/
|
||||
protected el_action_t
|
||||
/*ARGSUSED*/
|
||||
em_kill_region(EditLine *el, int c)
|
||||
{
|
||||
char *kp, *cp;
|
||||
|
||||
if (!el->el_chared.c_kill.mark)
|
||||
return (CC_ERROR);
|
||||
|
||||
if (el->el_chared.c_kill.mark > el->el_line.cursor) {
|
||||
cp = el->el_line.cursor;
|
||||
kp = el->el_chared.c_kill.buf;
|
||||
while (cp < el->el_chared.c_kill.mark)
|
||||
*kp++ = *cp++; /* copy it */
|
||||
el->el_chared.c_kill.last = kp;
|
||||
c_delafter(el, cp - el->el_line.cursor);
|
||||
} else { /* mark is before cursor */
|
||||
cp = el->el_chared.c_kill.mark;
|
||||
kp = el->el_chared.c_kill.buf;
|
||||
while (cp < el->el_line.cursor)
|
||||
*kp++ = *cp++; /* copy it */
|
||||
el->el_chared.c_kill.last = kp;
|
||||
c_delbefore(el, cp - el->el_chared.c_kill.mark);
|
||||
el->el_line.cursor = el->el_chared.c_kill.mark;
|
||||
}
|
||||
return (CC_REFRESH);
|
||||
}
|
||||
|
||||
|
||||
/* em_copy_region():
|
||||
* Copy area between mark and cursor to cut buffer
|
||||
* [M-W]
|
||||
*/
|
||||
protected el_action_t
|
||||
/*ARGSUSED*/
|
||||
em_copy_region(EditLine *el, int c)
|
||||
{
|
||||
char *kp, *cp;
|
||||
|
||||
if (el->el_chared.c_kill.mark)
|
||||
return (CC_ERROR);
|
||||
|
||||
if (el->el_chared.c_kill.mark > el->el_line.cursor) {
|
||||
cp = el->el_line.cursor;
|
||||
kp = el->el_chared.c_kill.buf;
|
||||
while (cp < el->el_chared.c_kill.mark)
|
||||
*kp++ = *cp++; /* copy it */
|
||||
el->el_chared.c_kill.last = kp;
|
||||
} else {
|
||||
cp = el->el_chared.c_kill.mark;
|
||||
kp = el->el_chared.c_kill.buf;
|
||||
while (cp < el->el_line.cursor)
|
||||
*kp++ = *cp++; /* copy it */
|
||||
el->el_chared.c_kill.last = kp;
|
||||
}
|
||||
return (CC_NORM);
|
||||
}
|
||||
|
||||
|
||||
/* em_gosmacs_traspose():
|
||||
* Exchange the two characters before the cursor
|
||||
* Gosling emacs transpose chars [^T]
|
||||
*/
|
||||
protected el_action_t
|
||||
em_gosmacs_traspose(EditLine *el, int c)
|
||||
{
|
||||
|
||||
if (el->el_line.cursor > &el->el_line.buffer[1]) {
|
||||
/* must have at least two chars entered */
|
||||
c = el->el_line.cursor[-2];
|
||||
el->el_line.cursor[-2] = el->el_line.cursor[-1];
|
||||
el->el_line.cursor[-1] = c;
|
||||
return (CC_REFRESH);
|
||||
} else
|
||||
return (CC_ERROR);
|
||||
}
|
||||
|
||||
|
||||
/* em_next_word():
|
||||
* Move next to end of current word
|
||||
* [M-f]
|
||||
*/
|
||||
protected el_action_t
|
||||
/*ARGSUSED*/
|
||||
em_next_word(EditLine *el, int c)
|
||||
{
|
||||
if (el->el_line.cursor == el->el_line.lastchar)
|
||||
return (CC_ERROR);
|
||||
|
||||
el->el_line.cursor = c__next_word(el->el_line.cursor,
|
||||
el->el_line.lastchar,
|
||||
el->el_state.argument,
|
||||
ce__isword);
|
||||
|
||||
if (el->el_map.type == MAP_VI)
|
||||
if (el->el_chared.c_vcmd.action & DELETE) {
|
||||
cv_delfini(el);
|
||||
return (CC_REFRESH);
|
||||
}
|
||||
return (CC_CURSOR);
|
||||
}
|
||||
|
||||
|
||||
/* em_upper_case():
|
||||
* Uppercase the characters from cursor to end of current word
|
||||
* [M-u]
|
||||
*/
|
||||
protected el_action_t
|
||||
/*ARGSUSED*/
|
||||
em_upper_case(EditLine *el, int c)
|
||||
{
|
||||
char *cp, *ep;
|
||||
|
||||
ep = c__next_word(el->el_line.cursor, el->el_line.lastchar,
|
||||
el->el_state.argument, ce__isword);
|
||||
|
||||
for (cp = el->el_line.cursor; cp < ep; cp++)
|
||||
if (islower((unsigned char) *cp))
|
||||
*cp = toupper(*cp);
|
||||
|
||||
el->el_line.cursor = ep;
|
||||
if (el->el_line.cursor > el->el_line.lastchar)
|
||||
el->el_line.cursor = el->el_line.lastchar;
|
||||
return (CC_REFRESH);
|
||||
}
|
||||
|
||||
|
||||
/* em_capitol_case():
|
||||
* Capitalize the characters from cursor to end of current word
|
||||
* [M-c]
|
||||
*/
|
||||
protected el_action_t
|
||||
/*ARGSUSED*/
|
||||
em_capitol_case(EditLine *el, int c)
|
||||
{
|
||||
char *cp, *ep;
|
||||
|
||||
ep = c__next_word(el->el_line.cursor, el->el_line.lastchar,
|
||||
el->el_state.argument, ce__isword);
|
||||
|
||||
for (cp = el->el_line.cursor; cp < ep; cp++) {
|
||||
if (isalpha((unsigned char) *cp)) {
|
||||
if (islower((unsigned char) *cp))
|
||||
*cp = toupper(*cp);
|
||||
cp++;
|
||||
break;
|
||||
}
|
||||
}
|
||||
for (; cp < ep; cp++)
|
||||
if (isupper((unsigned char) *cp))
|
||||
*cp = tolower(*cp);
|
||||
|
||||
el->el_line.cursor = ep;
|
||||
if (el->el_line.cursor > el->el_line.lastchar)
|
||||
el->el_line.cursor = el->el_line.lastchar;
|
||||
return (CC_REFRESH);
|
||||
}
|
||||
|
||||
|
||||
/* em_lower_case():
|
||||
* Lowercase the characters from cursor to end of current word
|
||||
* [M-l]
|
||||
*/
|
||||
protected el_action_t
|
||||
/*ARGSUSED*/
|
||||
em_lower_case(EditLine *el, int c)
|
||||
{
|
||||
char *cp, *ep;
|
||||
|
||||
ep = c__next_word(el->el_line.cursor, el->el_line.lastchar,
|
||||
el->el_state.argument, ce__isword);
|
||||
|
||||
for (cp = el->el_line.cursor; cp < ep; cp++)
|
||||
if (isupper((unsigned char) *cp))
|
||||
*cp = tolower(*cp);
|
||||
|
||||
el->el_line.cursor = ep;
|
||||
if (el->el_line.cursor > el->el_line.lastchar)
|
||||
el->el_line.cursor = el->el_line.lastchar;
|
||||
return (CC_REFRESH);
|
||||
}
|
||||
|
||||
|
||||
/* em_set_mark():
|
||||
* Set the mark at cursor
|
||||
* [^@]
|
||||
*/
|
||||
protected el_action_t
|
||||
/*ARGSUSED*/
|
||||
em_set_mark(EditLine *el, int c)
|
||||
{
|
||||
|
||||
el->el_chared.c_kill.mark = el->el_line.cursor;
|
||||
return (CC_NORM);
|
||||
}
|
||||
|
||||
|
||||
/* em_exchange_mark():
|
||||
* Exchange the cursor and mark
|
||||
* [^X^X]
|
||||
*/
|
||||
protected el_action_t
|
||||
/*ARGSUSED*/
|
||||
em_exchange_mark(EditLine *el, int c)
|
||||
{
|
||||
char *cp;
|
||||
|
||||
cp = el->el_line.cursor;
|
||||
el->el_line.cursor = el->el_chared.c_kill.mark;
|
||||
el->el_chared.c_kill.mark = cp;
|
||||
return (CC_CURSOR);
|
||||
}
|
||||
|
||||
|
||||
/* em_universal_argument():
|
||||
* Universal argument (argument times 4)
|
||||
* [^U]
|
||||
*/
|
||||
protected el_action_t
|
||||
/*ARGSUSED*/
|
||||
em_universal_argument(EditLine *el, int c)
|
||||
{ /* multiply current argument by 4 */
|
||||
|
||||
if (el->el_state.argument > 1000000)
|
||||
return (CC_ERROR);
|
||||
el->el_state.doingarg = 1;
|
||||
el->el_state.argument *= 4;
|
||||
return (CC_ARGHACK);
|
||||
}
|
||||
|
||||
|
||||
/* em_meta_next():
|
||||
* Add 8th bit to next character typed
|
||||
* [<ESC>]
|
||||
*/
|
||||
protected el_action_t
|
||||
/*ARGSUSED*/
|
||||
em_meta_next(EditLine *el, int c)
|
||||
{
|
||||
|
||||
el->el_state.metanext = 1;
|
||||
return (CC_ARGHACK);
|
||||
}
|
||||
|
||||
|
||||
/* em_toggle_overwrite():
|
||||
* Switch from insert to overwrite mode or vice versa
|
||||
*/
|
||||
protected el_action_t
|
||||
/*ARGSUSED*/
|
||||
em_toggle_overwrite(EditLine *el, int c)
|
||||
{
|
||||
|
||||
el->el_state.inputmode = (el->el_state.inputmode == MODE_INSERT) ?
|
||||
MODE_REPLACE : MODE_INSERT;
|
||||
return (CC_NORM);
|
||||
}
|
||||
|
||||
|
||||
/* em_copy_prev_word():
|
||||
* Copy current word to cursor
|
||||
*/
|
||||
protected el_action_t
|
||||
/*ARGSUSED*/
|
||||
em_copy_prev_word(EditLine *el, int c)
|
||||
{
|
||||
char *cp, *oldc, *dp;
|
||||
|
||||
if (el->el_line.cursor == el->el_line.buffer)
|
||||
return (CC_ERROR);
|
||||
|
||||
oldc = el->el_line.cursor;
|
||||
/* does a bounds check */
|
||||
cp = c__prev_word(el->el_line.cursor, el->el_line.buffer,
|
||||
el->el_state.argument, ce__isword);
|
||||
|
||||
c_insert(el, oldc - cp);
|
||||
for (dp = oldc; cp < oldc && dp < el->el_line.lastchar; cp++)
|
||||
*dp++ = *cp;
|
||||
|
||||
el->el_line.cursor = dp;/* put cursor at end */
|
||||
|
||||
return (CC_REFRESH);
|
||||
}
|
||||
|
||||
|
||||
/* em_inc_search_next():
|
||||
* Emacs incremental next search
|
||||
*/
|
||||
protected el_action_t
|
||||
/*ARGSUSED*/
|
||||
em_inc_search_next(EditLine *el, int c)
|
||||
{
|
||||
|
||||
el->el_search.patlen = 0;
|
||||
return (ce_inc_search(el, ED_SEARCH_NEXT_HISTORY));
|
||||
}
|
||||
|
||||
|
||||
/* em_inc_search_prev():
|
||||
* Emacs incremental reverse search
|
||||
*/
|
||||
protected el_action_t
|
||||
/*ARGSUSED*/
|
||||
em_inc_search_prev(EditLine *el, int c)
|
||||
{
|
||||
|
||||
el->el_search.patlen = 0;
|
||||
return (ce_inc_search(el, ED_SEARCH_PREV_HISTORY));
|
||||
}
|
@@ -1,197 +0,0 @@
|
||||
/* $NetBSD: hist.c,v 1.10 2002/03/18 16:00:53 christos Exp $ */
|
||||
|
||||
/*-
|
||||
* Copyright (c) 1992, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* This code is derived from software contributed to Berkeley by
|
||||
* Christos Zoulas of Cornell University.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
* 3. All advertising materials mentioning features or use of this software
|
||||
* must display the following acknowledgement:
|
||||
* This product includes software developed by the University of
|
||||
* California, Berkeley and its contributors.
|
||||
* 4. Neither the name of the University nor the names of its contributors
|
||||
* may be used to endorse or promote products derived from this software
|
||||
* without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
|
||||
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
* ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
|
||||
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
|
||||
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*/
|
||||
|
||||
#include "config.h"
|
||||
#if !defined(lint) && !defined(SCCSID)
|
||||
#if 0
|
||||
static char sccsid[] = "@(#)hist.c 8.1 (Berkeley) 6/4/93";
|
||||
#else
|
||||
__RCSID("$NetBSD: hist.c,v 1.10 2002/03/18 16:00:53 christos Exp $");
|
||||
#endif
|
||||
#endif /* not lint && not SCCSID */
|
||||
|
||||
/*
|
||||
* hist.c: History access functions
|
||||
*/
|
||||
#include <stdlib.h>
|
||||
#include "el.h"
|
||||
|
||||
/* hist_init():
|
||||
* Initialization function.
|
||||
*/
|
||||
protected int
|
||||
hist_init(EditLine *el)
|
||||
{
|
||||
|
||||
el->el_history.fun = NULL;
|
||||
el->el_history.ref = NULL;
|
||||
el->el_history.buf = (char *) el_malloc(EL_BUFSIZ);
|
||||
el->el_history.sz = EL_BUFSIZ;
|
||||
if (el->el_history.buf == NULL)
|
||||
return (-1);
|
||||
el->el_history.last = el->el_history.buf;
|
||||
return (0);
|
||||
}
|
||||
|
||||
|
||||
/* hist_end():
|
||||
* clean up history;
|
||||
*/
|
||||
protected void
|
||||
hist_end(EditLine *el)
|
||||
{
|
||||
|
||||
el_free((ptr_t) el->el_history.buf);
|
||||
el->el_history.buf = NULL;
|
||||
}
|
||||
|
||||
|
||||
/* hist_set():
|
||||
* Set new history interface
|
||||
*/
|
||||
protected int
|
||||
hist_set(EditLine *el, hist_fun_t fun, ptr_t ptr)
|
||||
{
|
||||
|
||||
el->el_history.ref = ptr;
|
||||
el->el_history.fun = fun;
|
||||
return (0);
|
||||
}
|
||||
|
||||
|
||||
/* hist_get():
|
||||
* Get a history line and update it in the buffer.
|
||||
* eventno tells us the event to get.
|
||||
*/
|
||||
protected el_action_t
|
||||
hist_get(EditLine *el)
|
||||
{
|
||||
const char *hp;
|
||||
int h;
|
||||
|
||||
if (el->el_history.eventno == 0) { /* if really the current line */
|
||||
(void) strncpy(el->el_line.buffer, el->el_history.buf,
|
||||
el->el_history.sz - 1);
|
||||
el->el_line.lastchar = el->el_line.buffer +
|
||||
(el->el_history.last - el->el_history.buf);
|
||||
|
||||
#ifdef KSHVI
|
||||
if (el->el_map.type == MAP_VI)
|
||||
el->el_line.cursor = el->el_line.buffer;
|
||||
else
|
||||
#endif /* KSHVI */
|
||||
el->el_line.cursor = el->el_line.lastchar;
|
||||
|
||||
return (CC_REFRESH);
|
||||
}
|
||||
if (el->el_history.ref == NULL)
|
||||
return (CC_ERROR);
|
||||
|
||||
hp = HIST_FIRST(el);
|
||||
|
||||
if (hp == NULL)
|
||||
return (CC_ERROR);
|
||||
|
||||
for (h = 1; h < el->el_history.eventno; h++)
|
||||
if ((hp = HIST_NEXT(el)) == NULL) {
|
||||
el->el_history.eventno = h;
|
||||
return (CC_ERROR);
|
||||
}
|
||||
(void) strncpy(el->el_line.buffer, hp,
|
||||
(size_t)(el->el_line.limit - el->el_line.buffer));
|
||||
el->el_line.lastchar = el->el_line.buffer + strlen(el->el_line.buffer);
|
||||
|
||||
if (el->el_line.lastchar > el->el_line.buffer) {
|
||||
if (el->el_line.lastchar[-1] == '\n')
|
||||
el->el_line.lastchar--;
|
||||
if ((el->el_line.lastchar > el->el_line.buffer)&&(el->el_line.lastchar[-1] == ' ')) /* bill heckel */
|
||||
el->el_line.lastchar--;
|
||||
if (el->el_line.lastchar < el->el_line.buffer)
|
||||
el->el_line.lastchar = el->el_line.buffer;
|
||||
}
|
||||
#ifdef KSHVI
|
||||
if (el->el_map.type == MAP_VI)
|
||||
el->el_line.cursor = el->el_line.buffer;
|
||||
else
|
||||
#endif /* KSHVI */
|
||||
el->el_line.cursor = el->el_line.lastchar;
|
||||
|
||||
return (CC_REFRESH);
|
||||
}
|
||||
|
||||
|
||||
/* hist_list()
|
||||
* List history entries
|
||||
*/
|
||||
protected int
|
||||
/*ARGSUSED*/
|
||||
hist_list(EditLine *el, int argc, const char **argv)
|
||||
{
|
||||
const char *str;
|
||||
|
||||
if (el->el_history.ref == NULL)
|
||||
return (-1);
|
||||
for (str = HIST_LAST(el); str != NULL; str = HIST_PREV(el))
|
||||
(void) fprintf(el->el_outfile, "%d %s",
|
||||
el->el_history.ev.num, str);
|
||||
return (0);
|
||||
}
|
||||
|
||||
/* hist_enlargebuf()
|
||||
* Enlarge history buffer to specified value. Called from el_enlargebufs().
|
||||
* Return 0 for failure, 1 for success.
|
||||
*/
|
||||
protected int
|
||||
/*ARGSUSED*/
|
||||
hist_enlargebuf(EditLine *el, size_t oldsz, size_t newsz)
|
||||
{
|
||||
char *newbuf;
|
||||
|
||||
newbuf = realloc(el->el_history.buf, newsz);
|
||||
if (!newbuf)
|
||||
return 0;
|
||||
|
||||
(void) memset(&newbuf[oldsz], '\0', newsz - oldsz);
|
||||
|
||||
el->el_history.last = newbuf +
|
||||
(el->el_history.last - el->el_history.buf);
|
||||
el->el_history.buf = newbuf;
|
||||
el->el_history.sz = newsz;
|
||||
|
||||
return 1;
|
||||
}
|
@@ -1,80 +0,0 @@
|
||||
/* $NetBSD: hist.h,v 1.7 2002/03/18 16:00:53 christos Exp $ */
|
||||
|
||||
/*-
|
||||
* Copyright (c) 1992, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* This code is derived from software contributed to Berkeley by
|
||||
* Christos Zoulas of Cornell University.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
* 3. All advertising materials mentioning features or use of this software
|
||||
* must display the following acknowledgement:
|
||||
* This product includes software developed by the University of
|
||||
* California, Berkeley and its contributors.
|
||||
* 4. Neither the name of the University nor the names of its contributors
|
||||
* may be used to endorse or promote products derived from this software
|
||||
* without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
|
||||
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
* ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
|
||||
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
|
||||
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* @(#)hist.h 8.1 (Berkeley) 6/4/93
|
||||
*/
|
||||
|
||||
/*
|
||||
* el.hist.c: History functions
|
||||
*/
|
||||
#ifndef _h_el_hist
|
||||
#define _h_el_hist
|
||||
|
||||
#include "histedit.h"
|
||||
|
||||
typedef int (*hist_fun_t)(ptr_t, HistEvent *, int, ...);
|
||||
|
||||
typedef struct el_history_t {
|
||||
char *buf; /* The history buffer */
|
||||
size_t sz; /* Size of history buffer */
|
||||
char *last; /* The last character */
|
||||
int eventno; /* Event we are looking for */
|
||||
ptr_t ref; /* Argument for history fcns */
|
||||
hist_fun_t fun; /* Event access */
|
||||
HistEvent ev; /* Event cookie */
|
||||
} el_history_t;
|
||||
|
||||
#define HIST_FUN(el, fn, arg) \
|
||||
((((*(el)->el_history.fun) ((el)->el_history.ref, &(el)->el_history.ev, \
|
||||
fn, arg)) == -1) ? NULL : (el)->el_history.ev.str)
|
||||
|
||||
#define HIST_NEXT(el) HIST_FUN(el, H_NEXT, NULL)
|
||||
#define HIST_FIRST(el) HIST_FUN(el, H_FIRST, NULL)
|
||||
#define HIST_LAST(el) HIST_FUN(el, H_LAST, NULL)
|
||||
#define HIST_PREV(el) HIST_FUN(el, H_PREV, NULL)
|
||||
#define HIST_EVENT(el, num) HIST_FUN(el, H_EVENT, num)
|
||||
#define HIST_LOAD(el, fname) HIST_FUN(el, H_LOAD fname)
|
||||
#define HIST_SAVE(el, fname) HIST_FUN(el, H_SAVE fname)
|
||||
|
||||
protected int hist_init(EditLine *);
|
||||
protected void hist_end(EditLine *);
|
||||
protected el_action_t hist_get(EditLine *);
|
||||
protected int hist_set(EditLine *, hist_fun_t, ptr_t);
|
||||
protected int hist_list(EditLine *, int, const char **);
|
||||
protected int hist_enlargebuf(EditLine *, size_t, size_t);
|
||||
|
||||
#endif /* _h_el_hist */
|
@@ -1,197 +0,0 @@
|
||||
/* $NetBSD: histedit.h,v 1.19 2002/03/18 16:00:54 christos Exp $ */
|
||||
|
||||
/*-
|
||||
* Copyright (c) 1992, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* This code is derived from software contributed to Berkeley by
|
||||
* Christos Zoulas of Cornell University.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
* 3. All advertising materials mentioning features or use of this software
|
||||
* must display the following acknowledgement:
|
||||
* This product includes software developed by the University of
|
||||
* California, Berkeley and its contributors.
|
||||
* 4. Neither the name of the University nor the names of its contributors
|
||||
* may be used to endorse or promote products derived from this software
|
||||
* without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
|
||||
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
* ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
|
||||
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
|
||||
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* @(#)histedit.h 8.2 (Berkeley) 1/3/94
|
||||
*/
|
||||
|
||||
/*
|
||||
* histedit.h: Line editor and history interface.
|
||||
*/
|
||||
#ifndef _HISTEDIT_H_
|
||||
#define _HISTEDIT_H_
|
||||
|
||||
#define LIBEDIT_MAJOR 2
|
||||
#define LIBEDIT_MINOR 6
|
||||
|
||||
#include <sys/types.h>
|
||||
#include <stdio.h>
|
||||
|
||||
/*
|
||||
* ==== Editing ====
|
||||
*/
|
||||
typedef struct editline EditLine;
|
||||
|
||||
/*
|
||||
* For user-defined function interface
|
||||
*/
|
||||
typedef struct lineinfo {
|
||||
char *buffer;
|
||||
char *cursor;
|
||||
char *lastchar;
|
||||
} LineInfo;
|
||||
|
||||
|
||||
/*
|
||||
* EditLine editor function return codes.
|
||||
* For user-defined function interface
|
||||
*/
|
||||
#define CC_NORM 0
|
||||
#define CC_NEWLINE 1
|
||||
#define CC_EOF 2
|
||||
#define CC_ARGHACK 3
|
||||
#define CC_REFRESH 4
|
||||
#define CC_CURSOR 5
|
||||
#define CC_ERROR 6
|
||||
#define CC_FATAL 7
|
||||
#define CC_REDISPLAY 8
|
||||
#define CC_REFRESH_BEEP 9
|
||||
|
||||
/*
|
||||
* Initialization, cleanup, and resetting
|
||||
*/
|
||||
EditLine *el_init(const char *, FILE *, FILE *, FILE *);
|
||||
void el_reset(EditLine *);
|
||||
void el_end(EditLine *);
|
||||
|
||||
|
||||
/*
|
||||
* Get a line, a character or push a string back in the input queue
|
||||
*/
|
||||
const char *el_gets(EditLine *, int *);
|
||||
int el_getc(EditLine *, char *);
|
||||
void el_push(EditLine *, char *);
|
||||
|
||||
/*
|
||||
* Beep!
|
||||
*/
|
||||
void el_beep(EditLine *);
|
||||
|
||||
/*
|
||||
* High level function internals control
|
||||
* Parses argc, argv array and executes builtin editline commands
|
||||
*/
|
||||
int el_parse(EditLine *, int, const char **);
|
||||
|
||||
/*
|
||||
* Low level editline access functions
|
||||
*/
|
||||
int el_set(EditLine *, int, ...);
|
||||
int el_get(EditLine *, int, void *);
|
||||
|
||||
/*
|
||||
* el_set/el_get parameters
|
||||
*/
|
||||
#define EL_PROMPT 0 /* , el_pfunc_t); */
|
||||
#define EL_TERMINAL 1 /* , const char *); */
|
||||
#define EL_EDITOR 2 /* , const char *); */
|
||||
#define EL_SIGNAL 3 /* , int); */
|
||||
#define EL_BIND 4 /* , const char *, ..., NULL); */
|
||||
#define EL_TELLTC 5 /* , const char *, ..., NULL); */
|
||||
#define EL_SETTC 6 /* , const char *, ..., NULL); */
|
||||
#define EL_ECHOTC 7 /* , const char *, ..., NULL); */
|
||||
#define EL_SETTY 8 /* , const char *, ..., NULL); */
|
||||
#define EL_ADDFN 9 /* , const char *, const char * */
|
||||
/* , el_func_t); */
|
||||
#define EL_HIST 10 /* , hist_fun_t, const char *); */
|
||||
#define EL_EDITMODE 11 /* , int); */
|
||||
#define EL_RPROMPT 12 /* , el_pfunc_t); */
|
||||
#define EL_GETCFN 13 /* , el_rfunc_t); */
|
||||
#define EL_CLIENTDATA 14 /* , void *); */
|
||||
|
||||
#define EL_BUILTIN_GETCFN (NULL)
|
||||
|
||||
/*
|
||||
* Source named file or $PWD/.editrc or $HOME/.editrc
|
||||
*/
|
||||
int el_source(EditLine *, const char *);
|
||||
|
||||
/*
|
||||
* Must be called when the terminal changes size; If EL_SIGNAL
|
||||
* is set this is done automatically otherwise it is the responsibility
|
||||
* of the application
|
||||
*/
|
||||
void el_resize(EditLine *);
|
||||
|
||||
|
||||
/*
|
||||
* User-defined function interface.
|
||||
*/
|
||||
const LineInfo *el_line(EditLine *);
|
||||
int el_insertstr(EditLine *, const char *);
|
||||
void el_deletestr(EditLine *, int);
|
||||
|
||||
/*
|
||||
* ==== History ====
|
||||
*/
|
||||
|
||||
typedef struct history History;
|
||||
|
||||
typedef struct HistEvent {
|
||||
int num;
|
||||
const char *str;
|
||||
} HistEvent;
|
||||
|
||||
/*
|
||||
* History access functions.
|
||||
*/
|
||||
History * history_init(void);
|
||||
void history_end(History *);
|
||||
|
||||
int history(History *, HistEvent *, int, ...);
|
||||
|
||||
#define H_FUNC 0 /* , UTSL */
|
||||
#define H_SETSIZE 1 /* , const int); */
|
||||
#define H_GETSIZE 2 /* , void); */
|
||||
#define H_FIRST 3 /* , void); */
|
||||
#define H_LAST 4 /* , void); */
|
||||
#define H_PREV 5 /* , void); */
|
||||
#define H_NEXT 6 /* , void); */
|
||||
#define H_CURR 8 /* , const int); */
|
||||
#define H_SET 7 /* , void); */
|
||||
#define H_ADD 9 /* , const char *); */
|
||||
#define H_ENTER 10 /* , const char *); */
|
||||
#define H_APPEND 11 /* , const char *); */
|
||||
#define H_END 12 /* , void); */
|
||||
#define H_NEXT_STR 13 /* , const char *); */
|
||||
#define H_PREV_STR 14 /* , const char *); */
|
||||
#define H_NEXT_EVENT 15 /* , const int); */
|
||||
#define H_PREV_EVENT 16 /* , const int); */
|
||||
#define H_LOAD 17 /* , const char *); */
|
||||
#define H_SAVE 18 /* , const char *); */
|
||||
#define H_CLEAR 19 /* , void); */
|
||||
|
||||
#endif /* _HISTEDIT_H_ */
|
@@ -1,875 +0,0 @@
|
||||
/* $NetBSD: history.c,v 1.19 2002/03/18 16:00:54 christos Exp $ */
|
||||
|
||||
/*-
|
||||
* Copyright (c) 1992, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* This code is derived from software contributed to Berkeley by
|
||||
* Christos Zoulas of Cornell University.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
* 3. All advertising materials mentioning features or use of this software
|
||||
* must display the following acknowledgement:
|
||||
* This product includes software developed by the University of
|
||||
* California, Berkeley and its contributors.
|
||||
* 4. Neither the name of the University nor the names of its contributors
|
||||
* may be used to endorse or promote products derived from this software
|
||||
* without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
|
||||
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
* ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
|
||||
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
|
||||
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*/
|
||||
|
||||
#include "config.h"
|
||||
#if !defined(lint) && !defined(SCCSID)
|
||||
#if 0
|
||||
static char sccsid[] = "@(#)history.c 8.1 (Berkeley) 6/4/93";
|
||||
#else
|
||||
__RCSID("$NetBSD: history.c,v 1.19 2002/03/18 16:00:54 christos Exp $");
|
||||
#endif
|
||||
#endif /* not lint && not SCCSID */
|
||||
|
||||
/*
|
||||
* hist.c: History access functions
|
||||
*/
|
||||
#include <string.h>
|
||||
#include <stdlib.h>
|
||||
#include <stdarg.h>
|
||||
#ifdef HAVE_VIS_H
|
||||
#include <vis.h>
|
||||
#else
|
||||
#include "np/vis.h"
|
||||
#endif
|
||||
#include <sys/stat.h>
|
||||
|
||||
static const char hist_cookie[] = "_HiStOrY_V2_\n";
|
||||
|
||||
#include "histedit.h"
|
||||
|
||||
typedef int (*history_gfun_t)(ptr_t, HistEvent *);
|
||||
typedef int (*history_efun_t)(ptr_t, HistEvent *, const char *);
|
||||
typedef void (*history_vfun_t)(ptr_t, HistEvent *);
|
||||
typedef int (*history_sfun_t)(ptr_t, HistEvent *, const int);
|
||||
|
||||
struct history {
|
||||
ptr_t h_ref; /* Argument for history fcns */
|
||||
int h_ent; /* Last entry point for history */
|
||||
history_gfun_t h_first; /* Get the first element */
|
||||
history_gfun_t h_next; /* Get the next element */
|
||||
history_gfun_t h_last; /* Get the last element */
|
||||
history_gfun_t h_prev; /* Get the previous element */
|
||||
history_gfun_t h_curr; /* Get the current element */
|
||||
history_sfun_t h_set; /* Set the current element */
|
||||
history_vfun_t h_clear; /* Clear the history list */
|
||||
history_efun_t h_enter; /* Add an element */
|
||||
history_efun_t h_add; /* Append to an element */
|
||||
};
|
||||
#define HNEXT(h, ev) (*(h)->h_next)((h)->h_ref, ev)
|
||||
#define HFIRST(h, ev) (*(h)->h_first)((h)->h_ref, ev)
|
||||
#define HPREV(h, ev) (*(h)->h_prev)((h)->h_ref, ev)
|
||||
#define HLAST(h, ev) (*(h)->h_last)((h)->h_ref, ev)
|
||||
#define HCURR(h, ev) (*(h)->h_curr)((h)->h_ref, ev)
|
||||
#define HSET(h, ev, n) (*(h)->h_set)((h)->h_ref, ev, n)
|
||||
#define HCLEAR(h, ev) (*(h)->h_clear)((h)->h_ref, ev)
|
||||
#define HENTER(h, ev, str) (*(h)->h_enter)((h)->h_ref, ev, str)
|
||||
#define HADD(h, ev, str) (*(h)->h_add)((h)->h_ref, ev, str)
|
||||
|
||||
#define h_malloc(a) malloc(a)
|
||||
#define h_realloc(a, b) realloc((a), (b))
|
||||
#define h_free(a) free(a)
|
||||
|
||||
typedef struct {
|
||||
int num;
|
||||
char *str;
|
||||
} HistEventPrivate;
|
||||
|
||||
|
||||
|
||||
private int history_setsize(History *, HistEvent *, int);
|
||||
private int history_getsize(History *, HistEvent *);
|
||||
private int history_set_fun(History *, History *);
|
||||
private int history_load(History *, const char *);
|
||||
private int history_save(History *, const char *);
|
||||
private int history_prev_event(History *, HistEvent *, int);
|
||||
private int history_next_event(History *, HistEvent *, int);
|
||||
private int history_next_string(History *, HistEvent *, const char *);
|
||||
private int history_prev_string(History *, HistEvent *, const char *);
|
||||
|
||||
|
||||
/***********************************************************************/
|
||||
|
||||
/*
|
||||
* Builtin- history implementation
|
||||
*/
|
||||
typedef struct hentry_t {
|
||||
HistEvent ev; /* What we return */
|
||||
struct hentry_t *next; /* Next entry */
|
||||
struct hentry_t *prev; /* Previous entry */
|
||||
} hentry_t;
|
||||
|
||||
typedef struct history_t {
|
||||
hentry_t list; /* Fake list header element */
|
||||
hentry_t *cursor; /* Current element in the list */
|
||||
int max; /* Maximum number of events */
|
||||
int cur; /* Current number of events */
|
||||
int eventid; /* For generation of unique event id */
|
||||
} history_t;
|
||||
|
||||
private int history_def_first(ptr_t, HistEvent *);
|
||||
private int history_def_last(ptr_t, HistEvent *);
|
||||
private int history_def_next(ptr_t, HistEvent *);
|
||||
private int history_def_prev(ptr_t, HistEvent *);
|
||||
private int history_def_curr(ptr_t, HistEvent *);
|
||||
private int history_def_set(ptr_t, HistEvent *, const int n);
|
||||
private int history_def_enter(ptr_t, HistEvent *, const char *);
|
||||
private int history_def_add(ptr_t, HistEvent *, const char *);
|
||||
private void history_def_init(ptr_t *, HistEvent *, int);
|
||||
private void history_def_clear(ptr_t, HistEvent *);
|
||||
private int history_def_insert(history_t *, HistEvent *, const char *);
|
||||
private void history_def_delete(history_t *, HistEvent *, hentry_t *);
|
||||
|
||||
#define history_def_setsize(p, num)(void) (((history_t *) p)->max = (num))
|
||||
#define history_def_getsize(p) (((history_t *) p)->cur)
|
||||
|
||||
#define he_strerror(code) he_errlist[code]
|
||||
#define he_seterrev(evp, code) {\
|
||||
evp->num = code;\
|
||||
evp->str = he_strerror(code);\
|
||||
}
|
||||
|
||||
/* error messages */
|
||||
static const char *const he_errlist[] = {
|
||||
"OK",
|
||||
"unknown error",
|
||||
"malloc() failed",
|
||||
"first event not found",
|
||||
"last event not found",
|
||||
"empty list",
|
||||
"no next event",
|
||||
"no previous event",
|
||||
"current event is invalid",
|
||||
"event not found",
|
||||
"can't read history from file",
|
||||
"can't write history",
|
||||
"required parameter(s) not supplied",
|
||||
"history size negative",
|
||||
"function not allowed with other history-functions-set the default",
|
||||
"bad parameters"
|
||||
};
|
||||
/* error codes */
|
||||
#define _HE_OK 0
|
||||
#define _HE_UNKNOWN 1
|
||||
#define _HE_MALLOC_FAILED 2
|
||||
#define _HE_FIRST_NOTFOUND 3
|
||||
#define _HE_LAST_NOTFOUND 4
|
||||
#define _HE_EMPTY_LIST 5
|
||||
#define _HE_END_REACHED 6
|
||||
#define _HE_START_REACHED 7
|
||||
#define _HE_CURR_INVALID 8
|
||||
#define _HE_NOT_FOUND 9
|
||||
#define _HE_HIST_READ 10
|
||||
#define _HE_HIST_WRITE 11
|
||||
#define _HE_PARAM_MISSING 12
|
||||
#define _HE_SIZE_NEGATIVE 13
|
||||
#define _HE_NOT_ALLOWED 14
|
||||
#define _HE_BAD_PARAM 15
|
||||
|
||||
/* history_def_first():
|
||||
* Default function to return the first event in the history.
|
||||
*/
|
||||
private int
|
||||
history_def_first(ptr_t p, HistEvent *ev)
|
||||
{
|
||||
history_t *h = (history_t *) p;
|
||||
|
||||
h->cursor = h->list.next;
|
||||
if (h->cursor != &h->list)
|
||||
*ev = h->cursor->ev;
|
||||
else {
|
||||
he_seterrev(ev, _HE_FIRST_NOTFOUND);
|
||||
return (-1);
|
||||
}
|
||||
|
||||
return (0);
|
||||
}
|
||||
|
||||
|
||||
/* history_def_last():
|
||||
* Default function to return the last event in the history.
|
||||
*/
|
||||
private int
|
||||
history_def_last(ptr_t p, HistEvent *ev)
|
||||
{
|
||||
history_t *h = (history_t *) p;
|
||||
|
||||
h->cursor = h->list.prev;
|
||||
if (h->cursor != &h->list)
|
||||
*ev = h->cursor->ev;
|
||||
else {
|
||||
he_seterrev(ev, _HE_LAST_NOTFOUND);
|
||||
return (-1);
|
||||
}
|
||||
|
||||
return (0);
|
||||
}
|
||||
|
||||
|
||||
/* history_def_next():
|
||||
* Default function to return the next event in the history.
|
||||
*/
|
||||
private int
|
||||
history_def_next(ptr_t p, HistEvent *ev)
|
||||
{
|
||||
history_t *h = (history_t *) p;
|
||||
|
||||
if (h->cursor != &h->list)
|
||||
h->cursor = h->cursor->next;
|
||||
else {
|
||||
he_seterrev(ev, _HE_EMPTY_LIST);
|
||||
return (-1);
|
||||
}
|
||||
|
||||
if (h->cursor != &h->list)
|
||||
*ev = h->cursor->ev;
|
||||
else {
|
||||
he_seterrev(ev, _HE_END_REACHED);
|
||||
return (-1);
|
||||
}
|
||||
|
||||
return (0);
|
||||
}
|
||||
|
||||
|
||||
/* history_def_prev():
|
||||
* Default function to return the previous event in the history.
|
||||
*/
|
||||
private int
|
||||
history_def_prev(ptr_t p, HistEvent *ev)
|
||||
{
|
||||
history_t *h = (history_t *) p;
|
||||
|
||||
if (h->cursor != &h->list)
|
||||
h->cursor = h->cursor->prev;
|
||||
else {
|
||||
he_seterrev(ev,
|
||||
(h->cur > 0) ? _HE_END_REACHED : _HE_EMPTY_LIST);
|
||||
return (-1);
|
||||
}
|
||||
|
||||
if (h->cursor != &h->list)
|
||||
*ev = h->cursor->ev;
|
||||
else {
|
||||
he_seterrev(ev, _HE_START_REACHED);
|
||||
return (-1);
|
||||
}
|
||||
|
||||
return (0);
|
||||
}
|
||||
|
||||
|
||||
/* history_def_curr():
|
||||
* Default function to return the current event in the history.
|
||||
*/
|
||||
private int
|
||||
history_def_curr(ptr_t p, HistEvent *ev)
|
||||
{
|
||||
history_t *h = (history_t *) p;
|
||||
|
||||
if (h->cursor != &h->list)
|
||||
*ev = h->cursor->ev;
|
||||
else {
|
||||
he_seterrev(ev,
|
||||
(h->cur > 0) ? _HE_CURR_INVALID : _HE_EMPTY_LIST);
|
||||
return (-1);
|
||||
}
|
||||
|
||||
return (0);
|
||||
}
|
||||
|
||||
|
||||
/* history_def_set():
|
||||
* Default function to set the current event in the history to the
|
||||
* given one.
|
||||
*/
|
||||
private int
|
||||
history_def_set(ptr_t p, HistEvent *ev, const int n)
|
||||
{
|
||||
history_t *h = (history_t *) p;
|
||||
|
||||
if (h->cur == 0) {
|
||||
he_seterrev(ev, _HE_EMPTY_LIST);
|
||||
return (-1);
|
||||
}
|
||||
if (h->cursor == &h->list || h->cursor->ev.num != n) {
|
||||
for (h->cursor = h->list.next; h->cursor != &h->list;
|
||||
h->cursor = h->cursor->next)
|
||||
if (h->cursor->ev.num == n)
|
||||
break;
|
||||
}
|
||||
if (h->cursor == &h->list) {
|
||||
he_seterrev(ev, _HE_NOT_FOUND);
|
||||
return (-1);
|
||||
}
|
||||
return (0);
|
||||
}
|
||||
|
||||
|
||||
/* history_def_add():
|
||||
* Append string to element
|
||||
*/
|
||||
private int
|
||||
history_def_add(ptr_t p, HistEvent *ev, const char *str)
|
||||
{
|
||||
history_t *h = (history_t *) p;
|
||||
size_t len;
|
||||
char *s;
|
||||
HistEventPrivate *evp = (void *)&h->cursor->ev;
|
||||
|
||||
if (h->cursor == &h->list)
|
||||
return (history_def_enter(p, ev, str));
|
||||
len = strlen(evp->str) + strlen(str) + 1;
|
||||
s = (char *) h_malloc(len);
|
||||
if (!s) {
|
||||
he_seterrev(ev, _HE_MALLOC_FAILED);
|
||||
return (-1);
|
||||
}
|
||||
(void) strlcpy(s, h->cursor->ev.str, len);
|
||||
(void) strlcat(s, str, len);
|
||||
h_free(evp->str);
|
||||
evp->str = s;
|
||||
*ev = h->cursor->ev;
|
||||
return (0);
|
||||
}
|
||||
|
||||
|
||||
/* history_def_delete():
|
||||
* Delete element hp of the h list
|
||||
*/
|
||||
/* ARGSUSED */
|
||||
private void
|
||||
history_def_delete(history_t *h, HistEvent *ev, hentry_t *hp)
|
||||
{
|
||||
HistEventPrivate *evp = (void *)&hp->ev;
|
||||
if (hp == &h->list)
|
||||
abort();
|
||||
hp->prev->next = hp->next;
|
||||
hp->next->prev = hp->prev;
|
||||
h_free((ptr_t) evp->str);
|
||||
h_free(hp);
|
||||
h->cur--;
|
||||
}
|
||||
|
||||
|
||||
/* history_def_insert():
|
||||
* Insert element with string str in the h list
|
||||
*/
|
||||
private int
|
||||
history_def_insert(history_t *h, HistEvent *ev, const char *str)
|
||||
{
|
||||
|
||||
h->cursor = (hentry_t *) h_malloc(sizeof(hentry_t));
|
||||
if (h->cursor)
|
||||
h->cursor->ev.str = strdup(str);
|
||||
if (!h->cursor || !h->cursor->ev.str) {
|
||||
he_seterrev(ev, _HE_MALLOC_FAILED);
|
||||
return (-1);
|
||||
}
|
||||
h->cursor->ev.num = ++h->eventid;
|
||||
h->cursor->next = h->list.next;
|
||||
h->cursor->prev = &h->list;
|
||||
h->list.next->prev = h->cursor;
|
||||
h->list.next = h->cursor;
|
||||
h->cur++;
|
||||
|
||||
*ev = h->cursor->ev;
|
||||
return (0);
|
||||
}
|
||||
|
||||
|
||||
/* history_def_enter():
|
||||
* Default function to enter an item in the history
|
||||
*/
|
||||
private int
|
||||
history_def_enter(ptr_t p, HistEvent *ev, const char *str)
|
||||
{
|
||||
history_t *h = (history_t *) p;
|
||||
|
||||
if (history_def_insert(h, ev, str) == -1)
|
||||
return (-1); /* error, keep error message */
|
||||
|
||||
/*
|
||||
* Always keep at least one entry.
|
||||
* This way we don't have to check for the empty list.
|
||||
*/
|
||||
while (h->cur > h->max && h->cur > 0)
|
||||
history_def_delete(h, ev, h->list.prev);
|
||||
|
||||
return (0);
|
||||
}
|
||||
|
||||
|
||||
/* history_def_init():
|
||||
* Default history initialization function
|
||||
*/
|
||||
/* ARGSUSED */
|
||||
private void
|
||||
history_def_init(ptr_t *p, HistEvent *ev, int n)
|
||||
{
|
||||
history_t *h = (history_t *) h_malloc(sizeof(history_t));
|
||||
|
||||
if (n <= 0)
|
||||
n = 0;
|
||||
h->eventid = 0;
|
||||
h->cur = 0;
|
||||
h->max = n;
|
||||
h->list.next = h->list.prev = &h->list;
|
||||
h->list.ev.str = NULL;
|
||||
h->list.ev.num = 0;
|
||||
h->cursor = &h->list;
|
||||
*p = (ptr_t) h;
|
||||
}
|
||||
|
||||
|
||||
/* history_def_clear():
|
||||
* Default history cleanup function
|
||||
*/
|
||||
private void
|
||||
history_def_clear(ptr_t p, HistEvent *ev)
|
||||
{
|
||||
history_t *h = (history_t *) p;
|
||||
|
||||
while (h->list.prev != &h->list)
|
||||
history_def_delete(h, ev, h->list.prev);
|
||||
h->eventid = 0;
|
||||
h->cur = 0;
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
/************************************************************************/
|
||||
|
||||
/* history_init():
|
||||
* Initialization function.
|
||||
*/
|
||||
public History *
|
||||
history_init(void)
|
||||
{
|
||||
History *h = (History *) h_malloc(sizeof(History));
|
||||
HistEvent ev;
|
||||
|
||||
history_def_init(&h->h_ref, &ev, 0);
|
||||
h->h_ent = -1;
|
||||
h->h_next = history_def_next;
|
||||
h->h_first = history_def_first;
|
||||
h->h_last = history_def_last;
|
||||
h->h_prev = history_def_prev;
|
||||
h->h_curr = history_def_curr;
|
||||
h->h_set = history_def_set;
|
||||
h->h_clear = history_def_clear;
|
||||
h->h_enter = history_def_enter;
|
||||
h->h_add = history_def_add;
|
||||
|
||||
return (h);
|
||||
}
|
||||
|
||||
|
||||
/* history_end():
|
||||
* clean up history;
|
||||
*/
|
||||
public void
|
||||
history_end(History *h)
|
||||
{
|
||||
HistEvent ev;
|
||||
|
||||
if (h->h_next == history_def_next)
|
||||
history_def_clear(h->h_ref, &ev);
|
||||
}
|
||||
|
||||
|
||||
|
||||
/* history_setsize():
|
||||
* Set history number of events
|
||||
*/
|
||||
private int
|
||||
history_setsize(History *h, HistEvent *ev, int num)
|
||||
{
|
||||
|
||||
if (h->h_next != history_def_next) {
|
||||
he_seterrev(ev, _HE_NOT_ALLOWED);
|
||||
return (-1);
|
||||
}
|
||||
if (num < 0) {
|
||||
he_seterrev(ev, _HE_BAD_PARAM);
|
||||
return (-1);
|
||||
}
|
||||
history_def_setsize(h->h_ref, num);
|
||||
return (0);
|
||||
}
|
||||
|
||||
|
||||
/* history_getsize():
|
||||
* Get number of events currently in history
|
||||
*/
|
||||
private int
|
||||
history_getsize(History *h, HistEvent *ev)
|
||||
{
|
||||
int retval = 0;
|
||||
|
||||
if (h->h_next != history_def_next) {
|
||||
he_seterrev(ev, _HE_NOT_ALLOWED);
|
||||
return (-1);
|
||||
}
|
||||
retval = history_def_getsize(h->h_ref);
|
||||
if (retval < -1) {
|
||||
he_seterrev(ev, _HE_SIZE_NEGATIVE);
|
||||
return (-1);
|
||||
}
|
||||
ev->num = retval;
|
||||
return (0);
|
||||
}
|
||||
|
||||
|
||||
/* history_set_fun():
|
||||
* Set history functions
|
||||
*/
|
||||
private int
|
||||
history_set_fun(History *h, History *nh)
|
||||
{
|
||||
HistEvent ev;
|
||||
|
||||
if (nh->h_first == NULL || nh->h_next == NULL || nh->h_last == NULL ||
|
||||
nh->h_prev == NULL || nh->h_curr == NULL || nh->h_set == NULL ||
|
||||
nh->h_enter == NULL || nh->h_add == NULL || nh->h_clear == NULL ||
|
||||
nh->h_ref == NULL) {
|
||||
if (h->h_next != history_def_next) {
|
||||
history_def_init(&h->h_ref, &ev, 0);
|
||||
h->h_first = history_def_first;
|
||||
h->h_next = history_def_next;
|
||||
h->h_last = history_def_last;
|
||||
h->h_prev = history_def_prev;
|
||||
h->h_curr = history_def_curr;
|
||||
h->h_set = history_def_set;
|
||||
h->h_clear = history_def_clear;
|
||||
h->h_enter = history_def_enter;
|
||||
h->h_add = history_def_add;
|
||||
}
|
||||
return (-1);
|
||||
}
|
||||
if (h->h_next == history_def_next)
|
||||
history_def_clear(h->h_ref, &ev);
|
||||
|
||||
h->h_ent = -1;
|
||||
h->h_first = nh->h_first;
|
||||
h->h_next = nh->h_next;
|
||||
h->h_last = nh->h_last;
|
||||
h->h_prev = nh->h_prev;
|
||||
h->h_curr = nh->h_curr;
|
||||
h->h_set = nh->h_set;
|
||||
h->h_clear = nh->h_clear;
|
||||
h->h_enter = nh->h_enter;
|
||||
h->h_add = nh->h_add;
|
||||
|
||||
return (0);
|
||||
}
|
||||
|
||||
|
||||
/* history_load():
|
||||
* History load function
|
||||
*/
|
||||
private int
|
||||
history_load(History *h, const char *fname)
|
||||
{
|
||||
FILE *fp;
|
||||
char *line;
|
||||
size_t sz, max_size;
|
||||
char *ptr;
|
||||
int i = -1;
|
||||
HistEvent ev;
|
||||
|
||||
if ((fp = fopen(fname, "r")) == NULL)
|
||||
return (i);
|
||||
|
||||
if ((line = fgetln(fp, &sz)) == NULL)
|
||||
goto done;
|
||||
|
||||
if (strncmp(line, hist_cookie, sz) != 0)
|
||||
goto done;
|
||||
|
||||
ptr = h_malloc(max_size = 1024);
|
||||
for (i = 0; (line = fgetln(fp, &sz)) != NULL; i++) {
|
||||
char c = line[sz];
|
||||
|
||||
if (sz != 0 && line[sz - 1] == '\n')
|
||||
line[--sz] = '\0';
|
||||
else
|
||||
line[sz] = '\0';
|
||||
|
||||
if (max_size < sz) {
|
||||
max_size = (sz + 1023) & ~1023;
|
||||
ptr = h_realloc(ptr, max_size);
|
||||
}
|
||||
(void) strunvis(ptr, line);
|
||||
line[sz] = c;
|
||||
HENTER(h, &ev, ptr);
|
||||
}
|
||||
h_free(ptr);
|
||||
|
||||
done:
|
||||
(void) fclose(fp);
|
||||
return (i);
|
||||
}
|
||||
|
||||
|
||||
/* history_save():
|
||||
* History save function
|
||||
*/
|
||||
private int
|
||||
history_save(History *h, const char *fname)
|
||||
{
|
||||
FILE *fp;
|
||||
HistEvent ev;
|
||||
int i = 0, retval;
|
||||
size_t len, max_size;
|
||||
char *ptr;
|
||||
|
||||
if ((fp = fopen(fname, "w")) == NULL)
|
||||
return (-1);
|
||||
|
||||
(void) fchmod(fileno(fp), S_IRUSR|S_IWUSR);
|
||||
(void) fputs(hist_cookie, fp);
|
||||
ptr = h_malloc(max_size = 1024);
|
||||
for (retval = HLAST(h, &ev);
|
||||
retval != -1;
|
||||
retval = HPREV(h, &ev), i++) {
|
||||
len = strlen(ev.str) * 4;
|
||||
if (len >= max_size) {
|
||||
max_size = (len + 1023) & 1023;
|
||||
ptr = h_realloc(ptr, max_size);
|
||||
}
|
||||
(void) strvis(ptr, ev.str, VIS_WHITE);
|
||||
(void) fprintf(fp, "%s\n", ev.str);
|
||||
}
|
||||
h_free(ptr);
|
||||
(void) fclose(fp);
|
||||
return (i);
|
||||
}
|
||||
|
||||
|
||||
/* history_prev_event():
|
||||
* Find the previous event, with number given
|
||||
*/
|
||||
private int
|
||||
history_prev_event(History *h, HistEvent *ev, int num)
|
||||
{
|
||||
int retval;
|
||||
|
||||
for (retval = HCURR(h, ev); retval != -1; retval = HPREV(h, ev))
|
||||
if (ev->num == num)
|
||||
return (0);
|
||||
|
||||
he_seterrev(ev, _HE_NOT_FOUND);
|
||||
return (-1);
|
||||
}
|
||||
|
||||
|
||||
/* history_next_event():
|
||||
* Find the next event, with number given
|
||||
*/
|
||||
private int
|
||||
history_next_event(History *h, HistEvent *ev, int num)
|
||||
{
|
||||
int retval;
|
||||
|
||||
for (retval = HCURR(h, ev); retval != -1; retval = HNEXT(h, ev))
|
||||
if (ev->num == num)
|
||||
return (0);
|
||||
|
||||
he_seterrev(ev, _HE_NOT_FOUND);
|
||||
return (-1);
|
||||
}
|
||||
|
||||
|
||||
/* history_prev_string():
|
||||
* Find the previous event beginning with string
|
||||
*/
|
||||
private int
|
||||
history_prev_string(History *h, HistEvent *ev, const char *str)
|
||||
{
|
||||
size_t len = strlen(str);
|
||||
int retval;
|
||||
|
||||
for (retval = HCURR(h, ev); retval != -1; retval = HNEXT(h, ev))
|
||||
if (strncmp(str, ev->str, len) == 0)
|
||||
return (0);
|
||||
|
||||
he_seterrev(ev, _HE_NOT_FOUND);
|
||||
return (-1);
|
||||
}
|
||||
|
||||
|
||||
/* history_next_string():
|
||||
* Find the next event beginning with string
|
||||
*/
|
||||
private int
|
||||
history_next_string(History *h, HistEvent *ev, const char *str)
|
||||
{
|
||||
size_t len = strlen(str);
|
||||
int retval;
|
||||
|
||||
for (retval = HCURR(h, ev); retval != -1; retval = HPREV(h, ev))
|
||||
if (strncmp(str, ev->str, len) == 0)
|
||||
return (0);
|
||||
|
||||
he_seterrev(ev, _HE_NOT_FOUND);
|
||||
return (-1);
|
||||
}
|
||||
|
||||
|
||||
/* history():
|
||||
* User interface to history functions.
|
||||
*/
|
||||
int
|
||||
history(History *h, HistEvent *ev, int fun, ...)
|
||||
{
|
||||
va_list va;
|
||||
const char *str;
|
||||
int retval;
|
||||
|
||||
va_start(va, fun);
|
||||
|
||||
he_seterrev(ev, _HE_OK);
|
||||
|
||||
switch (fun) {
|
||||
case H_GETSIZE:
|
||||
retval = history_getsize(h, ev);
|
||||
break;
|
||||
|
||||
case H_SETSIZE:
|
||||
retval = history_setsize(h, ev, va_arg(va, int));
|
||||
break;
|
||||
|
||||
case H_ADD:
|
||||
str = va_arg(va, const char *);
|
||||
retval = HADD(h, ev, str);
|
||||
break;
|
||||
|
||||
case H_ENTER:
|
||||
str = va_arg(va, const char *);
|
||||
if ((retval = HENTER(h, ev, str)) != -1)
|
||||
h->h_ent = ev->num;
|
||||
break;
|
||||
|
||||
case H_APPEND:
|
||||
str = va_arg(va, const char *);
|
||||
if ((retval = HSET(h, ev, h->h_ent)) != -1)
|
||||
retval = HADD(h, ev, str);
|
||||
break;
|
||||
|
||||
case H_FIRST:
|
||||
retval = HFIRST(h, ev);
|
||||
break;
|
||||
|
||||
case H_NEXT:
|
||||
retval = HNEXT(h, ev);
|
||||
break;
|
||||
|
||||
case H_LAST:
|
||||
retval = HLAST(h, ev);
|
||||
break;
|
||||
|
||||
case H_PREV:
|
||||
retval = HPREV(h, ev);
|
||||
break;
|
||||
|
||||
case H_CURR:
|
||||
retval = HCURR(h, ev);
|
||||
break;
|
||||
|
||||
case H_SET:
|
||||
retval = HSET(h, ev, va_arg(va, const int));
|
||||
break;
|
||||
|
||||
case H_CLEAR:
|
||||
HCLEAR(h, ev);
|
||||
retval = 0;
|
||||
break;
|
||||
|
||||
case H_LOAD:
|
||||
retval = history_load(h, va_arg(va, const char *));
|
||||
if (retval == -1)
|
||||
he_seterrev(ev, _HE_HIST_READ);
|
||||
break;
|
||||
|
||||
case H_SAVE:
|
||||
retval = history_save(h, va_arg(va, const char *));
|
||||
if (retval == -1)
|
||||
he_seterrev(ev, _HE_HIST_WRITE);
|
||||
break;
|
||||
|
||||
case H_PREV_EVENT:
|
||||
retval = history_prev_event(h, ev, va_arg(va, int));
|
||||
break;
|
||||
|
||||
case H_NEXT_EVENT:
|
||||
retval = history_next_event(h, ev, va_arg(va, int));
|
||||
break;
|
||||
|
||||
case H_PREV_STR:
|
||||
retval = history_prev_string(h, ev, va_arg(va, const char *));
|
||||
break;
|
||||
|
||||
case H_NEXT_STR:
|
||||
retval = history_next_string(h, ev, va_arg(va, const char *));
|
||||
break;
|
||||
|
||||
case H_FUNC:
|
||||
{
|
||||
History hf;
|
||||
|
||||
hf.h_ref = va_arg(va, ptr_t);
|
||||
h->h_ent = -1;
|
||||
hf.h_first = va_arg(va, history_gfun_t);
|
||||
hf.h_next = va_arg(va, history_gfun_t);
|
||||
hf.h_last = va_arg(va, history_gfun_t);
|
||||
hf.h_prev = va_arg(va, history_gfun_t);
|
||||
hf.h_curr = va_arg(va, history_gfun_t);
|
||||
hf.h_set = va_arg(va, history_sfun_t);
|
||||
hf.h_clear = va_arg(va, history_vfun_t);
|
||||
hf.h_enter = va_arg(va, history_efun_t);
|
||||
hf.h_add = va_arg(va, history_efun_t);
|
||||
|
||||
if ((retval = history_set_fun(h, &hf)) == -1)
|
||||
he_seterrev(ev, _HE_PARAM_MISSING);
|
||||
break;
|
||||
}
|
||||
|
||||
case H_END:
|
||||
history_end(h);
|
||||
retval = 0;
|
||||
break;
|
||||
|
||||
default:
|
||||
retval = -1;
|
||||
he_seterrev(ev, _HE_UNKNOWN);
|
||||
break;
|
||||
}
|
||||
va_end(va);
|
||||
return (retval);
|
||||
}
|
@@ -1,250 +0,0 @@
|
||||
#! /bin/sh
|
||||
#
|
||||
# install - install a program, script, or datafile
|
||||
# This comes from X11R5 (mit/util/scripts/install.sh).
|
||||
#
|
||||
# Copyright 1991 by the Massachusetts Institute of Technology
|
||||
#
|
||||
# Permission to use, copy, modify, distribute, and sell this software and its
|
||||
# documentation for any purpose is hereby granted without fee, provided that
|
||||
# the above copyright notice appear in all copies and that both that
|
||||
# copyright notice and this permission notice appear in supporting
|
||||
# documentation, and that the name of M.I.T. not be used in advertising or
|
||||
# publicity pertaining to distribution of the software without specific,
|
||||
# written prior permission. M.I.T. makes no representations about the
|
||||
# suitability of this software for any purpose. It is provided "as is"
|
||||
# without express or implied warranty.
|
||||
#
|
||||
# Calling this script install-sh is preferred over install.sh, to prevent
|
||||
# `make' implicit rules from creating a file called install from it
|
||||
# when there is no Makefile.
|
||||
#
|
||||
# This script is compatible with the BSD install script, but was written
|
||||
# from scratch. It can only install one file at a time, a restriction
|
||||
# shared with many OS's install programs.
|
||||
|
||||
|
||||
# set DOITPROG to echo to test this script
|
||||
|
||||
# Don't use :- since 4.3BSD and earlier shells don't like it.
|
||||
doit="${DOITPROG-}"
|
||||
|
||||
|
||||
# put in absolute paths if you don't have them in your path; or use env. vars.
|
||||
|
||||
mvprog="${MVPROG-mv}"
|
||||
cpprog="${CPPROG-cp}"
|
||||
chmodprog="${CHMODPROG-chmod}"
|
||||
chownprog="${CHOWNPROG-chown}"
|
||||
chgrpprog="${CHGRPPROG-chgrp}"
|
||||
stripprog="${STRIPPROG-strip}"
|
||||
rmprog="${RMPROG-rm}"
|
||||
mkdirprog="${MKDIRPROG-mkdir}"
|
||||
|
||||
transformbasename=""
|
||||
transform_arg=""
|
||||
instcmd="$mvprog"
|
||||
chmodcmd="$chmodprog 0755"
|
||||
chowncmd=""
|
||||
chgrpcmd=""
|
||||
stripcmd=""
|
||||
rmcmd="$rmprog -f"
|
||||
mvcmd="$mvprog"
|
||||
src=""
|
||||
dst=""
|
||||
dir_arg=""
|
||||
|
||||
while [ x"$1" != x ]; do
|
||||
case $1 in
|
||||
-c) instcmd="$cpprog"
|
||||
shift
|
||||
continue;;
|
||||
|
||||
-d) dir_arg=true
|
||||
shift
|
||||
continue;;
|
||||
|
||||
-m) chmodcmd="$chmodprog $2"
|
||||
shift
|
||||
shift
|
||||
continue;;
|
||||
|
||||
-o) chowncmd="$chownprog $2"
|
||||
shift
|
||||
shift
|
||||
continue;;
|
||||
|
||||
-g) chgrpcmd="$chgrpprog $2"
|
||||
shift
|
||||
shift
|
||||
continue;;
|
||||
|
||||
-s) stripcmd="$stripprog"
|
||||
shift
|
||||
continue;;
|
||||
|
||||
-t=*) transformarg=`echo $1 | sed 's/-t=//'`
|
||||
shift
|
||||
continue;;
|
||||
|
||||
-b=*) transformbasename=`echo $1 | sed 's/-b=//'`
|
||||
shift
|
||||
continue;;
|
||||
|
||||
*) if [ x"$src" = x ]
|
||||
then
|
||||
src=$1
|
||||
else
|
||||
# this colon is to work around a 386BSD /bin/sh bug
|
||||
:
|
||||
dst=$1
|
||||
fi
|
||||
shift
|
||||
continue;;
|
||||
esac
|
||||
done
|
||||
|
||||
if [ x"$src" = x ]
|
||||
then
|
||||
echo "install: no input file specified"
|
||||
exit 1
|
||||
else
|
||||
true
|
||||
fi
|
||||
|
||||
if [ x"$dir_arg" != x ]; then
|
||||
dst=$src
|
||||
src=""
|
||||
|
||||
if [ -d $dst ]; then
|
||||
instcmd=:
|
||||
else
|
||||
instcmd=mkdir
|
||||
fi
|
||||
else
|
||||
|
||||
# Waiting for this to be detected by the "$instcmd $src $dsttmp" command
|
||||
# might cause directories to be created, which would be especially bad
|
||||
# if $src (and thus $dsttmp) contains '*'.
|
||||
|
||||
if [ -f $src -o -d $src ]
|
||||
then
|
||||
true
|
||||
else
|
||||
echo "install: $src does not exist"
|
||||
exit 1
|
||||
fi
|
||||
|
||||
if [ x"$dst" = x ]
|
||||
then
|
||||
echo "install: no destination specified"
|
||||
exit 1
|
||||
else
|
||||
true
|
||||
fi
|
||||
|
||||
# If destination is a directory, append the input filename; if your system
|
||||
# does not like double slashes in filenames, you may need to add some logic
|
||||
|
||||
if [ -d $dst ]
|
||||
then
|
||||
dst="$dst"/`basename $src`
|
||||
else
|
||||
true
|
||||
fi
|
||||
fi
|
||||
|
||||
## this sed command emulates the dirname command
|
||||
dstdir=`echo $dst | sed -e 's,[^/]*$,,;s,/$,,;s,^$,.,'`
|
||||
|
||||
# Make sure that the destination directory exists.
|
||||
# this part is taken from Noah Friedman's mkinstalldirs script
|
||||
|
||||
# Skip lots of stat calls in the usual case.
|
||||
if [ ! -d "$dstdir" ]; then
|
||||
defaultIFS='
|
||||
'
|
||||
IFS="${IFS-${defaultIFS}}"
|
||||
|
||||
oIFS="${IFS}"
|
||||
# Some sh's can't handle IFS=/ for some reason.
|
||||
IFS='%'
|
||||
set - `echo ${dstdir} | sed -e 's@/@%@g' -e 's@^%@/@'`
|
||||
IFS="${oIFS}"
|
||||
|
||||
pathcomp=''
|
||||
|
||||
while [ $# -ne 0 ] ; do
|
||||
pathcomp="${pathcomp}${1}"
|
||||
shift
|
||||
|
||||
if [ ! -d "${pathcomp}" ] ;
|
||||
then
|
||||
$mkdirprog "${pathcomp}"
|
||||
else
|
||||
true
|
||||
fi
|
||||
|
||||
pathcomp="${pathcomp}/"
|
||||
done
|
||||
fi
|
||||
|
||||
if [ x"$dir_arg" != x ]
|
||||
then
|
||||
$doit $instcmd $dst &&
|
||||
|
||||
if [ x"$chowncmd" != x ]; then $doit $chowncmd $dst; else true ; fi &&
|
||||
if [ x"$chgrpcmd" != x ]; then $doit $chgrpcmd $dst; else true ; fi &&
|
||||
if [ x"$stripcmd" != x ]; then $doit $stripcmd $dst; else true ; fi &&
|
||||
if [ x"$chmodcmd" != x ]; then $doit $chmodcmd $dst; else true ; fi
|
||||
else
|
||||
|
||||
# If we're going to rename the final executable, determine the name now.
|
||||
|
||||
if [ x"$transformarg" = x ]
|
||||
then
|
||||
dstfile=`basename $dst`
|
||||
else
|
||||
dstfile=`basename $dst $transformbasename |
|
||||
sed $transformarg`$transformbasename
|
||||
fi
|
||||
|
||||
# don't allow the sed command to completely eliminate the filename
|
||||
|
||||
if [ x"$dstfile" = x ]
|
||||
then
|
||||
dstfile=`basename $dst`
|
||||
else
|
||||
true
|
||||
fi
|
||||
|
||||
# Make a temp file name in the proper directory.
|
||||
|
||||
dsttmp=$dstdir/#inst.$$#
|
||||
|
||||
# Move or copy the file name to the temp name
|
||||
|
||||
$doit $instcmd $src $dsttmp &&
|
||||
|
||||
trap "rm -f ${dsttmp}" 0 &&
|
||||
|
||||
# and set any options; do chmod last to preserve setuid bits
|
||||
|
||||
# If any of these fail, we abort the whole thing. If we want to
|
||||
# ignore errors from any of these, just make sure not to ignore
|
||||
# errors from the above "$doit $instcmd $src $dsttmp" command.
|
||||
|
||||
if [ x"$chowncmd" != x ]; then $doit $chowncmd $dsttmp; else true;fi &&
|
||||
if [ x"$chgrpcmd" != x ]; then $doit $chgrpcmd $dsttmp; else true;fi &&
|
||||
if [ x"$stripcmd" != x ]; then $doit $stripcmd $dsttmp; else true;fi &&
|
||||
if [ x"$chmodcmd" != x ]; then $doit $chmodcmd $dsttmp; else true;fi &&
|
||||
|
||||
# Now rename the file to the real destination.
|
||||
|
||||
$doit $rmcmd -f $dstdir/$dstfile &&
|
||||
$doit $mvcmd $dsttmp $dstdir/$dstfile
|
||||
|
||||
fi &&
|
||||
|
||||
|
||||
exit 0
|
@@ -1,687 +0,0 @@
|
||||
/* $NetBSD: key.c,v 1.13 2002/03/18 16:00:55 christos Exp $ */
|
||||
|
||||
/*-
|
||||
* Copyright (c) 1992, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* This code is derived from software contributed to Berkeley by
|
||||
* Christos Zoulas of Cornell University.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
* 3. All advertising materials mentioning features or use of this software
|
||||
* must display the following acknowledgement:
|
||||
* This product includes software developed by the University of
|
||||
* California, Berkeley and its contributors.
|
||||
* 4. Neither the name of the University nor the names of its contributors
|
||||
* may be used to endorse or promote products derived from this software
|
||||
* without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
|
||||
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
* ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
|
||||
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
|
||||
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*/
|
||||
|
||||
#include "config.h"
|
||||
#if !defined(lint) && !defined(SCCSID)
|
||||
#if 0
|
||||
static char sccsid[] = "@(#)key.c 8.1 (Berkeley) 6/4/93";
|
||||
#else
|
||||
__RCSID("$NetBSD: key.c,v 1.13 2002/03/18 16:00:55 christos Exp $");
|
||||
#endif
|
||||
#endif /* not lint && not SCCSID */
|
||||
|
||||
/*
|
||||
* key.c: This module contains the procedures for maintaining
|
||||
* the extended-key map.
|
||||
*
|
||||
* An extended-key (key) is a sequence of keystrokes introduced
|
||||
* with an sequence introducer and consisting of an arbitrary
|
||||
* number of characters. This module maintains a map (the el->el_key.map)
|
||||
* to convert these extended-key sequences into input strs
|
||||
* (XK_STR), editor functions (XK_CMD), or unix commands (XK_EXE).
|
||||
*
|
||||
* Warning:
|
||||
* If key is a substr of some other keys, then the longer
|
||||
* keys are lost!! That is, if the keys "abcd" and "abcef"
|
||||
* are in el->el_key.map, adding the key "abc" will cause the first two
|
||||
* definitions to be lost.
|
||||
*
|
||||
* Restrictions:
|
||||
* -------------
|
||||
* 1) It is not possible to have one key that is a
|
||||
* substr of another.
|
||||
*/
|
||||
#include <string.h>
|
||||
#include <stdlib.h>
|
||||
|
||||
#include "el.h"
|
||||
|
||||
/*
|
||||
* The Nodes of the el->el_key.map. The el->el_key.map is a linked list
|
||||
* of these node elements
|
||||
*/
|
||||
struct key_node_t {
|
||||
char ch; /* single character of key */
|
||||
int type; /* node type */
|
||||
key_value_t val; /* command code or pointer to str, */
|
||||
/* if this is a leaf */
|
||||
struct key_node_t *next; /* ptr to next char of this key */
|
||||
struct key_node_t *sibling; /* ptr to another key with same prefix*/
|
||||
};
|
||||
|
||||
private int node_trav(EditLine *, key_node_t *, char *,
|
||||
key_value_t *);
|
||||
private int node__try(EditLine *, key_node_t *, const char *,
|
||||
key_value_t *, int);
|
||||
private key_node_t *node__get(int);
|
||||
private void node__put(EditLine *, key_node_t *);
|
||||
private int node__delete(EditLine *, key_node_t **, const char *);
|
||||
private int node_lookup(EditLine *, const char *, key_node_t *,
|
||||
int);
|
||||
private int node_enum(EditLine *, key_node_t *, int);
|
||||
private int key__decode_char(char *, int, int);
|
||||
|
||||
#define KEY_BUFSIZ EL_BUFSIZ
|
||||
|
||||
|
||||
/* key_init():
|
||||
* Initialize the key maps
|
||||
*/
|
||||
protected int
|
||||
key_init(EditLine *el)
|
||||
{
|
||||
|
||||
el->el_key.buf = (char *) el_malloc(KEY_BUFSIZ);
|
||||
if (el->el_key.buf == NULL)
|
||||
return (-1);
|
||||
el->el_key.map = NULL;
|
||||
key_reset(el);
|
||||
return (0);
|
||||
}
|
||||
|
||||
|
||||
/* key_end():
|
||||
* Free the key maps
|
||||
*/
|
||||
protected void
|
||||
key_end(EditLine *el)
|
||||
{
|
||||
|
||||
el_free((ptr_t) el->el_key.buf);
|
||||
el->el_key.buf = NULL;
|
||||
node__put(el, el->el_key.map);
|
||||
el->el_key.map = NULL;
|
||||
}
|
||||
|
||||
|
||||
/* key_map_cmd():
|
||||
* Associate cmd with a key value
|
||||
*/
|
||||
protected key_value_t *
|
||||
key_map_cmd(EditLine *el, int cmd)
|
||||
{
|
||||
|
||||
el->el_key.val.cmd = (el_action_t) cmd;
|
||||
return (&el->el_key.val);
|
||||
}
|
||||
|
||||
|
||||
/* key_map_str():
|
||||
* Associate str with a key value
|
||||
*/
|
||||
protected key_value_t *
|
||||
key_map_str(EditLine *el, char *str)
|
||||
{
|
||||
|
||||
el->el_key.val.str = str;
|
||||
return (&el->el_key.val);
|
||||
}
|
||||
|
||||
|
||||
/* key_reset():
|
||||
* Takes all nodes on el->el_key.map and puts them on free list. Then
|
||||
* initializes el->el_key.map with arrow keys
|
||||
* [Always bind the ansi arrow keys?]
|
||||
*/
|
||||
protected void
|
||||
key_reset(EditLine *el)
|
||||
{
|
||||
|
||||
node__put(el, el->el_key.map);
|
||||
el->el_key.map = NULL;
|
||||
return;
|
||||
}
|
||||
|
||||
|
||||
/* key_get():
|
||||
* Calls the recursive function with entry point el->el_key.map
|
||||
* Looks up *ch in map and then reads characters until a
|
||||
* complete match is found or a mismatch occurs. Returns the
|
||||
* type of the match found (XK_STR, XK_CMD, or XK_EXE).
|
||||
* Returns NULL in val.str and XK_STR for no match.
|
||||
* The last character read is returned in *ch.
|
||||
*/
|
||||
protected int
|
||||
key_get(EditLine *el, char *ch, key_value_t *val)
|
||||
{
|
||||
|
||||
return (node_trav(el, el->el_key.map, ch, val));
|
||||
}
|
||||
|
||||
|
||||
/* key_add():
|
||||
* Adds key to the el->el_key.map and associates the value in val with it.
|
||||
* If key is already is in el->el_key.map, the new code is applied to the
|
||||
* existing key. Ntype specifies if code is a command, an
|
||||
* out str or a unix command.
|
||||
*/
|
||||
protected void
|
||||
key_add(EditLine *el, const char *key, key_value_t *val, int ntype)
|
||||
{
|
||||
|
||||
if (key[0] == '\0') {
|
||||
(void) fprintf(el->el_errfile,
|
||||
"key_add: Null extended-key not allowed.\n");
|
||||
return;
|
||||
}
|
||||
if (ntype == XK_CMD && val->cmd == ED_SEQUENCE_LEAD_IN) {
|
||||
(void) fprintf(el->el_errfile,
|
||||
"key_add: sequence-lead-in command not allowed\n");
|
||||
return;
|
||||
}
|
||||
if (el->el_key.map == NULL)
|
||||
/* tree is initially empty. Set up new node to match key[0] */
|
||||
el->el_key.map = node__get(key[0]);
|
||||
/* it is properly initialized */
|
||||
|
||||
/* Now recurse through el->el_key.map */
|
||||
(void) node__try(el, el->el_key.map, key, val, ntype);
|
||||
return;
|
||||
}
|
||||
|
||||
|
||||
/* key_clear():
|
||||
*
|
||||
*/
|
||||
protected void
|
||||
key_clear(EditLine *el, el_action_t *map, const char *in)
|
||||
{
|
||||
|
||||
if ((map[(unsigned char)*in] == ED_SEQUENCE_LEAD_IN) &&
|
||||
((map == el->el_map.key &&
|
||||
el->el_map.alt[(unsigned char)*in] != ED_SEQUENCE_LEAD_IN) ||
|
||||
(map == el->el_map.alt &&
|
||||
el->el_map.key[(unsigned char)*in] != ED_SEQUENCE_LEAD_IN)))
|
||||
(void) key_delete(el, in);
|
||||
}
|
||||
|
||||
|
||||
/* key_delete():
|
||||
* Delete the key and all longer keys staring with key, if
|
||||
* they exists.
|
||||
*/
|
||||
protected int
|
||||
key_delete(EditLine *el, const char *key)
|
||||
{
|
||||
|
||||
if (key[0] == '\0') {
|
||||
(void) fprintf(el->el_errfile,
|
||||
"key_delete: Null extended-key not allowed.\n");
|
||||
return (-1);
|
||||
}
|
||||
if (el->el_key.map == NULL)
|
||||
return (0);
|
||||
|
||||
(void) node__delete(el, &el->el_key.map, key);
|
||||
return (0);
|
||||
}
|
||||
|
||||
|
||||
/* key_print():
|
||||
* Print the binding associated with key key.
|
||||
* Print entire el->el_key.map if null
|
||||
*/
|
||||
protected void
|
||||
key_print(EditLine *el, const char *key)
|
||||
{
|
||||
|
||||
/* do nothing if el->el_key.map is empty and null key specified */
|
||||
if (el->el_key.map == NULL && *key == 0)
|
||||
return;
|
||||
|
||||
el->el_key.buf[0] = '"';
|
||||
if (node_lookup(el, key, el->el_key.map, 1) <= -1)
|
||||
/* key is not bound */
|
||||
(void) fprintf(el->el_errfile, "Unbound extended key \"%s\"\n",
|
||||
key);
|
||||
return;
|
||||
}
|
||||
|
||||
|
||||
/* node_trav():
|
||||
* recursively traverses node in tree until match or mismatch is
|
||||
* found. May read in more characters.
|
||||
*/
|
||||
private int
|
||||
node_trav(EditLine *el, key_node_t *ptr, char *ch, key_value_t *val)
|
||||
{
|
||||
|
||||
if (ptr->ch == *ch) {
|
||||
/* match found */
|
||||
if (ptr->next) {
|
||||
/* key not complete so get next char */
|
||||
if (el_getc(el, ch) != 1) { /* if EOF or error */
|
||||
val->cmd = ED_END_OF_FILE;
|
||||
return (XK_CMD);
|
||||
/* PWP: Pretend we just read an end-of-file */
|
||||
}
|
||||
return (node_trav(el, ptr->next, ch, val));
|
||||
} else {
|
||||
*val = ptr->val;
|
||||
if (ptr->type != XK_CMD)
|
||||
*ch = '\0';
|
||||
return (ptr->type);
|
||||
}
|
||||
} else {
|
||||
/* no match found here */
|
||||
if (ptr->sibling) {
|
||||
/* try next sibling */
|
||||
return (node_trav(el, ptr->sibling, ch, val));
|
||||
} else {
|
||||
/* no next sibling -- mismatch */
|
||||
val->str = NULL;
|
||||
return (XK_STR);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/* node__try():
|
||||
* Find a node that matches *str or allocate a new one
|
||||
*/
|
||||
private int
|
||||
node__try(EditLine *el, key_node_t *ptr, const char *str, key_value_t *val, int ntype)
|
||||
{
|
||||
|
||||
if (ptr->ch != *str) {
|
||||
key_node_t *xm;
|
||||
|
||||
for (xm = ptr; xm->sibling != NULL; xm = xm->sibling)
|
||||
if (xm->sibling->ch == *str)
|
||||
break;
|
||||
if (xm->sibling == NULL)
|
||||
xm->sibling = node__get(*str); /* setup new node */
|
||||
ptr = xm->sibling;
|
||||
}
|
||||
if (*++str == '\0') {
|
||||
/* we're there */
|
||||
if (ptr->next != NULL) {
|
||||
node__put(el, ptr->next);
|
||||
/* lose longer keys with this prefix */
|
||||
ptr->next = NULL;
|
||||
}
|
||||
switch (ptr->type) {
|
||||
case XK_CMD:
|
||||
case XK_NOD:
|
||||
break;
|
||||
case XK_STR:
|
||||
case XK_EXE:
|
||||
if (ptr->val.str)
|
||||
el_free((ptr_t) ptr->val.str);
|
||||
break;
|
||||
default:
|
||||
EL_ABORT((el->el_errfile, "Bad XK_ type %d\n",
|
||||
ptr->type));
|
||||
break;
|
||||
}
|
||||
|
||||
switch (ptr->type = ntype) {
|
||||
case XK_CMD:
|
||||
ptr->val = *val;
|
||||
break;
|
||||
case XK_STR:
|
||||
case XK_EXE:
|
||||
ptr->val.str = strdup(val->str);
|
||||
break;
|
||||
default:
|
||||
EL_ABORT((el->el_errfile, "Bad XK_ type %d\n", ntype));
|
||||
break;
|
||||
}
|
||||
} else {
|
||||
/* still more chars to go */
|
||||
if (ptr->next == NULL)
|
||||
ptr->next = node__get(*str); /* setup new node */
|
||||
(void) node__try(el, ptr->next, str, val, ntype);
|
||||
}
|
||||
return (0);
|
||||
}
|
||||
|
||||
|
||||
/* node__delete():
|
||||
* Delete node that matches str
|
||||
*/
|
||||
private int
|
||||
node__delete(EditLine *el, key_node_t **inptr, const char *str)
|
||||
{
|
||||
key_node_t *ptr;
|
||||
key_node_t *prev_ptr = NULL;
|
||||
|
||||
ptr = *inptr;
|
||||
|
||||
if (ptr->ch != *str) {
|
||||
key_node_t *xm;
|
||||
|
||||
for (xm = ptr; xm->sibling != NULL; xm = xm->sibling)
|
||||
if (xm->sibling->ch == *str)
|
||||
break;
|
||||
if (xm->sibling == NULL)
|
||||
return (0);
|
||||
prev_ptr = xm;
|
||||
ptr = xm->sibling;
|
||||
}
|
||||
if (*++str == '\0') {
|
||||
/* we're there */
|
||||
if (prev_ptr == NULL)
|
||||
*inptr = ptr->sibling;
|
||||
else
|
||||
prev_ptr->sibling = ptr->sibling;
|
||||
ptr->sibling = NULL;
|
||||
node__put(el, ptr);
|
||||
return (1);
|
||||
} else if (ptr->next != NULL &&
|
||||
node__delete(el, &ptr->next, str) == 1) {
|
||||
if (ptr->next != NULL)
|
||||
return (0);
|
||||
if (prev_ptr == NULL)
|
||||
*inptr = ptr->sibling;
|
||||
else
|
||||
prev_ptr->sibling = ptr->sibling;
|
||||
ptr->sibling = NULL;
|
||||
node__put(el, ptr);
|
||||
return (1);
|
||||
} else {
|
||||
return (0);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/* node__put():
|
||||
* Puts a tree of nodes onto free list using free(3).
|
||||
*/
|
||||
private void
|
||||
node__put(EditLine *el, key_node_t *ptr)
|
||||
{
|
||||
if (ptr == NULL)
|
||||
return;
|
||||
|
||||
if (ptr->next != NULL) {
|
||||
node__put(el, ptr->next);
|
||||
ptr->next = NULL;
|
||||
}
|
||||
node__put(el, ptr->sibling);
|
||||
|
||||
switch (ptr->type) {
|
||||
case XK_CMD:
|
||||
case XK_NOD:
|
||||
break;
|
||||
case XK_EXE:
|
||||
case XK_STR:
|
||||
if (ptr->val.str != NULL)
|
||||
el_free((ptr_t) ptr->val.str);
|
||||
break;
|
||||
default:
|
||||
EL_ABORT((el->el_errfile, "Bad XK_ type %d\n", ptr->type));
|
||||
break;
|
||||
}
|
||||
el_free((ptr_t) ptr);
|
||||
}
|
||||
|
||||
|
||||
/* node__get():
|
||||
* Returns pointer to an key_node_t for ch.
|
||||
*/
|
||||
private key_node_t *
|
||||
node__get(int ch)
|
||||
{
|
||||
key_node_t *ptr;
|
||||
|
||||
ptr = (key_node_t *) el_malloc((size_t) sizeof(key_node_t));
|
||||
if (ptr == NULL)
|
||||
return NULL;
|
||||
ptr->ch = ch;
|
||||
ptr->type = XK_NOD;
|
||||
ptr->val.str = NULL;
|
||||
ptr->next = NULL;
|
||||
ptr->sibling = NULL;
|
||||
return (ptr);
|
||||
}
|
||||
|
||||
|
||||
|
||||
/* node_lookup():
|
||||
* look for the str starting at node ptr.
|
||||
* Print if last node
|
||||
*/
|
||||
private int
|
||||
node_lookup(EditLine *el, const char *str, key_node_t *ptr, int cnt)
|
||||
{
|
||||
int ncnt;
|
||||
|
||||
if (ptr == NULL)
|
||||
return (-1); /* cannot have null ptr */
|
||||
|
||||
if (*str == 0) {
|
||||
/* no more chars in str. node_enum from here. */
|
||||
(void) node_enum(el, ptr, cnt);
|
||||
return (0);
|
||||
} else {
|
||||
/* If match put this char into el->el_key.buf. Recurse */
|
||||
if (ptr->ch == *str) {
|
||||
/* match found */
|
||||
ncnt = key__decode_char(el->el_key.buf, cnt,
|
||||
(unsigned char) ptr->ch);
|
||||
if (ptr->next != NULL)
|
||||
/* not yet at leaf */
|
||||
return (node_lookup(el, str + 1, ptr->next,
|
||||
ncnt + 1));
|
||||
else {
|
||||
/* next node is null so key should be complete */
|
||||
if (str[1] == 0) {
|
||||
el->el_key.buf[ncnt + 1] = '"';
|
||||
el->el_key.buf[ncnt + 2] = '\0';
|
||||
key_kprint(el, el->el_key.buf,
|
||||
&ptr->val, ptr->type);
|
||||
return (0);
|
||||
} else
|
||||
return (-1);
|
||||
/* mismatch -- str still has chars */
|
||||
}
|
||||
} else {
|
||||
/* no match found try sibling */
|
||||
if (ptr->sibling)
|
||||
return (node_lookup(el, str, ptr->sibling,
|
||||
cnt));
|
||||
else
|
||||
return (-1);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/* node_enum():
|
||||
* Traverse the node printing the characters it is bound in buffer
|
||||
*/
|
||||
private int
|
||||
node_enum(EditLine *el, key_node_t *ptr, int cnt)
|
||||
{
|
||||
int ncnt;
|
||||
|
||||
if (cnt >= KEY_BUFSIZ - 5) { /* buffer too small */
|
||||
el->el_key.buf[++cnt] = '"';
|
||||
el->el_key.buf[++cnt] = '\0';
|
||||
(void) fprintf(el->el_errfile,
|
||||
"Some extended keys too long for internal print buffer");
|
||||
(void) fprintf(el->el_errfile, " \"%s...\"\n", el->el_key.buf);
|
||||
return (0);
|
||||
}
|
||||
if (ptr == NULL) {
|
||||
#ifdef DEBUG_EDIT
|
||||
(void) fprintf(el->el_errfile,
|
||||
"node_enum: BUG!! Null ptr passed\n!");
|
||||
#endif
|
||||
return (-1);
|
||||
}
|
||||
/* put this char at end of str */
|
||||
ncnt = key__decode_char(el->el_key.buf, cnt, (unsigned char) ptr->ch);
|
||||
if (ptr->next == NULL) {
|
||||
/* print this key and function */
|
||||
el->el_key.buf[ncnt + 1] = '"';
|
||||
el->el_key.buf[ncnt + 2] = '\0';
|
||||
key_kprint(el, el->el_key.buf, &ptr->val, ptr->type);
|
||||
} else
|
||||
(void) node_enum(el, ptr->next, ncnt + 1);
|
||||
|
||||
/* go to sibling if there is one */
|
||||
if (ptr->sibling)
|
||||
(void) node_enum(el, ptr->sibling, cnt);
|
||||
return (0);
|
||||
}
|
||||
|
||||
|
||||
/* key_kprint():
|
||||
* Print the specified key and its associated
|
||||
* function specified by val
|
||||
*/
|
||||
protected void
|
||||
key_kprint(EditLine *el, const char *key, key_value_t *val, int ntype)
|
||||
{
|
||||
el_bindings_t *fp;
|
||||
char unparsbuf[EL_BUFSIZ];
|
||||
static const char fmt[] = "%-15s-> %s\n";
|
||||
|
||||
if (val != NULL)
|
||||
switch (ntype) {
|
||||
case XK_STR:
|
||||
case XK_EXE:
|
||||
(void) fprintf(el->el_outfile, fmt, key,
|
||||
key__decode_str(val->str, unparsbuf,
|
||||
ntype == XK_STR ? "\"\"" : "[]"));
|
||||
break;
|
||||
case XK_CMD:
|
||||
for (fp = el->el_map.help; fp->name; fp++)
|
||||
if (val->cmd == fp->func) {
|
||||
(void) fprintf(el->el_outfile, fmt,
|
||||
key, fp->name);
|
||||
break;
|
||||
}
|
||||
#ifdef DEBUG_KEY
|
||||
if (fp->name == NULL)
|
||||
(void) fprintf(el->el_outfile,
|
||||
"BUG! Command not found.\n");
|
||||
#endif
|
||||
|
||||
break;
|
||||
default:
|
||||
EL_ABORT((el->el_errfile, "Bad XK_ type %d\n", ntype));
|
||||
break;
|
||||
}
|
||||
else
|
||||
(void) fprintf(el->el_outfile, fmt, key, "no input");
|
||||
}
|
||||
|
||||
|
||||
/* key__decode_char():
|
||||
* Put a printable form of char in buf.
|
||||
*/
|
||||
private int
|
||||
key__decode_char(char *buf, int cnt, int ch)
|
||||
{
|
||||
if (ch == 0) {
|
||||
buf[cnt++] = '^';
|
||||
buf[cnt] = '@';
|
||||
return (cnt);
|
||||
}
|
||||
if (iscntrl(ch)) {
|
||||
buf[cnt++] = '^';
|
||||
if (ch == '\177')
|
||||
buf[cnt] = '?';
|
||||
else
|
||||
buf[cnt] = ch | 0100;
|
||||
} else if (ch == '^') {
|
||||
buf[cnt++] = '\\';
|
||||
buf[cnt] = '^';
|
||||
} else if (ch == '\\') {
|
||||
buf[cnt++] = '\\';
|
||||
buf[cnt] = '\\';
|
||||
} else if (ch == ' ' || (isprint(ch) && !isspace(ch))) {
|
||||
buf[cnt] = ch;
|
||||
} else {
|
||||
buf[cnt++] = '\\';
|
||||
buf[cnt++] = (((unsigned int) ch >> 6) & 7) + '0';
|
||||
buf[cnt++] = (((unsigned int) ch >> 3) & 7) + '0';
|
||||
buf[cnt] = (ch & 7) + '0';
|
||||
}
|
||||
return (cnt);
|
||||
}
|
||||
|
||||
|
||||
/* key__decode_str():
|
||||
* Make a printable version of the ey
|
||||
*/
|
||||
protected char *
|
||||
key__decode_str(const char *str, char *buf, const char *sep)
|
||||
{
|
||||
char *b;
|
||||
const char *p;
|
||||
|
||||
b = buf;
|
||||
if (sep[0] != '\0')
|
||||
*b++ = sep[0];
|
||||
if (*str == 0) {
|
||||
*b++ = '^';
|
||||
*b++ = '@';
|
||||
if (sep[0] != '\0' && sep[1] != '\0')
|
||||
*b++ = sep[1];
|
||||
*b++ = 0;
|
||||
return (buf);
|
||||
}
|
||||
for (p = str; *p != 0; p++) {
|
||||
if (iscntrl((unsigned char) *p)) {
|
||||
*b++ = '^';
|
||||
if (*p == '\177')
|
||||
*b++ = '?';
|
||||
else
|
||||
*b++ = *p | 0100;
|
||||
} else if (*p == '^' || *p == '\\') {
|
||||
*b++ = '\\';
|
||||
*b++ = *p;
|
||||
} else if (*p == ' ' || (isprint((unsigned char) *p) &&
|
||||
!isspace((unsigned char) *p))) {
|
||||
*b++ = *p;
|
||||
} else {
|
||||
*b++ = '\\';
|
||||
*b++ = (((unsigned int) *p >> 6) & 7) + '0';
|
||||
*b++ = (((unsigned int) *p >> 3) & 7) + '0';
|
||||
*b++ = (*p & 7) + '0';
|
||||
}
|
||||
}
|
||||
if (sep[0] != '\0' && sep[1] != '\0')
|
||||
*b++ = sep[1];
|
||||
*b++ = 0;
|
||||
return (buf); /* should check for overflow */
|
||||
}
|
@@ -1,79 +0,0 @@
|
||||
/* $NetBSD: key.h,v 1.6 2002/03/18 16:00:55 christos Exp $ */
|
||||
|
||||
/*-
|
||||
* Copyright (c) 1992, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* This code is derived from software contributed to Berkeley by
|
||||
* Christos Zoulas of Cornell University.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
* 3. All advertising materials mentioning features or use of this software
|
||||
* must display the following acknowledgement:
|
||||
* This product includes software developed by the University of
|
||||
* California, Berkeley and its contributors.
|
||||
* 4. Neither the name of the University nor the names of its contributors
|
||||
* may be used to endorse or promote products derived from this software
|
||||
* without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
|
||||
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
* ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
|
||||
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
|
||||
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* @(#)key.h 8.1 (Berkeley) 6/4/93
|
||||
*/
|
||||
|
||||
/*
|
||||
* el.key.h: Key macro header
|
||||
*/
|
||||
#ifndef _h_el_key
|
||||
#define _h_el_key
|
||||
|
||||
typedef union key_value_t {
|
||||
el_action_t cmd; /* If it is a command the # */
|
||||
char *str; /* If it is a string... */
|
||||
} key_value_t;
|
||||
|
||||
typedef struct key_node_t key_node_t;
|
||||
|
||||
typedef struct el_key_t {
|
||||
char *buf; /* Key print buffer */
|
||||
key_node_t *map; /* Key map */
|
||||
key_value_t val; /* Local conversion buffer */
|
||||
} el_key_t;
|
||||
|
||||
#define XK_CMD 0
|
||||
#define XK_STR 1
|
||||
#define XK_NOD 2
|
||||
#define XK_EXE 3
|
||||
|
||||
protected int key_init(EditLine *);
|
||||
protected void key_end(EditLine *);
|
||||
protected key_value_t *key_map_cmd(EditLine *, int);
|
||||
protected key_value_t *key_map_str(EditLine *, char *);
|
||||
protected void key_reset(EditLine *);
|
||||
protected int key_get(EditLine *, char *, key_value_t *);
|
||||
protected void key_add(EditLine *, const char *, key_value_t *, int);
|
||||
protected void key_clear(EditLine *, el_action_t *, const char *);
|
||||
protected int key_delete(EditLine *, const char *);
|
||||
protected void key_print(EditLine *, const char *);
|
||||
protected void key_kprint(EditLine *, const char *, key_value_t *,
|
||||
int);
|
||||
protected char *key__decode_str(const char *, char *, const char *);
|
||||
|
||||
#endif /* _h_el_key */
|
@@ -1,254 +0,0 @@
|
||||
#!/bin/sh -
|
||||
# $NetBSD: makelist,v 1.7 2001/01/09 19:22:31 jdolecek Exp $
|
||||
#
|
||||
# Copyright (c) 1992, 1993
|
||||
# The Regents of the University of California. All rights reserved.
|
||||
#
|
||||
# This code is derived from software contributed to Berkeley by
|
||||
# Christos Zoulas of Cornell University.
|
||||
#
|
||||
# Redistribution and use in source and binary forms, with or without
|
||||
# modification, are permitted provided that the following conditions
|
||||
# are met:
|
||||
# 1. Redistributions of source code must retain the above copyright
|
||||
# notice, this list of conditions and the following disclaimer.
|
||||
# 2. Redistributions in binary form must reproduce the above copyright
|
||||
# notice, this list of conditions and the following disclaimer in the
|
||||
# documentation and/or other materials provided with the distribution.
|
||||
# 3. All advertising materials mentioning features or use of this software
|
||||
# must display the following acknowledgement:
|
||||
# This product includes software developed by the University of
|
||||
# California, Berkeley and its contributors.
|
||||
# 4. Neither the name of the University nor the names of its contributors
|
||||
# may be used to endorse or promote products derived from this software
|
||||
# without specific prior written permission.
|
||||
#
|
||||
# THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
|
||||
# ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
# IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
# ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
|
||||
# FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
# DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
# OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
# HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
|
||||
# LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
|
||||
# OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
# SUCH DAMAGE.
|
||||
#
|
||||
# @(#)makelist 5.3 (Berkeley) 6/4/93
|
||||
|
||||
# makelist.sh: Automatically generate header files...
|
||||
|
||||
AWK=@AWK@
|
||||
USAGE="Usage: $0 -h|-e|-fc|-fh|-bc|-bh|-m <filenames>"
|
||||
|
||||
if [ "x$1" = "x" ]
|
||||
then
|
||||
echo $USAGE 1>&2
|
||||
exit 1
|
||||
fi
|
||||
|
||||
FLAG="$1"
|
||||
shift
|
||||
|
||||
FILES="$@"
|
||||
|
||||
case $FLAG in
|
||||
|
||||
# generate foo.h file from foo.c
|
||||
#
|
||||
-h)
|
||||
set - `echo $FILES | sed -e 's/\\./_/g'`
|
||||
hdr="_h_`basename $1`"
|
||||
cat $FILES | $AWK '
|
||||
BEGIN {
|
||||
printf("/* Automatically generated file, do not edit */\n");
|
||||
printf("#ifndef %s\n#define %s\n", "'$hdr'", "'$hdr'");
|
||||
}
|
||||
/\(\):/ {
|
||||
pr = substr($2, 1, 2);
|
||||
if (pr == "vi" || pr == "em" || pr == "ed") {
|
||||
name = substr($2, 1, length($2) - 3);
|
||||
#
|
||||
# XXX: need a space between name and prototype so that -fc and -fh
|
||||
# parsing is much easier
|
||||
#
|
||||
printf("protected el_action_t\t%s (EditLine *, int);\n", name);
|
||||
}
|
||||
}
|
||||
END {
|
||||
printf("#endif /* %s */\n", "'$hdr'");
|
||||
}'
|
||||
;;
|
||||
|
||||
# generate help.c from various .c files
|
||||
#
|
||||
-bc)
|
||||
cat $FILES | $AWK '
|
||||
BEGIN {
|
||||
printf("/* Automatically generated file, do not edit */\n");
|
||||
printf("#include \"sys.h\"\n#include \"el.h\"\n");
|
||||
printf("private const struct el_bindings_t el_func_help[] = {\n");
|
||||
low = "abcdefghijklmnopqrstuvwxyz_";
|
||||
high = "ABCDEFGHIJKLMNOPQRSTUVWXYZ_";
|
||||
for (i = 1; i <= length(low); i++)
|
||||
tr[substr(low, i, 1)] = substr(high, i, 1);
|
||||
}
|
||||
/\(\):/ {
|
||||
pr = substr($2, 1, 2);
|
||||
if (pr == "vi" || pr == "em" || pr == "ed") {
|
||||
name = substr($2, 1, length($2) - 3);
|
||||
uname = "";
|
||||
fname = "";
|
||||
for (i = 1; i <= length(name); i++) {
|
||||
s = substr(name, i, 1);
|
||||
uname = uname tr[s];
|
||||
if (s == "_")
|
||||
s = "-";
|
||||
fname = fname s;
|
||||
}
|
||||
|
||||
printf(" { %-30.30s %-30.30s\n","\"" fname "\",", uname ",");
|
||||
ok = 1;
|
||||
}
|
||||
}
|
||||
/^ \*/ {
|
||||
if (ok) {
|
||||
printf(" \"");
|
||||
for (i = 2; i < NF; i++)
|
||||
printf("%s ", $i);
|
||||
printf("%s\" },\n", $i);
|
||||
ok = 0;
|
||||
}
|
||||
}
|
||||
END {
|
||||
printf(" { NULL, 0, NULL }\n");
|
||||
printf("};\n");
|
||||
printf("\nprotected const el_bindings_t* help__get()");
|
||||
printf("{ return el_func_help; }\n");
|
||||
}'
|
||||
;;
|
||||
|
||||
# generate help.h from various .c files
|
||||
#
|
||||
-bh)
|
||||
$AWK '
|
||||
BEGIN {
|
||||
printf("/* Automatically generated file, do not edit */\n");
|
||||
printf("#ifndef _h_help_c\n#define _h_help_c\n");
|
||||
printf("protected const el_bindings_t *help__get(void);\n");
|
||||
printf("#endif /* _h_help_c */\n");
|
||||
}' /dev/null
|
||||
;;
|
||||
|
||||
# generate fcns.h from various .h files
|
||||
#
|
||||
-fh)
|
||||
cat $FILES | $AWK '/el_action_t/ { print $3 }' | \
|
||||
sort | tr '[:lower:]' '[:upper:]' | $AWK '
|
||||
BEGIN {
|
||||
printf("/* Automatically generated file, do not edit */\n");
|
||||
printf("#ifndef _h_fcns_c\n#define _h_fcns_c\n");
|
||||
count = 0;
|
||||
}
|
||||
{
|
||||
printf("#define\t%-30.30s\t%3d\n", $1, count++);
|
||||
}
|
||||
END {
|
||||
printf("#define\t%-30.30s\t%3d\n", "EL_NUM_FCNS", count);
|
||||
|
||||
printf("typedef el_action_t (*el_func_t)(EditLine *, int);");
|
||||
printf("\nprotected const el_func_t* func__get(void);\n");
|
||||
printf("#endif /* _h_fcns_c */\n");
|
||||
}'
|
||||
;;
|
||||
|
||||
# generate fcns.c from various .h files
|
||||
#
|
||||
-fc)
|
||||
cat $FILES | $AWK '/el_action_t/ { print $3 }' | sort | $AWK '
|
||||
BEGIN {
|
||||
printf("/* Automatically generated file, do not edit */\n");
|
||||
printf("#include \"sys.h\"\n#include \"el.h\"\n");
|
||||
printf("private const el_func_t el_func[] = {");
|
||||
maxlen = 80;
|
||||
needn = 1;
|
||||
len = 0;
|
||||
}
|
||||
{
|
||||
clen = 25 + 2;
|
||||
len += clen;
|
||||
if (len >= maxlen)
|
||||
needn = 1;
|
||||
if (needn) {
|
||||
printf("\n ");
|
||||
needn = 0;
|
||||
len = 4 + clen;
|
||||
}
|
||||
s = $1 ",";
|
||||
printf("%-26.26s ", s);
|
||||
}
|
||||
END {
|
||||
printf("\n};\n");
|
||||
printf("\nprotected const el_func_t* func__get() { return el_func; }\n");
|
||||
}'
|
||||
;;
|
||||
|
||||
# generate editline.c from various .c files
|
||||
#
|
||||
-e)
|
||||
echo "$FILES" | tr ' ' '\012' | $AWK '
|
||||
BEGIN {
|
||||
printf("/* Automatically generated file, do not edit */\n");
|
||||
printf("#define protected static\n");
|
||||
printf("#define SCCSID\n");
|
||||
}
|
||||
{
|
||||
printf("#include \"%s\"\n", $1);
|
||||
}'
|
||||
;;
|
||||
|
||||
# generate man page fragment from various .c files
|
||||
#
|
||||
-m)
|
||||
cat $FILES | $AWK '
|
||||
BEGIN {
|
||||
printf(".\\\" Section automatically generated with makelist\n");
|
||||
printf(".Bl -tag -width 4n\n");
|
||||
}
|
||||
/\(\):/ {
|
||||
pr = substr($2, 1, 2);
|
||||
if (pr == "vi" || pr == "em" || pr == "ed") {
|
||||
name = substr($2, 1, length($2) - 3);
|
||||
fname = "";
|
||||
for (i = 1; i <= length(name); i++) {
|
||||
s = substr(name, i, 1);
|
||||
if (s == "_")
|
||||
s = "-";
|
||||
fname = fname s;
|
||||
}
|
||||
|
||||
printf(".It Ic %s\n", fname);
|
||||
ok = 1;
|
||||
}
|
||||
}
|
||||
/^ \*/ {
|
||||
if (ok) {
|
||||
for (i = 2; i < NF; i++)
|
||||
printf("%s ", $i);
|
||||
printf("%s.\n", $i);
|
||||
ok = 0;
|
||||
}
|
||||
}
|
||||
END {
|
||||
printf(".El\n");
|
||||
printf(".\\\" End of section automatically generated with makelist\n");
|
||||
}'
|
||||
;;
|
||||
|
||||
*)
|
||||
echo $USAGE 1>&2
|
||||
exit 1
|
||||
;;
|
||||
|
||||
esac
|
1418
main/editline/map.c
1418
main/editline/map.c
File diff suppressed because it is too large
Load Diff
@@ -1,79 +0,0 @@
|
||||
/* $NetBSD: map.h,v 1.7 2002/03/18 16:00:56 christos Exp $ */
|
||||
|
||||
/*-
|
||||
* Copyright (c) 1992, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* This code is derived from software contributed to Berkeley by
|
||||
* Christos Zoulas of Cornell University.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
* 3. All advertising materials mentioning features or use of this software
|
||||
* must display the following acknowledgement:
|
||||
* This product includes software developed by the University of
|
||||
* California, Berkeley and its contributors.
|
||||
* 4. Neither the name of the University nor the names of its contributors
|
||||
* may be used to endorse or promote products derived from this software
|
||||
* without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
|
||||
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
* ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
|
||||
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
|
||||
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* @(#)map.h 8.1 (Berkeley) 6/4/93
|
||||
*/
|
||||
|
||||
/*
|
||||
* el.map.h: Editor maps
|
||||
*/
|
||||
#ifndef _h_el_map
|
||||
#define _h_el_map
|
||||
|
||||
typedef struct el_bindings_t { /* for the "bind" shell command */
|
||||
const char *name; /* function name for bind command */
|
||||
int func; /* function numeric value */
|
||||
const char *description; /* description of function */
|
||||
} el_bindings_t;
|
||||
|
||||
|
||||
typedef struct el_map_t {
|
||||
el_action_t *alt; /* The current alternate key map */
|
||||
el_action_t *key; /* The current normal key map */
|
||||
el_action_t *current; /* The keymap we are using */
|
||||
const el_action_t *emacs; /* The default emacs key map */
|
||||
const el_action_t *vic; /* The vi command mode key map */
|
||||
const el_action_t *vii; /* The vi insert mode key map */
|
||||
int type; /* Emacs or vi */
|
||||
el_bindings_t *help; /* The help for the editor functions */
|
||||
el_func_t *func; /* List of available functions */
|
||||
int nfunc; /* The number of functions/help items */
|
||||
} el_map_t;
|
||||
|
||||
#define MAP_EMACS 0
|
||||
#define MAP_VI 1
|
||||
|
||||
protected int map_bind(EditLine *, int, const char **);
|
||||
protected int map_init(EditLine *);
|
||||
protected void map_end(EditLine *);
|
||||
protected void map_init_vi(EditLine *);
|
||||
protected void map_init_emacs(EditLine *);
|
||||
protected int map_set_editor(EditLine *, char *);
|
||||
protected int map_get_editor(EditLine *, const char **);
|
||||
protected int map_addfunc(EditLine *, const char *, const char *, el_func_t);
|
||||
|
||||
#endif /* _h_el_map */
|
@@ -1,88 +0,0 @@
|
||||
/* $NetBSD: fgetln.c,v 1.1.1.1 1999/04/12 07:43:21 crooksa Exp $ */
|
||||
|
||||
/*-
|
||||
* Copyright (c) 1998 The NetBSD Foundation, Inc.
|
||||
* All rights reserved.
|
||||
*
|
||||
* This code is derived from software contributed to The NetBSD Foundation
|
||||
* by Christos Zoulas.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
* 3. All advertising materials mentioning features or use of this software
|
||||
* must display the following acknowledgement:
|
||||
* This product includes software developed by the NetBSD
|
||||
* Foundation, Inc. and its contributors.
|
||||
* 4. Neither the name of The NetBSD Foundation nor the names of its
|
||||
* contributors may be used to endorse or promote products derived
|
||||
* from this software without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS
|
||||
* ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
|
||||
* TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
|
||||
* PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS
|
||||
* BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
|
||||
* CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
|
||||
* SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
|
||||
* INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
|
||||
* CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
|
||||
* ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
|
||||
* POSSIBILITY OF SUCH DAMAGE.
|
||||
*/
|
||||
|
||||
#include "config.h"
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <unistd.h>
|
||||
#include <errno.h>
|
||||
#include <string.h>
|
||||
|
||||
char *
|
||||
fgetln(fp, len)
|
||||
FILE *fp;
|
||||
size_t *len;
|
||||
{
|
||||
static char *buf = NULL;
|
||||
static size_t bufsiz = 0;
|
||||
char *ptr;
|
||||
|
||||
|
||||
if (buf == NULL) {
|
||||
bufsiz = BUFSIZ;
|
||||
if ((buf = malloc(bufsiz)) == NULL)
|
||||
return NULL;
|
||||
}
|
||||
|
||||
if (fgets(buf, bufsiz, fp) == NULL)
|
||||
return NULL;
|
||||
*len = 0;
|
||||
|
||||
while ((ptr = strchr(&buf[*len], '\n')) == NULL) {
|
||||
size_t nbufsiz = bufsiz + BUFSIZ;
|
||||
char *nbuf = realloc(buf, nbufsiz);
|
||||
|
||||
if (nbuf == NULL) {
|
||||
int oerrno = errno;
|
||||
free(buf);
|
||||
errno = oerrno;
|
||||
buf = NULL;
|
||||
return NULL;
|
||||
} else
|
||||
buf = nbuf;
|
||||
|
||||
*len = bufsiz;
|
||||
if (fgets(&buf[bufsiz], BUFSIZ, fp) == NULL)
|
||||
return buf;
|
||||
|
||||
bufsiz = nbufsiz;
|
||||
}
|
||||
|
||||
*len = (ptr - buf) + 1;
|
||||
return buf;
|
||||
}
|
@@ -1,75 +0,0 @@
|
||||
/*
|
||||
* Copyright (c) 1998 Todd C. Miller <Todd.Miller@courtesan.com>
|
||||
* All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
* 3. The name of the author may not be used to endorse or promote products
|
||||
* derived from this software without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES,
|
||||
* INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY
|
||||
* AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL
|
||||
* THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
|
||||
* EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
|
||||
* PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS;
|
||||
* OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
|
||||
* WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
|
||||
* OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
|
||||
* ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
*/
|
||||
|
||||
#include "config.h"
|
||||
#if defined(LIBC_SCCS) && !defined(lint)
|
||||
static char *rcsid = "$OpenBSD: strlcat.c,v 1.2 1999/06/17 16:28:58 millert Exp $";
|
||||
#endif /* LIBC_SCCS and not lint */
|
||||
#ifndef lint
|
||||
static const char rcsid[] =
|
||||
"$FreeBSD: src/lib/libc/string/strlcat.c,v 1.2.4.2 2001/07/09 23:30:06 obrien Exp $";
|
||||
#endif
|
||||
|
||||
#include <sys/types.h>
|
||||
#include <string.h>
|
||||
|
||||
/*
|
||||
* Appends src to string dst of size siz (unlike strncat, siz is the
|
||||
* full size of dst, not space left). At most siz-1 characters
|
||||
* will be copied. Always NUL terminates (unless siz <= strlen(dst)).
|
||||
* Returns strlen(initial dst) + strlen(src); if retval >= siz,
|
||||
* truncation occurred.
|
||||
*/
|
||||
size_t strlcat(dst, src, siz)
|
||||
char *dst;
|
||||
const char *src;
|
||||
size_t siz;
|
||||
{
|
||||
register char *d = dst;
|
||||
register const char *s = src;
|
||||
register size_t n = siz;
|
||||
size_t dlen;
|
||||
|
||||
/* Find the end of dst and adjust bytes left but don't go past end */
|
||||
while (n-- != 0 && *d != '\0')
|
||||
d++;
|
||||
dlen = d - dst;
|
||||
n = siz - dlen;
|
||||
|
||||
if (n == 0)
|
||||
return(dlen + strlen(s));
|
||||
while (*s != '\0') {
|
||||
if (n != 1) {
|
||||
*d++ = *s;
|
||||
n--;
|
||||
}
|
||||
s++;
|
||||
}
|
||||
*d = '\0';
|
||||
|
||||
return(dlen + (s - src)); /* count does not include NUL */
|
||||
}
|
@@ -1,75 +0,0 @@
|
||||
/* $OpenBSD: strlcpy.c,v 1.4 1999/05/01 18:56:41 millert Exp $ */
|
||||
|
||||
/*
|
||||
* Copyright (c) 1998 Todd C. Miller <Todd.Miller@courtesan.com>
|
||||
* All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
* 3. The name of the author may not be used to endorse or promote products
|
||||
* derived from this software without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES,
|
||||
* INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY
|
||||
* AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL
|
||||
* THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
|
||||
* EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
|
||||
* PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS;
|
||||
* OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
|
||||
* WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
|
||||
* OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
|
||||
* ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
*/
|
||||
|
||||
#include "config.h"
|
||||
#if defined(LIBC_SCCS) && !defined(lint)
|
||||
#if 0
|
||||
static char *rcsid = "$OpenBSD: strlcpy.c,v 1.4 1999/05/01 18:56:41 millert Exp $";
|
||||
#endif
|
||||
#endif /* LIBC_SCCS and not lint */
|
||||
#ifndef lint
|
||||
static const char rcsid[] =
|
||||
"$FreeBSD: src/lib/libc/string/strlcpy.c,v 1.2.4.1 2001/07/09 23:30:06 obrien Exp $";
|
||||
#endif
|
||||
|
||||
#include <sys/types.h>
|
||||
#include <string.h>
|
||||
|
||||
/*
|
||||
* Copy src to string dst of size siz. At most siz-1 characters
|
||||
* will be copied. Always NUL terminates (unless siz == 0).
|
||||
* Returns strlen(src); if retval >= siz, truncation occurred.
|
||||
*/
|
||||
size_t strlcpy(dst, src, siz)
|
||||
char *dst;
|
||||
const char *src;
|
||||
size_t siz;
|
||||
{
|
||||
register char *d = dst;
|
||||
register const char *s = src;
|
||||
register size_t n = siz;
|
||||
|
||||
/* Copy as many bytes as will fit */
|
||||
if (n != 0 && --n != 0) {
|
||||
do {
|
||||
if ((*d++ = *s++) == 0)
|
||||
break;
|
||||
} while (--n != 0);
|
||||
}
|
||||
|
||||
/* Not enough room in dst, add NUL and traverse rest of src */
|
||||
if (n == 0) {
|
||||
if (siz != 0)
|
||||
*d = '\0'; /* NUL-terminate dst */
|
||||
while (*s++)
|
||||
;
|
||||
}
|
||||
|
||||
return(s - src - 1); /* count does not include NUL */
|
||||
}
|
@@ -1,322 +0,0 @@
|
||||
/* $NetBSD: unvis.c,v 1.22 2002/03/23 17:38:27 christos Exp $ */
|
||||
|
||||
/*-
|
||||
* Copyright (c) 1989, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
* 3. All advertising materials mentioning features or use of this software
|
||||
* must display the following acknowledgement:
|
||||
* This product includes software developed by the University of
|
||||
* California, Berkeley and its contributors.
|
||||
* 4. Neither the name of the University nor the names of its contributors
|
||||
* may be used to endorse or promote products derived from this software
|
||||
* without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
|
||||
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
* ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
|
||||
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
|
||||
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*/
|
||||
|
||||
#include <sys/cdefs.h>
|
||||
#if defined(LIBC_SCCS) && !defined(lint)
|
||||
#if 0
|
||||
static char sccsid[] = "@(#)unvis.c 8.1 (Berkeley) 6/4/93";
|
||||
#else
|
||||
__RCSID("$NetBSD: unvis.c,v 1.22 2002/03/23 17:38:27 christos Exp $");
|
||||
#endif
|
||||
#endif /* LIBC_SCCS and not lint */
|
||||
|
||||
#define __LIBC12_SOURCE__
|
||||
|
||||
#include <sys/types.h>
|
||||
|
||||
#include <assert.h>
|
||||
#include <ctype.h>
|
||||
#include <stdio.h>
|
||||
#include "np/vis.h"
|
||||
|
||||
#ifdef __weak_alias
|
||||
__weak_alias(strunvis,_strunvis)
|
||||
__weak_alias(unvis,_unvis)
|
||||
#endif
|
||||
|
||||
#ifdef __warn_references
|
||||
__warn_references(unvis,
|
||||
"warning: reference to compatibility unvis(); include <vis.h> for correct reference")
|
||||
#endif
|
||||
|
||||
#ifndef HAVE_VIS_H
|
||||
/*
|
||||
* decode driven by state machine
|
||||
*/
|
||||
#define S_GROUND 0 /* haven't seen escape char */
|
||||
#define S_START 1 /* start decoding special sequence */
|
||||
#define S_META 2 /* metachar started (M) */
|
||||
#define S_META1 3 /* metachar more, regular char (-) */
|
||||
#define S_CTRL 4 /* control char started (^) */
|
||||
#define S_OCTAL2 5 /* octal digit 2 */
|
||||
#define S_OCTAL3 6 /* octal digit 3 */
|
||||
#define S_HEX1 7 /* hex digit */
|
||||
#define S_HEX2 8 /* hex digit 2 */
|
||||
|
||||
#define isoctal(c) (((u_char)(c)) >= '0' && ((u_char)(c)) <= '7')
|
||||
#define xtod(c) (isdigit(c) ? (c - '0') : ((tolower(c) - 'a') + 10))
|
||||
|
||||
int
|
||||
unvis(cp, c, astate, flag)
|
||||
char *cp;
|
||||
int c;
|
||||
int *astate, flag;
|
||||
{
|
||||
return __unvis13(cp, (int)c, astate, flag);
|
||||
}
|
||||
|
||||
/*
|
||||
* unvis - decode characters previously encoded by vis
|
||||
*/
|
||||
int
|
||||
__unvis13(cp, c, astate, flag)
|
||||
char *cp;
|
||||
int c;
|
||||
int *astate, flag;
|
||||
{
|
||||
|
||||
_DIAGASSERT(cp != NULL);
|
||||
_DIAGASSERT(astate != NULL);
|
||||
|
||||
if (flag & UNVIS_END) {
|
||||
if (*astate == S_OCTAL2 || *astate == S_OCTAL3
|
||||
|| *astate == S_HEX2) {
|
||||
*astate = S_GROUND;
|
||||
return (UNVIS_VALID);
|
||||
}
|
||||
return (*astate == S_GROUND ? UNVIS_NOCHAR : UNVIS_SYNBAD);
|
||||
}
|
||||
|
||||
switch (*astate) {
|
||||
|
||||
case S_GROUND:
|
||||
*cp = 0;
|
||||
if (c == '\\') {
|
||||
*astate = S_START;
|
||||
return (0);
|
||||
}
|
||||
if ((flag & VIS_HTTPSTYLE) && c == '%') {
|
||||
*astate = S_HEX1;
|
||||
return (0);
|
||||
}
|
||||
*cp = c;
|
||||
return (UNVIS_VALID);
|
||||
|
||||
case S_START:
|
||||
switch(c) {
|
||||
case '\\':
|
||||
*cp = c;
|
||||
*astate = S_GROUND;
|
||||
return (UNVIS_VALID);
|
||||
case '0': case '1': case '2': case '3':
|
||||
case '4': case '5': case '6': case '7':
|
||||
*cp = (c - '0');
|
||||
*astate = S_OCTAL2;
|
||||
return (0);
|
||||
case 'M':
|
||||
*cp = (char)0200;
|
||||
*astate = S_META;
|
||||
return (0);
|
||||
case '^':
|
||||
*astate = S_CTRL;
|
||||
return (0);
|
||||
case 'n':
|
||||
*cp = '\n';
|
||||
*astate = S_GROUND;
|
||||
return (UNVIS_VALID);
|
||||
case 'r':
|
||||
*cp = '\r';
|
||||
*astate = S_GROUND;
|
||||
return (UNVIS_VALID);
|
||||
case 'b':
|
||||
*cp = '\b';
|
||||
*astate = S_GROUND;
|
||||
return (UNVIS_VALID);
|
||||
case 'a':
|
||||
*cp = '\007';
|
||||
*astate = S_GROUND;
|
||||
return (UNVIS_VALID);
|
||||
case 'v':
|
||||
*cp = '\v';
|
||||
*astate = S_GROUND;
|
||||
return (UNVIS_VALID);
|
||||
case 't':
|
||||
*cp = '\t';
|
||||
*astate = S_GROUND;
|
||||
return (UNVIS_VALID);
|
||||
case 'f':
|
||||
*cp = '\f';
|
||||
*astate = S_GROUND;
|
||||
return (UNVIS_VALID);
|
||||
case 's':
|
||||
*cp = ' ';
|
||||
*astate = S_GROUND;
|
||||
return (UNVIS_VALID);
|
||||
case 'E':
|
||||
*cp = '\033';
|
||||
*astate = S_GROUND;
|
||||
return (UNVIS_VALID);
|
||||
case '\n':
|
||||
/*
|
||||
* hidden newline
|
||||
*/
|
||||
*astate = S_GROUND;
|
||||
return (UNVIS_NOCHAR);
|
||||
case '$':
|
||||
/*
|
||||
* hidden marker
|
||||
*/
|
||||
*astate = S_GROUND;
|
||||
return (UNVIS_NOCHAR);
|
||||
}
|
||||
*astate = S_GROUND;
|
||||
return (UNVIS_SYNBAD);
|
||||
|
||||
case S_META:
|
||||
if (c == '-')
|
||||
*astate = S_META1;
|
||||
else if (c == '^')
|
||||
*astate = S_CTRL;
|
||||
else {
|
||||
*astate = S_GROUND;
|
||||
return (UNVIS_SYNBAD);
|
||||
}
|
||||
return (0);
|
||||
|
||||
case S_META1:
|
||||
*astate = S_GROUND;
|
||||
*cp |= c;
|
||||
return (UNVIS_VALID);
|
||||
|
||||
case S_CTRL:
|
||||
if (c == '?')
|
||||
*cp |= 0177;
|
||||
else
|
||||
*cp |= c & 037;
|
||||
*astate = S_GROUND;
|
||||
return (UNVIS_VALID);
|
||||
|
||||
case S_OCTAL2: /* second possible octal digit */
|
||||
if (isoctal(c)) {
|
||||
/*
|
||||
* yes - and maybe a third
|
||||
*/
|
||||
*cp = (*cp << 3) + (c - '0');
|
||||
*astate = S_OCTAL3;
|
||||
return (0);
|
||||
}
|
||||
/*
|
||||
* no - done with current sequence, push back passed char
|
||||
*/
|
||||
*astate = S_GROUND;
|
||||
return (UNVIS_VALIDPUSH);
|
||||
|
||||
case S_OCTAL3: /* third possible octal digit */
|
||||
*astate = S_GROUND;
|
||||
if (isoctal(c)) {
|
||||
*cp = (*cp << 3) + (c - '0');
|
||||
return (UNVIS_VALID);
|
||||
}
|
||||
/*
|
||||
* we were done, push back passed char
|
||||
*/
|
||||
return (UNVIS_VALIDPUSH);
|
||||
case S_HEX1:
|
||||
if (isxdigit(c)) {
|
||||
*cp = xtod(c);
|
||||
*astate = S_HEX2;
|
||||
return (0);
|
||||
}
|
||||
/*
|
||||
* no - done with current sequence, push back passed char
|
||||
*/
|
||||
*astate = S_GROUND;
|
||||
return (UNVIS_VALIDPUSH);
|
||||
case S_HEX2:
|
||||
*astate = S_GROUND;
|
||||
if (isxdigit(c)) {
|
||||
*cp = xtod(c) | (*cp << 4);
|
||||
return (UNVIS_VALID);
|
||||
}
|
||||
return (UNVIS_VALIDPUSH);
|
||||
default:
|
||||
/*
|
||||
* decoder in unknown state - (probably uninitialized)
|
||||
*/
|
||||
*astate = S_GROUND;
|
||||
return (UNVIS_SYNBAD);
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
* strunvis - decode src into dst
|
||||
*
|
||||
* Number of chars decoded into dst is returned, -1 on error.
|
||||
* Dst is null terminated.
|
||||
*/
|
||||
|
||||
int
|
||||
strunvisx(dst, src, flag)
|
||||
char *dst;
|
||||
const char *src;
|
||||
int flag;
|
||||
{
|
||||
char c;
|
||||
char *start = dst;
|
||||
int state = 0;
|
||||
|
||||
_DIAGASSERT(src != NULL);
|
||||
_DIAGASSERT(dst != NULL);
|
||||
|
||||
while ((c = *src++) != '\0') {
|
||||
again:
|
||||
switch (__unvis13(dst, c, &state, flag)) {
|
||||
case UNVIS_VALID:
|
||||
dst++;
|
||||
break;
|
||||
case UNVIS_VALIDPUSH:
|
||||
dst++;
|
||||
goto again;
|
||||
case 0:
|
||||
case UNVIS_NOCHAR:
|
||||
break;
|
||||
default:
|
||||
return (-1);
|
||||
}
|
||||
}
|
||||
if (__unvis13(dst, c, &state, UNVIS_END) == UNVIS_VALID)
|
||||
dst++;
|
||||
*dst = '\0';
|
||||
return (dst - start);
|
||||
}
|
||||
|
||||
int
|
||||
strunvis(dst, src)
|
||||
char *dst;
|
||||
const char *src;
|
||||
{
|
||||
return strunvisx(dst, src, 0);
|
||||
}
|
||||
#endif
|
@@ -1,348 +0,0 @@
|
||||
/* $NetBSD: vis.c,v 1.22 2002/03/23 17:38:27 christos Exp $ */
|
||||
|
||||
/*-
|
||||
* Copyright (c) 1999 The NetBSD Foundation, Inc.
|
||||
* Copyright (c) 1989, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
* 3. All advertising materials mentioning features or use of this software
|
||||
* must display the following acknowledgement:
|
||||
* This product includes software developed by the University of
|
||||
* California, Berkeley and its contributors.
|
||||
* 4. Neither the name of the University nor the names of its contributors
|
||||
* may be used to endorse or promote products derived from this software
|
||||
* without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
|
||||
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
* ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
|
||||
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
|
||||
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*/
|
||||
|
||||
#include <sys/cdefs.h>
|
||||
#if defined(LIBC_SCCS) && !defined(lint)
|
||||
__RCSID("$NetBSD: vis.c,v 1.22 2002/03/23 17:38:27 christos Exp $");
|
||||
#endif /* LIBC_SCCS and not lint */
|
||||
|
||||
#include <sys/types.h>
|
||||
|
||||
#include <assert.h>
|
||||
#include "np/vis.h"
|
||||
#include <stdlib.h>
|
||||
#include <stdint.h>
|
||||
|
||||
#ifdef __weak_alias
|
||||
__weak_alias(strsvis,_strsvis)
|
||||
__weak_alias(strsvisx,_strsvisx)
|
||||
__weak_alias(strvis,_strvis)
|
||||
__weak_alias(strvisx,_strvisx)
|
||||
__weak_alias(svis,_svis)
|
||||
__weak_alias(vis,_vis)
|
||||
#endif
|
||||
|
||||
#ifndef HAVE_VIS_H
|
||||
#include <ctype.h>
|
||||
#include <limits.h>
|
||||
#include <stdio.h>
|
||||
#include <string.h>
|
||||
|
||||
#undef BELL
|
||||
#if defined(__STDC__)
|
||||
#define BELL '\a'
|
||||
#else
|
||||
#define BELL '\007'
|
||||
#endif
|
||||
|
||||
#ifdef SOLARIS
|
||||
#include <alloca.h>
|
||||
#endif
|
||||
|
||||
#define isoctal(c) (((u_char)(c)) >= '0' && ((u_char)(c)) <= '7')
|
||||
#define iswhite(c) (c == ' ' || c == '\t' || c == '\n')
|
||||
#define issafe(c) (c == '\b' || c == BELL || c == '\r')
|
||||
#define xtoa(c) "0123456789abcdef"[c]
|
||||
|
||||
#define MAXEXTRAS 5
|
||||
|
||||
|
||||
#define MAKEEXTRALIST(flag, extra, orig) \
|
||||
do { \
|
||||
const char *o = orig; \
|
||||
char *e; \
|
||||
while (*o++) \
|
||||
continue; \
|
||||
extra = alloca((size_t)((o - orig) + MAXEXTRAS)); \
|
||||
for (o = orig, e = extra; (*e++ = *o++) != '\0';) \
|
||||
continue; \
|
||||
e--; \
|
||||
if (flag & VIS_SP) *e++ = ' '; \
|
||||
if (flag & VIS_TAB) *e++ = '\t'; \
|
||||
if (flag & VIS_NL) *e++ = '\n'; \
|
||||
if ((flag & VIS_NOSLASH) == 0) *e++ = '\\'; \
|
||||
*e = '\0'; \
|
||||
} while (/*CONSTCOND*/0)
|
||||
|
||||
|
||||
/*
|
||||
* This is HVIS, the macro of vis used to HTTP style (RFC 1808)
|
||||
*/
|
||||
#define HVIS(dst, c, flag, nextc, extra) \
|
||||
do \
|
||||
if (!isascii(c) || !isalnum(c) || strchr("$-_.+!*'(),", c) != NULL) { \
|
||||
*dst++ = '%'; \
|
||||
*dst++ = xtoa(((unsigned int)c >> 4) & 0xf); \
|
||||
*dst++ = xtoa((unsigned int)c & 0xf); \
|
||||
} else { \
|
||||
SVIS(dst, c, flag, nextc, extra); \
|
||||
} \
|
||||
while (/*CONSTCOND*/0)
|
||||
|
||||
/*
|
||||
* This is SVIS, the central macro of vis.
|
||||
* dst: Pointer to the destination buffer
|
||||
* c: Character to encode
|
||||
* flag: Flag word
|
||||
* nextc: The character following 'c'
|
||||
* extra: Pointer to the list of extra characters to be
|
||||
* backslash-protected.
|
||||
*/
|
||||
#define SVIS(dst, c, flag, nextc, extra) \
|
||||
do { \
|
||||
int isextra, isc; \
|
||||
isextra = strchr(extra, c) != NULL; \
|
||||
if (!isextra && isascii(c) && (isgraph(c) || iswhite(c) || \
|
||||
((flag & VIS_SAFE) && issafe(c)))) { \
|
||||
*dst++ = c; \
|
||||
break; \
|
||||
} \
|
||||
isc = 0; \
|
||||
if (flag & VIS_CSTYLE) { \
|
||||
switch (c) { \
|
||||
case '\n': \
|
||||
isc = 1; *dst++ = '\\'; *dst++ = 'n'; \
|
||||
break; \
|
||||
case '\r': \
|
||||
isc = 1; *dst++ = '\\'; *dst++ = 'r'; \
|
||||
break; \
|
||||
case '\b': \
|
||||
isc = 1; *dst++ = '\\'; *dst++ = 'b'; \
|
||||
break; \
|
||||
case BELL: \
|
||||
isc = 1; *dst++ = '\\'; *dst++ = 'a'; \
|
||||
break; \
|
||||
case '\v': \
|
||||
isc = 1; *dst++ = '\\'; *dst++ = 'v'; \
|
||||
break; \
|
||||
case '\t': \
|
||||
isc = 1; *dst++ = '\\'; *dst++ = 't'; \
|
||||
break; \
|
||||
case '\f': \
|
||||
isc = 1; *dst++ = '\\'; *dst++ = 'f'; \
|
||||
break; \
|
||||
case ' ': \
|
||||
isc = 1; *dst++ = '\\'; *dst++ = 's'; \
|
||||
break; \
|
||||
case '\0': \
|
||||
isc = 1; *dst++ = '\\'; *dst++ = '0'; \
|
||||
if (isoctal(nextc)) { \
|
||||
*dst++ = '0'; \
|
||||
*dst++ = '0'; \
|
||||
} \
|
||||
} \
|
||||
} \
|
||||
if (isc) break; \
|
||||
if (isextra || ((c & 0177) == ' ') || (flag & VIS_OCTAL)) { \
|
||||
*dst++ = '\\'; \
|
||||
*dst++ = (u_char)(((uint32_t)(u_char)c >> 6) & 03) + '0'; \
|
||||
*dst++ = (u_char)(((uint32_t)(u_char)c >> 3) & 07) + '0'; \
|
||||
*dst++ = (c & 07) + '0'; \
|
||||
} else { \
|
||||
if ((flag & VIS_NOSLASH) == 0) *dst++ = '\\'; \
|
||||
if (c & 0200) { \
|
||||
c &= 0177; *dst++ = 'M'; \
|
||||
} \
|
||||
if (iscntrl(c)) { \
|
||||
*dst++ = '^'; \
|
||||
if (c == 0177) \
|
||||
*dst++ = '?'; \
|
||||
else \
|
||||
*dst++ = c + '@'; \
|
||||
} else { \
|
||||
*dst++ = '-'; *dst++ = c; \
|
||||
} \
|
||||
} \
|
||||
} while (/*CONSTCOND*/0)
|
||||
|
||||
|
||||
/*
|
||||
* svis - visually encode characters, also encoding the characters
|
||||
* pointed to by `extra'
|
||||
*/
|
||||
char *
|
||||
svis(dst, c, flag, nextc, extra)
|
||||
char *dst;
|
||||
int c, flag, nextc;
|
||||
const char *extra;
|
||||
{
|
||||
char *nextra;
|
||||
_DIAGASSERT(dst != NULL);
|
||||
_DIAGASSERT(extra != NULL);
|
||||
MAKEEXTRALIST(flag, nextra, extra);
|
||||
if (flag & VIS_HTTPSTYLE)
|
||||
HVIS(dst, c, flag, nextc, nextra);
|
||||
else
|
||||
SVIS(dst, c, flag, nextc, nextra);
|
||||
*dst = '\0';
|
||||
return(dst);
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
* strsvis, strsvisx - visually encode characters from src into dst
|
||||
*
|
||||
* Extra is a pointer to a \0-terminated list of characters to
|
||||
* be encoded, too. These functions are useful e. g. to
|
||||
* encode strings in such a way so that they are not interpreted
|
||||
* by a shell.
|
||||
*
|
||||
* Dst must be 4 times the size of src to account for possible
|
||||
* expansion. The length of dst, not including the trailing NULL,
|
||||
* is returned.
|
||||
*
|
||||
* Strsvisx encodes exactly len bytes from src into dst.
|
||||
* This is useful for encoding a block of data.
|
||||
*/
|
||||
int
|
||||
strsvis(dst, src, flag, extra)
|
||||
char *dst;
|
||||
const char *src;
|
||||
int flag;
|
||||
const char *extra;
|
||||
{
|
||||
char c;
|
||||
char *start;
|
||||
char *nextra;
|
||||
|
||||
_DIAGASSERT(dst != NULL);
|
||||
_DIAGASSERT(src != NULL);
|
||||
_DIAGASSERT(extra != NULL);
|
||||
MAKEEXTRALIST(flag, nextra, extra);
|
||||
if (flag & VIS_HTTPSTYLE) {
|
||||
for (start = dst; (c = *src++) != '\0'; /* empty */)
|
||||
HVIS(dst, c, flag, *src, nextra);
|
||||
} else {
|
||||
for (start = dst; (c = *src++) != '\0'; /* empty */)
|
||||
SVIS(dst, c, flag, *src, nextra);
|
||||
}
|
||||
*dst = '\0';
|
||||
return (dst - start);
|
||||
}
|
||||
|
||||
|
||||
int
|
||||
strsvisx(dst, src, len, flag, extra)
|
||||
char *dst;
|
||||
const char *src;
|
||||
size_t len;
|
||||
int flag;
|
||||
const char *extra;
|
||||
{
|
||||
char c;
|
||||
char *start;
|
||||
char *nextra;
|
||||
|
||||
_DIAGASSERT(dst != NULL);
|
||||
_DIAGASSERT(src != NULL);
|
||||
_DIAGASSERT(extra != NULL);
|
||||
MAKEEXTRALIST(flag, nextra, extra);
|
||||
|
||||
if (flag & VIS_HTTPSTYLE) {
|
||||
for (start = dst; len > 0; len--) {
|
||||
c = *src++;
|
||||
HVIS(dst, c, flag, len ? *src : '\0', nextra);
|
||||
}
|
||||
} else {
|
||||
for (start = dst; len > 0; len--) {
|
||||
c = *src++;
|
||||
SVIS(dst, c, flag, len ? *src : '\0', nextra);
|
||||
}
|
||||
}
|
||||
*dst = '\0';
|
||||
return (dst - start);
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
* vis - visually encode characters
|
||||
*/
|
||||
char *
|
||||
vis(dst, c, flag, nextc)
|
||||
char *dst;
|
||||
int c, flag, nextc;
|
||||
|
||||
{
|
||||
char *extra;
|
||||
|
||||
_DIAGASSERT(dst != NULL);
|
||||
|
||||
MAKEEXTRALIST(flag, extra, "");
|
||||
if (flag & VIS_HTTPSTYLE)
|
||||
HVIS(dst, c, flag, nextc, extra);
|
||||
else
|
||||
SVIS(dst, c, flag, nextc, extra);
|
||||
*dst = '\0';
|
||||
return (dst);
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
* strvis, strvisx - visually encode characters from src into dst
|
||||
*
|
||||
* Dst must be 4 times the size of src to account for possible
|
||||
* expansion. The length of dst, not including the trailing NULL,
|
||||
* is returned.
|
||||
*
|
||||
* Strvisx encodes exactly len bytes from src into dst.
|
||||
* This is useful for encoding a block of data.
|
||||
*/
|
||||
int
|
||||
strvis(dst, src, flag)
|
||||
char *dst;
|
||||
const char *src;
|
||||
int flag;
|
||||
{
|
||||
char *extra;
|
||||
|
||||
MAKEEXTRALIST(flag, extra, "");
|
||||
return (strsvis(dst, src, flag, extra));
|
||||
}
|
||||
|
||||
|
||||
int
|
||||
strvisx(dst, src, len, flag)
|
||||
char *dst;
|
||||
const char *src;
|
||||
size_t len;
|
||||
int flag;
|
||||
{
|
||||
char *extra;
|
||||
|
||||
MAKEEXTRALIST(flag, extra, "");
|
||||
return (strsvisx(dst, src, len, flag, extra));
|
||||
}
|
||||
#endif
|
@@ -1,96 +0,0 @@
|
||||
/* $NetBSD: vis.h,v 1.12 2002/03/23 17:39:05 christos Exp $ */
|
||||
|
||||
/*-
|
||||
* Copyright (c) 1990, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
* 3. All advertising materials mentioning features or use of this software
|
||||
* must display the following acknowledgement:
|
||||
* This product includes software developed by the University of
|
||||
* California, Berkeley and its contributors.
|
||||
* 4. Neither the name of the University nor the names of its contributors
|
||||
* may be used to endorse or promote products derived from this software
|
||||
* without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
|
||||
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
* ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
|
||||
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
|
||||
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* @(#)vis.h 8.1 (Berkeley) 6/2/93
|
||||
*/
|
||||
|
||||
#ifndef _VIS_H_
|
||||
#define _VIS_H_
|
||||
|
||||
/*
|
||||
* to select alternate encoding format
|
||||
*/
|
||||
#define VIS_OCTAL 0x01 /* use octal \ddd format */
|
||||
#define VIS_CSTYLE 0x02 /* use \[nrft0..] where appropiate */
|
||||
|
||||
/*
|
||||
* to alter set of characters encoded (default is to encode all
|
||||
* non-graphic except space, tab, and newline).
|
||||
*/
|
||||
#define VIS_SP 0x04 /* also encode space */
|
||||
#define VIS_TAB 0x08 /* also encode tab */
|
||||
#define VIS_NL 0x10 /* also encode newline */
|
||||
#define VIS_WHITE (VIS_SP | VIS_TAB | VIS_NL)
|
||||
#define VIS_SAFE 0x20 /* only encode "unsafe" characters */
|
||||
|
||||
/*
|
||||
* other
|
||||
*/
|
||||
#define VIS_NOSLASH 0x40 /* inhibit printing '\' */
|
||||
#define VIS_HTTPSTYLE 0x80 /* http-style escape % HEX HEX */
|
||||
|
||||
/*
|
||||
* unvis return codes
|
||||
*/
|
||||
#define UNVIS_VALID 1 /* character valid */
|
||||
#define UNVIS_VALIDPUSH 2 /* character valid, push back passed char */
|
||||
#define UNVIS_NOCHAR 3 /* valid sequence, no character produced */
|
||||
#define UNVIS_SYNBAD -1 /* unrecognized escape sequence */
|
||||
#define UNVIS_ERROR -2 /* decoder in unknown state (unrecoverable) */
|
||||
|
||||
/*
|
||||
* unvis flags
|
||||
*/
|
||||
#define UNVIS_END 1 /* no more characters */
|
||||
|
||||
#include <sys/cdefs.h>
|
||||
|
||||
__BEGIN_DECLS
|
||||
char *vis __P((char *, int, int, int));
|
||||
char *svis __P((char *, int, int, int, const char *));
|
||||
int strvis __P((char *, const char *, int));
|
||||
int strsvis __P((char *, const char *, int, const char *));
|
||||
int strvisx __P((char *, const char *, size_t, int));
|
||||
int strsvisx __P((char *, const char *, size_t, int, const char *));
|
||||
int strunvis __P((char *, const char *));
|
||||
int strunvisx __P((char *, const char *, int));
|
||||
#ifdef __LIBC12_SOURCE__
|
||||
int unvis __P((char *, int, int *, int));
|
||||
int __unvis13 __P((char *, int, int *, int));
|
||||
#else
|
||||
int unvis __P((char *, int, int *, int)) __RENAME(__unvis13);
|
||||
#endif
|
||||
__END_DECLS
|
||||
|
||||
#endif /* !_VIS_H_ */
|
@@ -1,259 +0,0 @@
|
||||
/* $NetBSD: parse.c,v 1.15 2002/03/18 16:00:56 christos Exp $ */
|
||||
|
||||
/*-
|
||||
* Copyright (c) 1992, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* This code is derived from software contributed to Berkeley by
|
||||
* Christos Zoulas of Cornell University.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
* 3. All advertising materials mentioning features or use of this software
|
||||
* must display the following acknowledgement:
|
||||
* This product includes software developed by the University of
|
||||
* California, Berkeley and its contributors.
|
||||
* 4. Neither the name of the University nor the names of its contributors
|
||||
* may be used to endorse or promote products derived from this software
|
||||
* without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
|
||||
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
* ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
|
||||
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
|
||||
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*/
|
||||
|
||||
#include "config.h"
|
||||
#if !defined(lint) && !defined(SCCSID)
|
||||
#if 0
|
||||
static char sccsid[] = "@(#)parse.c 8.1 (Berkeley) 6/4/93";
|
||||
#else
|
||||
__RCSID("$NetBSD: parse.c,v 1.15 2002/03/18 16:00:56 christos Exp $");
|
||||
#endif
|
||||
#endif /* not lint && not SCCSID */
|
||||
|
||||
/*
|
||||
* parse.c: parse an editline extended command
|
||||
*
|
||||
* commands are:
|
||||
*
|
||||
* bind
|
||||
* echotc
|
||||
* edit
|
||||
* gettc
|
||||
* history
|
||||
* settc
|
||||
* setty
|
||||
*/
|
||||
#include "el.h"
|
||||
#include "tokenizer.h"
|
||||
#include <stdlib.h>
|
||||
|
||||
private const struct {
|
||||
const char *name;
|
||||
int (*func)(EditLine *, int, const char **);
|
||||
} cmds[] = {
|
||||
{ "bind", map_bind },
|
||||
{ "echotc", term_echotc },
|
||||
{ "edit", el_editmode },
|
||||
{ "history", hist_list },
|
||||
{ "telltc", term_telltc },
|
||||
{ "settc", term_settc },
|
||||
{ "setty", tty_stty },
|
||||
{ NULL, NULL }
|
||||
};
|
||||
|
||||
|
||||
/* parse_line():
|
||||
* Parse a line and dispatch it
|
||||
*/
|
||||
protected int
|
||||
parse_line(EditLine *el, const char *line)
|
||||
{
|
||||
const char **argv;
|
||||
int argc;
|
||||
Tokenizer *tok;
|
||||
|
||||
tok = tok_init(NULL);
|
||||
tok_line(tok, line, &argc, &argv);
|
||||
argc = el_parse(el, argc, argv);
|
||||
tok_end(tok);
|
||||
return (argc);
|
||||
}
|
||||
|
||||
|
||||
/* el_parse():
|
||||
* Command dispatcher
|
||||
*/
|
||||
public int
|
||||
el_parse(EditLine *el, int argc, const char *argv[])
|
||||
{
|
||||
const char *ptr;
|
||||
int i;
|
||||
|
||||
if (argc < 1)
|
||||
return (-1);
|
||||
ptr = strchr(argv[0], ':');
|
||||
if (ptr != NULL) {
|
||||
char *tprog;
|
||||
size_t l;
|
||||
|
||||
if (ptr == argv[0])
|
||||
return (0);
|
||||
l = ptr - argv[0] - 1;
|
||||
tprog = (char *) el_malloc(l + 1);
|
||||
if (tprog == NULL)
|
||||
return (0);
|
||||
(void) strncpy(tprog, argv[0], l);
|
||||
tprog[l] = '\0';
|
||||
ptr++;
|
||||
l = el_match(el->el_prog, tprog);
|
||||
el_free(tprog);
|
||||
if (!l)
|
||||
return (0);
|
||||
} else
|
||||
ptr = argv[0];
|
||||
|
||||
for (i = 0; cmds[i].name != NULL; i++)
|
||||
if (strcmp(cmds[i].name, ptr) == 0) {
|
||||
i = (*cmds[i].func) (el, argc, argv);
|
||||
return (-i);
|
||||
}
|
||||
return (-1);
|
||||
}
|
||||
|
||||
|
||||
/* parse__escape():
|
||||
* Parse a string of the form ^<char> \<odigit> \<char> and return
|
||||
* the appropriate character or -1 if the escape is not valid
|
||||
*/
|
||||
protected int
|
||||
parse__escape(const char **const ptr)
|
||||
{
|
||||
const char *p;
|
||||
int c;
|
||||
|
||||
p = *ptr;
|
||||
|
||||
if (p[1] == 0)
|
||||
return (-1);
|
||||
|
||||
if (*p == '\\') {
|
||||
p++;
|
||||
switch (*p) {
|
||||
case 'a':
|
||||
c = '\007'; /* Bell */
|
||||
break;
|
||||
case 'b':
|
||||
c = '\010'; /* Backspace */
|
||||
break;
|
||||
case 't':
|
||||
c = '\011'; /* Horizontal Tab */
|
||||
break;
|
||||
case 'n':
|
||||
c = '\012'; /* New Line */
|
||||
break;
|
||||
case 'v':
|
||||
c = '\013'; /* Vertical Tab */
|
||||
break;
|
||||
case 'f':
|
||||
c = '\014'; /* Form Feed */
|
||||
break;
|
||||
case 'r':
|
||||
c = '\015'; /* Carriage Return */
|
||||
break;
|
||||
case 'e':
|
||||
c = '\033'; /* Escape */
|
||||
break;
|
||||
case '0':
|
||||
case '1':
|
||||
case '2':
|
||||
case '3':
|
||||
case '4':
|
||||
case '5':
|
||||
case '6':
|
||||
case '7':
|
||||
{
|
||||
int cnt, ch;
|
||||
|
||||
for (cnt = 0, c = 0; cnt < 3; cnt++) {
|
||||
ch = *p++;
|
||||
if (ch < '0' || ch > '7') {
|
||||
p--;
|
||||
break;
|
||||
}
|
||||
c = (c << 3) | (ch - '0');
|
||||
}
|
||||
if ((c & 0xffffff00) != 0)
|
||||
return (-1);
|
||||
--p;
|
||||
break;
|
||||
}
|
||||
default:
|
||||
c = *p;
|
||||
break;
|
||||
}
|
||||
} else if (*p == '^' && isalpha((unsigned char) p[1])) {
|
||||
p++;
|
||||
c = (*p == '?') ? '\177' : (*p & 0237);
|
||||
} else
|
||||
c = *p;
|
||||
*ptr = ++p;
|
||||
return (c);
|
||||
}
|
||||
/* parse__string():
|
||||
* Parse the escapes from in and put the raw string out
|
||||
*/
|
||||
protected char *
|
||||
parse__string(char *out, const char *in)
|
||||
{
|
||||
char *rv = out;
|
||||
int n;
|
||||
|
||||
for (;;)
|
||||
switch (*in) {
|
||||
case '\0':
|
||||
*out = '\0';
|
||||
return (rv);
|
||||
|
||||
case '\\':
|
||||
case '^':
|
||||
if ((n = parse__escape(&in)) == -1)
|
||||
return (NULL);
|
||||
*out++ = n;
|
||||
break;
|
||||
|
||||
default:
|
||||
*out++ = *in++;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/* parse_cmd():
|
||||
* Return the command number for the command string given
|
||||
* or -1 if one is not found
|
||||
*/
|
||||
protected int
|
||||
parse_cmd(EditLine *el, const char *cmd)
|
||||
{
|
||||
el_bindings_t *b;
|
||||
|
||||
for (b = el->el_map.help; b->name != NULL; b++)
|
||||
if (strcmp(b->name, cmd) == 0)
|
||||
return (b->func);
|
||||
return (-1);
|
||||
}
|
@@ -1,52 +0,0 @@
|
||||
/* $NetBSD: parse.h,v 1.4 2000/09/04 22:06:31 lukem Exp $ */
|
||||
|
||||
/*-
|
||||
* Copyright (c) 1992, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* This code is derived from software contributed to Berkeley by
|
||||
* Christos Zoulas of Cornell University.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
* 3. All advertising materials mentioning features or use of this software
|
||||
* must display the following acknowledgement:
|
||||
* This product includes software developed by the University of
|
||||
* California, Berkeley and its contributors.
|
||||
* 4. Neither the name of the University nor the names of its contributors
|
||||
* may be used to endorse or promote products derived from this software
|
||||
* without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
|
||||
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
* ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
|
||||
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
|
||||
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* @(#)parse.h 8.1 (Berkeley) 6/4/93
|
||||
*/
|
||||
|
||||
/*
|
||||
* el.parse.h: Parser functions
|
||||
*/
|
||||
#ifndef _h_el_parse
|
||||
#define _h_el_parse
|
||||
|
||||
protected int parse_line(EditLine *, const char *);
|
||||
protected int parse__escape(const char ** const);
|
||||
protected char *parse__string(char *, const char *);
|
||||
protected int parse_cmd(EditLine *, const char *);
|
||||
|
||||
#endif /* _h_el_parse */
|
@@ -1,174 +0,0 @@
|
||||
/* $NetBSD: prompt.c,v 1.9 2002/03/18 16:00:56 christos Exp $ */
|
||||
|
||||
/*-
|
||||
* Copyright (c) 1992, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* This code is derived from software contributed to Berkeley by
|
||||
* Christos Zoulas of Cornell University.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
* 3. All advertising materials mentioning features or use of this software
|
||||
* must display the following acknowledgement:
|
||||
* This product includes software developed by the University of
|
||||
* California, Berkeley and its contributors.
|
||||
* 4. Neither the name of the University nor the names of its contributors
|
||||
* may be used to endorse or promote products derived from this software
|
||||
* without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
|
||||
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
* ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
|
||||
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
|
||||
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*/
|
||||
|
||||
#include "config.h"
|
||||
#if !defined(lint) && !defined(SCCSID)
|
||||
#if 0
|
||||
static char sccsid[] = "@(#)prompt.c 8.1 (Berkeley) 6/4/93";
|
||||
#else
|
||||
__RCSID("$NetBSD: prompt.c,v 1.9 2002/03/18 16:00:56 christos Exp $");
|
||||
#endif
|
||||
#endif /* not lint && not SCCSID */
|
||||
|
||||
/*
|
||||
* prompt.c: Prompt printing functions
|
||||
*/
|
||||
#include <stdio.h>
|
||||
#include "el.h"
|
||||
|
||||
private char *prompt_default(EditLine *);
|
||||
private char *prompt_default_r(EditLine *);
|
||||
|
||||
/* prompt_default():
|
||||
* Just a default prompt, in case the user did not provide one
|
||||
*/
|
||||
private char *
|
||||
/*ARGSUSED*/
|
||||
prompt_default(EditLine *el)
|
||||
{
|
||||
static char a[3] = {'?', ' ', '\0'};
|
||||
|
||||
return (a);
|
||||
}
|
||||
|
||||
|
||||
/* prompt_default_r():
|
||||
* Just a default rprompt, in case the user did not provide one
|
||||
*/
|
||||
private char *
|
||||
/*ARGSUSED*/
|
||||
prompt_default_r(EditLine *el)
|
||||
{
|
||||
static char a[1] = {'\0'};
|
||||
|
||||
return (a);
|
||||
}
|
||||
|
||||
|
||||
/* prompt_print():
|
||||
* Print the prompt and update the prompt position.
|
||||
* We use an array of integers in case we want to pass
|
||||
* literal escape sequences in the prompt and we want a
|
||||
* bit to flag them
|
||||
*/
|
||||
protected void
|
||||
prompt_print(EditLine *el, int op)
|
||||
{
|
||||
el_prompt_t *elp;
|
||||
char *p;
|
||||
|
||||
if (op == EL_PROMPT)
|
||||
elp = &el->el_prompt;
|
||||
else
|
||||
elp = &el->el_rprompt;
|
||||
p = (elp->p_func) (el);
|
||||
while (*p)
|
||||
re_putc(el, *p++, 1);
|
||||
|
||||
elp->p_pos.v = el->el_refresh.r_cursor.v;
|
||||
elp->p_pos.h = el->el_refresh.r_cursor.h;
|
||||
}
|
||||
|
||||
|
||||
/* prompt_init():
|
||||
* Initialize the prompt stuff
|
||||
*/
|
||||
protected int
|
||||
prompt_init(EditLine *el)
|
||||
{
|
||||
|
||||
el->el_prompt.p_func = prompt_default;
|
||||
el->el_prompt.p_pos.v = 0;
|
||||
el->el_prompt.p_pos.h = 0;
|
||||
el->el_rprompt.p_func = prompt_default_r;
|
||||
el->el_rprompt.p_pos.v = 0;
|
||||
el->el_rprompt.p_pos.h = 0;
|
||||
return (0);
|
||||
}
|
||||
|
||||
|
||||
/* prompt_end():
|
||||
* Clean up the prompt stuff
|
||||
*/
|
||||
protected void
|
||||
/*ARGSUSED*/
|
||||
prompt_end(EditLine *el)
|
||||
{
|
||||
}
|
||||
|
||||
|
||||
/* prompt_set():
|
||||
* Install a prompt printing function
|
||||
*/
|
||||
protected int
|
||||
prompt_set(EditLine *el, el_pfunc_t prf, int op)
|
||||
{
|
||||
el_prompt_t *p;
|
||||
|
||||
if (op == EL_PROMPT)
|
||||
p = &el->el_prompt;
|
||||
else
|
||||
p = &el->el_rprompt;
|
||||
if (prf == NULL) {
|
||||
if (op == EL_PROMPT)
|
||||
p->p_func = prompt_default;
|
||||
else
|
||||
p->p_func = prompt_default_r;
|
||||
} else
|
||||
p->p_func = prf;
|
||||
p->p_pos.v = 0;
|
||||
p->p_pos.h = 0;
|
||||
return (0);
|
||||
}
|
||||
|
||||
|
||||
/* prompt_get():
|
||||
* Retrieve the prompt printing function
|
||||
*/
|
||||
protected int
|
||||
prompt_get(EditLine *el, el_pfunc_t *prf, int op)
|
||||
{
|
||||
|
||||
if (prf == NULL)
|
||||
return (-1);
|
||||
if (op == EL_PROMPT)
|
||||
*prf = el->el_prompt.p_func;
|
||||
else
|
||||
*prf = el->el_rprompt.p_func;
|
||||
return (0);
|
||||
}
|
@@ -1,62 +0,0 @@
|
||||
/* $NetBSD: prompt.h,v 1.5 2000/09/04 22:06:31 lukem Exp $ */
|
||||
|
||||
/*-
|
||||
* Copyright (c) 1992, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* This code is derived from software contributed to Berkeley by
|
||||
* Christos Zoulas of Cornell University.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
* 3. All advertising materials mentioning features or use of this software
|
||||
* must display the following acknowledgement:
|
||||
* This product includes software developed by the University of
|
||||
* California, Berkeley and its contributors.
|
||||
* 4. Neither the name of the University nor the names of its contributors
|
||||
* may be used to endorse or promote products derived from this software
|
||||
* without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
|
||||
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
* ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
|
||||
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
|
||||
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* @(#)prompt.h 8.1 (Berkeley) 6/4/93
|
||||
*/
|
||||
|
||||
/*
|
||||
* el.prompt.h: Prompt printing stuff
|
||||
*/
|
||||
#ifndef _h_el_prompt
|
||||
#define _h_el_prompt
|
||||
|
||||
#include "histedit.h"
|
||||
|
||||
typedef char * (*el_pfunc_t)(EditLine*);
|
||||
|
||||
typedef struct el_prompt_t {
|
||||
el_pfunc_t p_func; /* Function to return the prompt */
|
||||
coord_t p_pos; /* position in the line after prompt */
|
||||
} el_prompt_t;
|
||||
|
||||
protected void prompt_print(EditLine *, int);
|
||||
protected int prompt_set(EditLine *, el_pfunc_t, int);
|
||||
protected int prompt_get(EditLine *, el_pfunc_t *, int);
|
||||
protected int prompt_init(EditLine *);
|
||||
protected void prompt_end(EditLine *);
|
||||
|
||||
#endif /* _h_el_prompt */
|
@@ -1,558 +0,0 @@
|
||||
/* $NetBSD: read.c,v 1.21 2002/03/18 16:00:57 christos Exp $ */
|
||||
|
||||
/*-
|
||||
* Copyright (c) 1992, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* This code is derived from software contributed to Berkeley by
|
||||
* Christos Zoulas of Cornell University.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
* 3. All advertising materials mentioning features or use of this software
|
||||
* must display the following acknowledgement:
|
||||
* This product includes software developed by the University of
|
||||
* California, Berkeley and its contributors.
|
||||
* 4. Neither the name of the University nor the names of its contributors
|
||||
* may be used to endorse or promote products derived from this software
|
||||
* without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
|
||||
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
* ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
|
||||
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
|
||||
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*/
|
||||
|
||||
#include "config.h"
|
||||
#if !defined(lint) && !defined(SCCSID)
|
||||
#if 0
|
||||
static char sccsid[] = "@(#)read.c 8.1 (Berkeley) 6/4/93";
|
||||
#else
|
||||
__RCSID("$NetBSD: read.c,v 1.21 2002/03/18 16:00:57 christos Exp $");
|
||||
#endif
|
||||
#endif /* not lint && not SCCSID */
|
||||
|
||||
/*
|
||||
* read.c: Clean this junk up! This is horrible code.
|
||||
* Terminal read functions
|
||||
*/
|
||||
#include <errno.h>
|
||||
#include <unistd.h>
|
||||
#include <stdlib.h>
|
||||
#include "el.h"
|
||||
|
||||
#define OKCMD -1
|
||||
|
||||
private int read__fixio(int, int);
|
||||
private int read_preread(EditLine *);
|
||||
private int read_char(EditLine *, char *);
|
||||
private int read_getcmd(EditLine *, el_action_t *, char *);
|
||||
|
||||
/* read_init():
|
||||
* Initialize the read stuff
|
||||
*/
|
||||
protected int
|
||||
read_init(EditLine *el)
|
||||
{
|
||||
/* builtin read_char */
|
||||
el->el_read.read_char = read_char;
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
/* el_read_setfn():
|
||||
* Set the read char function to the one provided.
|
||||
* If it is set to EL_BUILTIN_GETCFN, then reset to the builtin one.
|
||||
*/
|
||||
protected int
|
||||
el_read_setfn(EditLine *el, el_rfunc_t rc)
|
||||
{
|
||||
el->el_read.read_char = (rc == EL_BUILTIN_GETCFN) ? read_char : rc;
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
/* el_read_getfn():
|
||||
* return the current read char function, or EL_BUILTIN_GETCFN
|
||||
* if it is the default one
|
||||
*/
|
||||
protected el_rfunc_t
|
||||
el_read_getfn(EditLine *el)
|
||||
{
|
||||
return (el->el_read.read_char == read_char) ?
|
||||
EL_BUILTIN_GETCFN : el->el_read.read_char;
|
||||
}
|
||||
|
||||
|
||||
#ifdef DEBUG_EDIT
|
||||
private void
|
||||
read_debug(EditLine *el)
|
||||
{
|
||||
|
||||
if (el->el_line.cursor > el->el_line.lastchar)
|
||||
(void) fprintf(el->el_errfile, "cursor > lastchar\r\n");
|
||||
if (el->el_line.cursor < el->el_line.buffer)
|
||||
(void) fprintf(el->el_errfile, "cursor < buffer\r\n");
|
||||
if (el->el_line.cursor > el->el_line.limit)
|
||||
(void) fprintf(el->el_errfile, "cursor > limit\r\n");
|
||||
if (el->el_line.lastchar > el->el_line.limit)
|
||||
(void) fprintf(el->el_errfile, "lastchar > limit\r\n");
|
||||
if (el->el_line.limit != &el->el_line.buffer[EL_BUFSIZ - 2])
|
||||
(void) fprintf(el->el_errfile, "limit != &buffer[EL_BUFSIZ-2]\r\n");
|
||||
}
|
||||
#endif /* DEBUG_EDIT */
|
||||
|
||||
|
||||
/* read__fixio():
|
||||
* Try to recover from a read error
|
||||
*/
|
||||
/* ARGSUSED */
|
||||
private int
|
||||
read__fixio(int fd, int e)
|
||||
{
|
||||
|
||||
switch (e) {
|
||||
case -1: /* Make sure that the code is reachable */
|
||||
|
||||
#ifdef EWOULDBLOCK
|
||||
case EWOULDBLOCK:
|
||||
#ifndef TRY_AGAIN
|
||||
#define TRY_AGAIN
|
||||
#endif
|
||||
#endif /* EWOULDBLOCK */
|
||||
|
||||
#if defined(POSIX) && defined(EAGAIN)
|
||||
#if defined(EWOULDBLOCK) && EWOULDBLOCK != EAGAIN
|
||||
case EAGAIN:
|
||||
#ifndef TRY_AGAIN
|
||||
#define TRY_AGAIN
|
||||
#endif
|
||||
#endif /* EWOULDBLOCK && EWOULDBLOCK != EAGAIN */
|
||||
#endif /* POSIX && EAGAIN */
|
||||
|
||||
e = 0;
|
||||
#ifdef TRY_AGAIN
|
||||
#if defined(F_SETFL) && defined(O_NDELAY)
|
||||
if ((e = fcntl(fd, F_GETFL, 0)) == -1)
|
||||
return (-1);
|
||||
|
||||
if (fcntl(fd, F_SETFL, e & ~O_NDELAY) == -1)
|
||||
return (-1);
|
||||
else
|
||||
e = 1;
|
||||
#endif /* F_SETFL && O_NDELAY */
|
||||
|
||||
#ifdef FIONBIO
|
||||
{
|
||||
int zero = 0;
|
||||
|
||||
if (ioctl(fd, FIONBIO, (ioctl_t) & zero) == -1)
|
||||
return (-1);
|
||||
else
|
||||
e = 1;
|
||||
}
|
||||
#endif /* FIONBIO */
|
||||
|
||||
#endif /* TRY_AGAIN */
|
||||
return (e ? 0 : -1);
|
||||
|
||||
case EINTR:
|
||||
return (0);
|
||||
|
||||
default:
|
||||
return (-1);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/* read_preread():
|
||||
* Try to read the stuff in the input queue;
|
||||
*/
|
||||
private int
|
||||
read_preread(EditLine *el)
|
||||
{
|
||||
int chrs = 0;
|
||||
|
||||
if (el->el_chared.c_macro.nline) {
|
||||
el_free((ptr_t) el->el_chared.c_macro.nline);
|
||||
el->el_chared.c_macro.nline = NULL;
|
||||
}
|
||||
if (el->el_tty.t_mode == ED_IO)
|
||||
return (0);
|
||||
|
||||
#ifdef FIONREAD
|
||||
(void) ioctl(el->el_infd, FIONREAD, (ioctl_t) & chrs);
|
||||
if (chrs > 0) {
|
||||
char buf[EL_BUFSIZ];
|
||||
|
||||
chrs = read(el->el_infd, buf,
|
||||
(size_t) MIN(chrs, EL_BUFSIZ - 1));
|
||||
if (chrs > 0) {
|
||||
buf[chrs] = '\0';
|
||||
el->el_chared.c_macro.nline = strdup(buf);
|
||||
el_push(el, el->el_chared.c_macro.nline);
|
||||
}
|
||||
}
|
||||
#endif /* FIONREAD */
|
||||
|
||||
return (chrs > 0);
|
||||
}
|
||||
|
||||
|
||||
/* el_push():
|
||||
* Push a macro
|
||||
*/
|
||||
public void
|
||||
el_push(EditLine *el, char *str)
|
||||
{
|
||||
c_macro_t *ma = &el->el_chared.c_macro;
|
||||
|
||||
if (str != NULL && ma->level + 1 < EL_MAXMACRO) {
|
||||
ma->level++;
|
||||
ma->macro[ma->level] = str;
|
||||
} else {
|
||||
term_beep(el);
|
||||
term__flush();
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/* read_getcmd():
|
||||
* Return next command from the input stream.
|
||||
*/
|
||||
private int
|
||||
read_getcmd(EditLine *el, el_action_t *cmdnum, char *ch)
|
||||
{
|
||||
el_action_t cmd = ED_UNASSIGNED;
|
||||
int num;
|
||||
|
||||
while (cmd == ED_UNASSIGNED || cmd == ED_SEQUENCE_LEAD_IN) {
|
||||
if ((num = el_getc(el, ch)) != 1) /* if EOF or error */
|
||||
return (num);
|
||||
|
||||
#ifdef KANJI
|
||||
if ((*ch & 0200)) {
|
||||
el->el_state.metanext = 0;
|
||||
cmd = CcViMap[' '];
|
||||
break;
|
||||
} else
|
||||
#endif /* KANJI */
|
||||
|
||||
if (el->el_state.metanext) {
|
||||
el->el_state.metanext = 0;
|
||||
*ch |= 0200;
|
||||
}
|
||||
cmd = el->el_map.current[(unsigned char) *ch];
|
||||
if (cmd == ED_SEQUENCE_LEAD_IN) {
|
||||
key_value_t val;
|
||||
switch (key_get(el, ch, &val)) {
|
||||
case XK_CMD:
|
||||
cmd = val.cmd;
|
||||
break;
|
||||
case XK_STR:
|
||||
el_push(el, val.str);
|
||||
break;
|
||||
#ifdef notyet
|
||||
case XK_EXE:
|
||||
/* XXX: In the future to run a user function */
|
||||
RunCommand(val.str);
|
||||
break;
|
||||
#endif
|
||||
default:
|
||||
EL_ABORT((el->el_errfile, "Bad XK_ type \n"));
|
||||
break;
|
||||
}
|
||||
}
|
||||
if (el->el_map.alt == NULL)
|
||||
el->el_map.current = el->el_map.key;
|
||||
}
|
||||
*cmdnum = cmd;
|
||||
return (OKCMD);
|
||||
}
|
||||
|
||||
|
||||
/* read_char():
|
||||
* Read a character from the tty.
|
||||
* XXX This routine is the default, but what you are actually looking for
|
||||
* is in main/asterisk.c, in ast_el_read_char(). XXX
|
||||
*/
|
||||
private int
|
||||
read_char(EditLine *el, char *cp)
|
||||
{
|
||||
int num_read;
|
||||
int tried = 0;
|
||||
|
||||
while ((num_read = read(el->el_infd, cp, 1)) == -1)
|
||||
if (!tried && read__fixio(el->el_infd, errno) == 0)
|
||||
tried = 1;
|
||||
else {
|
||||
*cp = '\0';
|
||||
return (-1);
|
||||
}
|
||||
|
||||
return (num_read);
|
||||
}
|
||||
|
||||
|
||||
/* el_getc():
|
||||
* Read a character
|
||||
*/
|
||||
public int
|
||||
el_getc(EditLine *el, char *cp)
|
||||
{
|
||||
int num_read;
|
||||
c_macro_t *ma = &el->el_chared.c_macro;
|
||||
|
||||
term__flush();
|
||||
for (;;) {
|
||||
if (ma->level < 0) {
|
||||
if (!read_preread(el))
|
||||
break;
|
||||
}
|
||||
if (ma->level < 0)
|
||||
break;
|
||||
|
||||
if (*ma->macro[ma->level] == 0) {
|
||||
ma->level--;
|
||||
continue;
|
||||
}
|
||||
*cp = *ma->macro[ma->level]++ & 0377;
|
||||
if (*ma->macro[ma->level] == 0) { /* Needed for QuoteMode
|
||||
* On */
|
||||
ma->level--;
|
||||
}
|
||||
return (1);
|
||||
}
|
||||
|
||||
#ifdef DEBUG_READ
|
||||
(void) fprintf(el->el_errfile, "Turning raw mode on\n");
|
||||
#endif /* DEBUG_READ */
|
||||
if (tty_rawmode(el) < 0)/* make sure the tty is set up correctly */
|
||||
return (0);
|
||||
|
||||
#ifdef DEBUG_READ
|
||||
(void) fprintf(el->el_errfile, "Reading a character\n");
|
||||
#endif /* DEBUG_READ */
|
||||
/* See main/asterisk.c: ast_el_read_char() */
|
||||
num_read = (*el->el_read.read_char)(el, cp);
|
||||
#ifdef DEBUG_READ
|
||||
(void) fprintf(el->el_errfile, "Got it %c\n", *cp);
|
||||
#endif /* DEBUG_READ */
|
||||
return (num_read);
|
||||
}
|
||||
|
||||
|
||||
public const char *
|
||||
el_gets(EditLine *el, int *nread)
|
||||
{
|
||||
int retval;
|
||||
el_action_t cmdnum = 0;
|
||||
int num; /* how many chars we have read at NL */
|
||||
char ch;
|
||||
#ifdef FIONREAD
|
||||
c_macro_t *ma = &el->el_chared.c_macro;
|
||||
#endif /* FIONREAD */
|
||||
|
||||
if (el->el_flags & HANDLE_SIGNALS)
|
||||
sig_set(el);
|
||||
|
||||
if (el->el_flags & NO_TTY) {
|
||||
char *cp = el->el_line.buffer;
|
||||
size_t idx;
|
||||
|
||||
while ((*el->el_read.read_char)(el, cp) == 1) {
|
||||
/* make sure there is space for next character */
|
||||
if (cp + 1 >= el->el_line.limit) {
|
||||
idx = (cp - el->el_line.buffer);
|
||||
if (!ch_enlargebufs(el, 2))
|
||||
break;
|
||||
cp = &el->el_line.buffer[idx];
|
||||
}
|
||||
cp++;
|
||||
if (cp[-1] == '\r' || cp[-1] == '\n')
|
||||
break;
|
||||
}
|
||||
|
||||
el->el_line.cursor = el->el_line.lastchar = cp;
|
||||
*cp = '\0';
|
||||
if (nread)
|
||||
*nread = el->el_line.cursor - el->el_line.buffer;
|
||||
return (el->el_line.buffer);
|
||||
}
|
||||
re_clear_display(el); /* reset the display stuff */
|
||||
ch_reset(el);
|
||||
|
||||
#ifdef FIONREAD
|
||||
if (el->el_tty.t_mode == EX_IO && ma->level < 0) {
|
||||
long chrs = 0;
|
||||
|
||||
(void) ioctl(el->el_infd, FIONREAD, (ioctl_t) & chrs);
|
||||
if (chrs == 0) {
|
||||
if (tty_rawmode(el) < 0) {
|
||||
if (nread)
|
||||
*nread = 0;
|
||||
return (NULL);
|
||||
}
|
||||
}
|
||||
}
|
||||
#endif /* FIONREAD */
|
||||
|
||||
re_refresh(el); /* print the prompt */
|
||||
|
||||
if (el->el_flags & EDIT_DISABLED) {
|
||||
char *cp = el->el_line.buffer;
|
||||
size_t idx;
|
||||
|
||||
term__flush();
|
||||
|
||||
while ((*el->el_read.read_char)(el, cp) == 1) {
|
||||
/* make sure there is space next character */
|
||||
if (cp + 1 >= el->el_line.limit) {
|
||||
idx = (cp - el->el_line.buffer);
|
||||
if (!ch_enlargebufs(el, 2))
|
||||
break;
|
||||
cp = &el->el_line.buffer[idx];
|
||||
}
|
||||
cp++;
|
||||
if (cp[-1] == '\r' || cp[-1] == '\n')
|
||||
break;
|
||||
}
|
||||
|
||||
el->el_line.cursor = el->el_line.lastchar = cp;
|
||||
*cp = '\0';
|
||||
if (nread)
|
||||
*nread = el->el_line.cursor - el->el_line.buffer;
|
||||
return (el->el_line.buffer);
|
||||
}
|
||||
for (num = OKCMD; num == OKCMD;) { /* while still editing this
|
||||
* line */
|
||||
#ifdef DEBUG_EDIT
|
||||
read_debug(el);
|
||||
#endif /* DEBUG_EDIT */
|
||||
/* if EOF or error */
|
||||
if ((num = read_getcmd(el, &cmdnum, &ch)) != OKCMD) {
|
||||
#ifdef DEBUG_READ
|
||||
(void) fprintf(el->el_errfile,
|
||||
"Returning from el_gets %d\n", num);
|
||||
#endif /* DEBUG_READ */
|
||||
break;
|
||||
}
|
||||
if ((int) cmdnum >= el->el_map.nfunc) { /* BUG CHECK command */
|
||||
#ifdef DEBUG_EDIT
|
||||
(void) fprintf(el->el_errfile,
|
||||
"ERROR: illegal command from key 0%o\r\n", ch);
|
||||
#endif /* DEBUG_EDIT */
|
||||
continue; /* try again */
|
||||
}
|
||||
/* now do the real command */
|
||||
#ifdef DEBUG_READ
|
||||
{
|
||||
el_bindings_t *b;
|
||||
for (b = el->el_map.help; b->name; b++)
|
||||
if (b->func == cmdnum)
|
||||
break;
|
||||
if (b->name)
|
||||
(void) fprintf(el->el_errfile,
|
||||
"Executing %s\n", b->name);
|
||||
else
|
||||
(void) fprintf(el->el_errfile,
|
||||
"Error command = %d\n", cmdnum);
|
||||
}
|
||||
#endif /* DEBUG_READ */
|
||||
retval = (*el->el_map.func[cmdnum]) (el, ch);
|
||||
|
||||
/* save the last command here */
|
||||
el->el_state.lastcmd = cmdnum;
|
||||
|
||||
/* use any return value */
|
||||
switch (retval) {
|
||||
case CC_CURSOR:
|
||||
el->el_state.argument = 1;
|
||||
el->el_state.doingarg = 0;
|
||||
re_refresh_cursor(el);
|
||||
break;
|
||||
|
||||
case CC_REDISPLAY:
|
||||
re_clear_lines(el);
|
||||
re_clear_display(el);
|
||||
/* FALLTHROUGH */
|
||||
|
||||
case CC_REFRESH:
|
||||
el->el_state.argument = 1;
|
||||
el->el_state.doingarg = 0;
|
||||
re_refresh(el);
|
||||
break;
|
||||
|
||||
case CC_REFRESH_BEEP:
|
||||
el->el_state.argument = 1;
|
||||
el->el_state.doingarg = 0;
|
||||
re_refresh(el);
|
||||
term_beep(el);
|
||||
break;
|
||||
|
||||
case CC_NORM: /* normal char */
|
||||
el->el_state.argument = 1;
|
||||
el->el_state.doingarg = 0;
|
||||
break;
|
||||
|
||||
case CC_ARGHACK: /* Suggested by Rich Salz */
|
||||
/* <rsalz@pineapple.bbn.com> */
|
||||
break; /* keep going... */
|
||||
|
||||
case CC_EOF: /* end of file typed */
|
||||
num = 0;
|
||||
break;
|
||||
|
||||
case CC_NEWLINE: /* normal end of line */
|
||||
num = el->el_line.lastchar - el->el_line.buffer;
|
||||
break;
|
||||
|
||||
case CC_FATAL: /* fatal error, reset to known state */
|
||||
#ifdef DEBUG_READ
|
||||
(void) fprintf(el->el_errfile,
|
||||
"*** editor fatal ERROR ***\r\n\n");
|
||||
#endif /* DEBUG_READ */
|
||||
/* put (real) cursor in a known place */
|
||||
re_clear_display(el); /* reset the display stuff */
|
||||
ch_reset(el); /* reset the input pointers */
|
||||
re_refresh(el); /* print the prompt again */
|
||||
el->el_state.argument = 1;
|
||||
el->el_state.doingarg = 0;
|
||||
break;
|
||||
|
||||
case CC_ERROR:
|
||||
default: /* functions we don't know about */
|
||||
#ifdef DEBUG_READ
|
||||
(void) fprintf(el->el_errfile,
|
||||
"*** editor ERROR ***\r\n\n");
|
||||
#endif /* DEBUG_READ */
|
||||
el->el_state.argument = 1;
|
||||
el->el_state.doingarg = 0;
|
||||
term_beep(el);
|
||||
term__flush();
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
/* make sure the tty is set up correctly */
|
||||
(void) tty_cookedmode(el);
|
||||
term__flush(); /* flush any buffered output */
|
||||
if (el->el_flags & HANDLE_SIGNALS)
|
||||
sig_clr(el);
|
||||
if (nread)
|
||||
*nread = num;
|
||||
return (num ? el->el_line.buffer : NULL);
|
||||
}
|
@@ -1,55 +0,0 @@
|
||||
/* $NetBSD: read.h,v 1.1 2001/09/27 19:29:50 christos Exp $ */
|
||||
|
||||
/*-
|
||||
* Copyright (c) 2001 The NetBSD Foundation, Inc.
|
||||
* All rights reserved.
|
||||
*
|
||||
* This code is derived from software contributed to The NetBSD Foundation
|
||||
* by Anthony Mallet.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
* 3. All advertising materials mentioning features or use of this software
|
||||
* must display the following acknowledgement:
|
||||
* This product includes software developed by the NetBSD
|
||||
* Foundation, Inc. and its contributors.
|
||||
* 4. Neither the name of The NetBSD Foundation nor the names of its
|
||||
* contributors may be used to endorse or promote products derived
|
||||
* from this software without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS
|
||||
* ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
|
||||
* TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
|
||||
* PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS
|
||||
* BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
|
||||
* CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
|
||||
* SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
|
||||
* INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
|
||||
* CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
|
||||
* ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
|
||||
* POSSIBILITY OF SUCH DAMAGE.
|
||||
*/
|
||||
|
||||
/*
|
||||
* el.read.h: Character reading functions
|
||||
*/
|
||||
#ifndef _h_el_read
|
||||
#define _h_el_read
|
||||
|
||||
typedef int (*el_rfunc_t)(EditLine *, char *);
|
||||
|
||||
typedef struct el_read_t {
|
||||
el_rfunc_t read_char; /* Function to read a character */
|
||||
} el_read_t;
|
||||
|
||||
protected int read_init(EditLine *);
|
||||
protected int el_read_setfn(EditLine *, el_rfunc_t);
|
||||
protected el_rfunc_t el_read_getfn(EditLine *);
|
||||
|
||||
#endif /* _h_el_read */
|
File diff suppressed because it is too large
Load Diff
@@ -1,118 +0,0 @@
|
||||
/* $NetBSD: readline.h,v 1.1 2001/01/05 21:15:50 jdolecek Exp $ */
|
||||
|
||||
/*-
|
||||
* Copyright (c) 1997 The NetBSD Foundation, Inc.
|
||||
* All rights reserved.
|
||||
*
|
||||
* This code is derived from software contributed to The NetBSD Foundation
|
||||
* by Jaromir Dolecek.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
* 3. All advertising materials mentioning features or use of this software
|
||||
* must display the following acknowledgement:
|
||||
* This product includes software developed by the NetBSD
|
||||
* Foundation, Inc. and its contributors.
|
||||
* 4. Neither the name of The NetBSD Foundation nor the names of its
|
||||
* contributors may be used to endorse or promote products derived
|
||||
* from this software without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS
|
||||
* ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
|
||||
* TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
|
||||
* PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS
|
||||
* BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
|
||||
* CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
|
||||
* SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
|
||||
* INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
|
||||
* CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
|
||||
* ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
|
||||
* POSSIBILITY OF SUCH DAMAGE.
|
||||
*/
|
||||
#ifndef _READLINE_H_
|
||||
#define _READLINE_H_
|
||||
|
||||
#include <sys/types.h>
|
||||
|
||||
/* list of readline stuff supported by editline library's readline wrapper */
|
||||
|
||||
/* typedefs */
|
||||
typedef int Function(const char *, int);
|
||||
typedef void VFunction(void);
|
||||
typedef char *CPFunction(const char *, int);
|
||||
typedef char **CPPFunction(const char *, int, int);
|
||||
|
||||
typedef struct _hist_entry {
|
||||
const char *line;
|
||||
const char *data;
|
||||
} HIST_ENTRY;
|
||||
|
||||
/* global variables used by readline enabled applications */
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
extern const char *rl_library_version;
|
||||
extern char *rl_readline_name;
|
||||
extern FILE *rl_instream;
|
||||
extern FILE *rl_outstream;
|
||||
extern char *rl_line_buffer;
|
||||
extern int rl_point, rl_end;
|
||||
extern int history_base, history_length;
|
||||
extern int max_input_history;
|
||||
extern char *rl_basic_word_break_characters;
|
||||
extern char *rl_completer_word_break_characters;
|
||||
extern char *rl_completer_quote_characters;
|
||||
extern CPFunction *rl_completion_entry_function;
|
||||
extern CPPFunction *rl_attempted_completion_function;
|
||||
extern int rl_completion_type;
|
||||
extern int rl_completion_query_items;
|
||||
extern char *rl_special_prefixes;
|
||||
extern int rl_completion_append_character;
|
||||
|
||||
/* supported functions */
|
||||
char *readline(const char *);
|
||||
int rl_initialize(void);
|
||||
|
||||
void using_history(void);
|
||||
int add_history(const char *);
|
||||
void clear_history(void);
|
||||
void stifle_history(int);
|
||||
int unstifle_history(void);
|
||||
int history_is_stifled(void);
|
||||
int where_history(void);
|
||||
HIST_ENTRY *current_history(void);
|
||||
HIST_ENTRY *history_get(int);
|
||||
int history_total_bytes(void);
|
||||
int history_set_pos(int);
|
||||
HIST_ENTRY *previous_history(void);
|
||||
HIST_ENTRY *next_history(void);
|
||||
int history_search(const char *, int);
|
||||
int history_search_prefix(const char *, int);
|
||||
int history_search_pos(const char *, int, int);
|
||||
int read_history(const char *);
|
||||
int write_history(const char *);
|
||||
int history_expand(char *, char **);
|
||||
char **history_tokenize(const char *);
|
||||
|
||||
char *tilde_expand(char *);
|
||||
char *filename_completion_function(const char *, int);
|
||||
char *username_completion_function(const char *, int);
|
||||
int rl_complete(int, int);
|
||||
int rl_read_key(void);
|
||||
char **completion_matches(const char *, CPFunction *);
|
||||
void rl_display_match_list(char **, int, int);
|
||||
|
||||
int rl_insert(int, int);
|
||||
void rl_reset_terminal(const char *);
|
||||
int rl_bind_key(int, int (*)(int, int));
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif /* _READLINE_H_ */
|
File diff suppressed because it is too large
Load Diff
@@ -1,63 +0,0 @@
|
||||
/* $NetBSD: refresh.h,v 1.4 2001/01/10 07:45:42 jdolecek Exp $ */
|
||||
|
||||
/*-
|
||||
* Copyright (c) 1992, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* This code is derived from software contributed to Berkeley by
|
||||
* Christos Zoulas of Cornell University.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
* 3. All advertising materials mentioning features or use of this software
|
||||
* must display the following acknowledgement:
|
||||
* This product includes software developed by the University of
|
||||
* California, Berkeley and its contributors.
|
||||
* 4. Neither the name of the University nor the names of its contributors
|
||||
* may be used to endorse or promote products derived from this software
|
||||
* without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
|
||||
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
* ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
|
||||
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
|
||||
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* @(#)refresh.h 8.1 (Berkeley) 6/4/93
|
||||
*/
|
||||
|
||||
/*
|
||||
* el.refresh.h: Screen refresh functions
|
||||
*/
|
||||
#ifndef _h_el_refresh
|
||||
#define _h_el_refresh
|
||||
|
||||
#include "histedit.h"
|
||||
|
||||
typedef struct {
|
||||
coord_t r_cursor; /* Refresh cursor position */
|
||||
int r_oldcv; /* Vertical locations */
|
||||
int r_newcv;
|
||||
} el_refresh_t;
|
||||
|
||||
protected void re_putc(EditLine *, int, int);
|
||||
protected void re_clear_lines(EditLine *);
|
||||
protected void re_clear_display(EditLine *);
|
||||
protected void re_refresh(EditLine *);
|
||||
protected void re_refresh_cursor(EditLine *);
|
||||
protected void re_fastaddc(EditLine *);
|
||||
protected void re_goto_bottom(EditLine *);
|
||||
|
||||
#endif /* _h_el_refresh */
|
@@ -1,649 +0,0 @@
|
||||
/* $NetBSD: search.c,v 1.12 2002/03/18 16:00:58 christos Exp $ */
|
||||
|
||||
/*-
|
||||
* Copyright (c) 1992, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* This code is derived from software contributed to Berkeley by
|
||||
* Christos Zoulas of Cornell University.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
* 3. All advertising materials mentioning features or use of this software
|
||||
* must display the following acknowledgement:
|
||||
* This product includes software developed by the University of
|
||||
* California, Berkeley and its contributors.
|
||||
* 4. Neither the name of the University nor the names of its contributors
|
||||
* may be used to endorse or promote products derived from this software
|
||||
* without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
|
||||
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
* ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
|
||||
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
|
||||
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*/
|
||||
|
||||
#include "config.h"
|
||||
#if !defined(lint) && !defined(SCCSID)
|
||||
#if 0
|
||||
static char sccsid[] = "@(#)search.c 8.1 (Berkeley) 6/4/93";
|
||||
#else
|
||||
__RCSID("$NetBSD: search.c,v 1.12 2002/03/18 16:00:58 christos Exp $");
|
||||
#endif
|
||||
#endif /* not lint && not SCCSID */
|
||||
|
||||
/*
|
||||
* search.c: History and character search functions
|
||||
*/
|
||||
#include <stdlib.h>
|
||||
#if defined(REGEX)
|
||||
#include <regex.h>
|
||||
#elif defined(REGEXP)
|
||||
#include <regexp.h>
|
||||
#endif
|
||||
#include "el.h"
|
||||
|
||||
/*
|
||||
* Adjust cursor in vi mode to include the character under it
|
||||
*/
|
||||
#define EL_CURSOR(el) \
|
||||
((el)->el_line.cursor + (((el)->el_map.type == MAP_VI) && \
|
||||
((el)->el_map.current == (el)->el_map.alt)))
|
||||
|
||||
/* search_init():
|
||||
* Initialize the search stuff
|
||||
*/
|
||||
protected int
|
||||
search_init(EditLine *el)
|
||||
{
|
||||
|
||||
el->el_search.patbuf = (char *) el_malloc(EL_BUFSIZ);
|
||||
if (el->el_search.patbuf == NULL)
|
||||
return (-1);
|
||||
el->el_search.patlen = 0;
|
||||
el->el_search.patdir = -1;
|
||||
el->el_search.chacha = '\0';
|
||||
el->el_search.chadir = -1;
|
||||
return (0);
|
||||
}
|
||||
|
||||
|
||||
/* search_end():
|
||||
* Initialize the search stuff
|
||||
*/
|
||||
protected void
|
||||
search_end(EditLine *el)
|
||||
{
|
||||
|
||||
el_free((ptr_t) el->el_search.patbuf);
|
||||
el->el_search.patbuf = NULL;
|
||||
}
|
||||
|
||||
|
||||
#ifdef REGEXP
|
||||
/* regerror():
|
||||
* Handle regular expression errors
|
||||
*/
|
||||
public void
|
||||
/*ARGSUSED*/
|
||||
regerror(const char *msg)
|
||||
{
|
||||
}
|
||||
#endif
|
||||
|
||||
|
||||
/* el_match():
|
||||
* Return if string matches pattern
|
||||
*/
|
||||
protected int
|
||||
el_match(const char *str, const char *pat)
|
||||
{
|
||||
#if defined (REGEX)
|
||||
regex_t re;
|
||||
int rv;
|
||||
#elif defined (REGEXP)
|
||||
regexp *rp;
|
||||
int rv;
|
||||
#else
|
||||
extern char *re_comp(const char *);
|
||||
extern int re_exec(const char *);
|
||||
#endif
|
||||
|
||||
if (strstr(str, pat) != NULL)
|
||||
return (1);
|
||||
|
||||
#if defined(REGEX)
|
||||
if (regcomp(&re, pat, 0) == 0) {
|
||||
rv = regexec(&re, str, 0, NULL, 0) == 0;
|
||||
regfree(&re);
|
||||
} else {
|
||||
rv = 0;
|
||||
}
|
||||
return (rv);
|
||||
#elif defined(REGEXP)
|
||||
if ((re = regcomp(pat)) != NULL) {
|
||||
rv = regexec(re, str);
|
||||
free((ptr_t) re);
|
||||
} else {
|
||||
rv = 0;
|
||||
}
|
||||
return (rv);
|
||||
#else
|
||||
if (re_comp(pat) != NULL)
|
||||
return (0);
|
||||
else
|
||||
return (re_exec(str) == 1);
|
||||
#endif
|
||||
}
|
||||
|
||||
|
||||
/* c_hmatch():
|
||||
* return True if the pattern matches the prefix
|
||||
*/
|
||||
protected int
|
||||
c_hmatch(EditLine *el, const char *str)
|
||||
{
|
||||
#ifdef SDEBUG
|
||||
(void) fprintf(el->el_errfile, "match `%s' with `%s'\n",
|
||||
el->el_search.patbuf, str);
|
||||
#endif /* SDEBUG */
|
||||
|
||||
return (el_match(str, el->el_search.patbuf));
|
||||
}
|
||||
|
||||
|
||||
/* c_setpat():
|
||||
* Set the history seatch pattern
|
||||
*/
|
||||
protected void
|
||||
c_setpat(EditLine *el)
|
||||
{
|
||||
if (el->el_state.lastcmd != ED_SEARCH_PREV_HISTORY &&
|
||||
el->el_state.lastcmd != ED_SEARCH_NEXT_HISTORY) {
|
||||
el->el_search.patlen = EL_CURSOR(el) - el->el_line.buffer;
|
||||
if (el->el_search.patlen >= EL_BUFSIZ)
|
||||
el->el_search.patlen = EL_BUFSIZ - 1;
|
||||
if (el->el_search.patlen != 0) {
|
||||
(void) strncpy(el->el_search.patbuf, el->el_line.buffer,
|
||||
el->el_search.patlen);
|
||||
el->el_search.patbuf[el->el_search.patlen] = '\0';
|
||||
} else
|
||||
el->el_search.patlen = strlen(el->el_search.patbuf);
|
||||
}
|
||||
#ifdef SDEBUG
|
||||
(void) fprintf(el->el_errfile, "\neventno = %d\n",
|
||||
el->el_history.eventno);
|
||||
(void) fprintf(el->el_errfile, "patlen = %d\n", el->el_search.patlen);
|
||||
(void) fprintf(el->el_errfile, "patbuf = \"%s\"\n",
|
||||
el->el_search.patbuf);
|
||||
(void) fprintf(el->el_errfile, "cursor %d lastchar %d\n",
|
||||
EL_CURSOR(el) - el->el_line.buffer,
|
||||
el->el_line.lastchar - el->el_line.buffer);
|
||||
#endif
|
||||
}
|
||||
|
||||
|
||||
/* ce_inc_search():
|
||||
* Emacs incremental search
|
||||
*/
|
||||
protected el_action_t
|
||||
ce_inc_search(EditLine *el, int dir)
|
||||
{
|
||||
static const char STRfwd[] = {'f', 'w', 'd', '\0'},
|
||||
STRbck[] = {'b', 'c', 'k', '\0'};
|
||||
static char pchar = ':';/* ':' = normal, '?' = failed */
|
||||
static char endcmd[2] = {'\0', '\0'};
|
||||
char ch, *ocursor = el->el_line.cursor, oldpchar = pchar;
|
||||
const char *cp;
|
||||
|
||||
el_action_t ret = CC_NORM;
|
||||
|
||||
int ohisteventno = el->el_history.eventno;
|
||||
int oldpatlen = el->el_search.patlen;
|
||||
int newdir = dir;
|
||||
int done, redo;
|
||||
|
||||
if (el->el_line.lastchar + sizeof(STRfwd) / sizeof(char) + 2 +
|
||||
el->el_search.patlen >= el->el_line.limit)
|
||||
return (CC_ERROR);
|
||||
|
||||
for (;;) {
|
||||
|
||||
if (el->el_search.patlen == 0) { /* first round */
|
||||
pchar = ':';
|
||||
#ifdef ANCHOR
|
||||
el->el_search.patbuf[el->el_search.patlen++] = '.';
|
||||
el->el_search.patbuf[el->el_search.patlen++] = '*';
|
||||
#endif
|
||||
}
|
||||
done = redo = 0;
|
||||
*el->el_line.lastchar++ = '\n';
|
||||
for (cp = (newdir == ED_SEARCH_PREV_HISTORY) ? STRbck : STRfwd;
|
||||
*cp; *el->el_line.lastchar++ = *cp++)
|
||||
continue;
|
||||
*el->el_line.lastchar++ = pchar;
|
||||
for (cp = &el->el_search.patbuf[1];
|
||||
cp < &el->el_search.patbuf[el->el_search.patlen];
|
||||
*el->el_line.lastchar++ = *cp++)
|
||||
continue;
|
||||
*el->el_line.lastchar = '\0';
|
||||
re_refresh(el);
|
||||
|
||||
if (el_getc(el, &ch) != 1)
|
||||
return (ed_end_of_file(el, 0));
|
||||
|
||||
switch (el->el_map.current[(unsigned char) ch]) {
|
||||
case ED_INSERT:
|
||||
case ED_DIGIT:
|
||||
if (el->el_search.patlen > EL_BUFSIZ - 3)
|
||||
term_beep(el);
|
||||
else {
|
||||
el->el_search.patbuf[el->el_search.patlen++] =
|
||||
ch;
|
||||
*el->el_line.lastchar++ = ch;
|
||||
*el->el_line.lastchar = '\0';
|
||||
re_refresh(el);
|
||||
}
|
||||
break;
|
||||
|
||||
case EM_INC_SEARCH_NEXT:
|
||||
newdir = ED_SEARCH_NEXT_HISTORY;
|
||||
redo++;
|
||||
break;
|
||||
|
||||
case EM_INC_SEARCH_PREV:
|
||||
newdir = ED_SEARCH_PREV_HISTORY;
|
||||
redo++;
|
||||
break;
|
||||
|
||||
case ED_DELETE_PREV_CHAR:
|
||||
if (el->el_search.patlen > 1)
|
||||
done++;
|
||||
else
|
||||
term_beep(el);
|
||||
break;
|
||||
|
||||
default:
|
||||
switch (ch) {
|
||||
case 0007: /* ^G: Abort */
|
||||
ret = CC_ERROR;
|
||||
done++;
|
||||
break;
|
||||
|
||||
case 0027: /* ^W: Append word */
|
||||
/* No can do if globbing characters in pattern */
|
||||
for (cp = &el->el_search.patbuf[1];; cp++)
|
||||
if (cp >= &el->el_search.patbuf[el->el_search.patlen]) {
|
||||
el->el_line.cursor +=
|
||||
el->el_search.patlen - 1;
|
||||
cp = c__next_word(el->el_line.cursor,
|
||||
el->el_line.lastchar, 1,
|
||||
ce__isword);
|
||||
while (el->el_line.cursor < cp &&
|
||||
*el->el_line.cursor != '\n') {
|
||||
if (el->el_search.patlen >
|
||||
EL_BUFSIZ - 3) {
|
||||
term_beep(el);
|
||||
break;
|
||||
}
|
||||
el->el_search.patbuf[el->el_search.patlen++] =
|
||||
*el->el_line.cursor;
|
||||
*el->el_line.lastchar++ =
|
||||
*el->el_line.cursor++;
|
||||
}
|
||||
el->el_line.cursor = ocursor;
|
||||
*el->el_line.lastchar = '\0';
|
||||
re_refresh(el);
|
||||
break;
|
||||
} else if (isglob(*cp)) {
|
||||
term_beep(el);
|
||||
break;
|
||||
}
|
||||
break;
|
||||
|
||||
default: /* Terminate and execute cmd */
|
||||
endcmd[0] = ch;
|
||||
el_push(el, endcmd);
|
||||
/* FALLTHROUGH */
|
||||
|
||||
case 0033: /* ESC: Terminate */
|
||||
ret = CC_REFRESH;
|
||||
done++;
|
||||
break;
|
||||
}
|
||||
break;
|
||||
}
|
||||
|
||||
while (el->el_line.lastchar > el->el_line.buffer &&
|
||||
*el->el_line.lastchar != '\n')
|
||||
*el->el_line.lastchar-- = '\0';
|
||||
*el->el_line.lastchar = '\0';
|
||||
|
||||
if (!done) {
|
||||
|
||||
/* Can't search if unmatched '[' */
|
||||
for (cp = &el->el_search.patbuf[el->el_search.patlen-1],
|
||||
ch = ']';
|
||||
cp > el->el_search.patbuf;
|
||||
cp--)
|
||||
if (*cp == '[' || *cp == ']') {
|
||||
ch = *cp;
|
||||
break;
|
||||
}
|
||||
if (el->el_search.patlen > 1 && ch != '[') {
|
||||
if (redo && newdir == dir) {
|
||||
if (pchar == '?') { /* wrap around */
|
||||
el->el_history.eventno =
|
||||
newdir == ED_SEARCH_PREV_HISTORY ? 0 : 0x7fffffff;
|
||||
if (hist_get(el) == CC_ERROR)
|
||||
/* el->el_history.event
|
||||
* no was fixed by
|
||||
* first call */
|
||||
(void) hist_get(el);
|
||||
el->el_line.cursor = newdir ==
|
||||
ED_SEARCH_PREV_HISTORY ?
|
||||
el->el_line.lastchar :
|
||||
el->el_line.buffer;
|
||||
} else
|
||||
el->el_line.cursor +=
|
||||
newdir ==
|
||||
ED_SEARCH_PREV_HISTORY ?
|
||||
-1 : 1;
|
||||
}
|
||||
#ifdef ANCHOR
|
||||
el->el_search.patbuf[el->el_search.patlen++] =
|
||||
'.';
|
||||
el->el_search.patbuf[el->el_search.patlen++] =
|
||||
'*';
|
||||
#endif
|
||||
el->el_search.patbuf[el->el_search.patlen] =
|
||||
'\0';
|
||||
if (el->el_line.cursor < el->el_line.buffer ||
|
||||
el->el_line.cursor > el->el_line.lastchar ||
|
||||
(ret = ce_search_line(el,
|
||||
&el->el_search.patbuf[1],
|
||||
newdir)) == CC_ERROR) {
|
||||
/* avoid c_setpat */
|
||||
el->el_state.lastcmd =
|
||||
(el_action_t) newdir;
|
||||
ret = newdir == ED_SEARCH_PREV_HISTORY ?
|
||||
ed_search_prev_history(el, 0) :
|
||||
ed_search_next_history(el, 0);
|
||||
if (ret != CC_ERROR) {
|
||||
el->el_line.cursor = newdir ==
|
||||
ED_SEARCH_PREV_HISTORY ?
|
||||
el->el_line.lastchar :
|
||||
el->el_line.buffer;
|
||||
(void) ce_search_line(el,
|
||||
&el->el_search.patbuf[1],
|
||||
newdir);
|
||||
}
|
||||
}
|
||||
el->el_search.patbuf[--el->el_search.patlen] =
|
||||
'\0';
|
||||
if (ret == CC_ERROR) {
|
||||
term_beep(el);
|
||||
if (el->el_history.eventno !=
|
||||
ohisteventno) {
|
||||
el->el_history.eventno =
|
||||
ohisteventno;
|
||||
if (hist_get(el) == CC_ERROR)
|
||||
return (CC_ERROR);
|
||||
}
|
||||
el->el_line.cursor = ocursor;
|
||||
pchar = '?';
|
||||
} else {
|
||||
pchar = ':';
|
||||
}
|
||||
}
|
||||
ret = ce_inc_search(el, newdir);
|
||||
|
||||
if (ret == CC_ERROR && pchar == '?' && oldpchar == ':')
|
||||
/*
|
||||
* break abort of failed search at last
|
||||
* non-failed
|
||||
*/
|
||||
ret = CC_NORM;
|
||||
|
||||
}
|
||||
if (ret == CC_NORM || (ret == CC_ERROR && oldpatlen == 0)) {
|
||||
/* restore on normal return or error exit */
|
||||
pchar = oldpchar;
|
||||
el->el_search.patlen = oldpatlen;
|
||||
if (el->el_history.eventno != ohisteventno) {
|
||||
el->el_history.eventno = ohisteventno;
|
||||
if (hist_get(el) == CC_ERROR)
|
||||
return (CC_ERROR);
|
||||
}
|
||||
el->el_line.cursor = ocursor;
|
||||
if (ret == CC_ERROR)
|
||||
re_refresh(el);
|
||||
}
|
||||
if (done || ret != CC_NORM)
|
||||
return (ret);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/* cv_search():
|
||||
* Vi search.
|
||||
*/
|
||||
protected el_action_t
|
||||
cv_search(EditLine *el, int dir)
|
||||
{
|
||||
char ch;
|
||||
char tmpbuf[EL_BUFSIZ];
|
||||
int tmplen;
|
||||
|
||||
tmplen = 0;
|
||||
#ifdef ANCHOR
|
||||
tmpbuf[tmplen++] = '.';
|
||||
tmpbuf[tmplen++] = '*';
|
||||
#endif
|
||||
|
||||
el->el_line.buffer[0] = '\0';
|
||||
el->el_line.lastchar = el->el_line.buffer;
|
||||
el->el_line.cursor = el->el_line.buffer;
|
||||
el->el_search.patdir = dir;
|
||||
|
||||
c_insert(el, 2); /* prompt + '\n' */
|
||||
*el->el_line.cursor++ = '\n';
|
||||
*el->el_line.cursor++ = dir == ED_SEARCH_PREV_HISTORY ? '/' : '?';
|
||||
re_refresh(el);
|
||||
|
||||
#ifdef ANCHOR
|
||||
#define LEN 2
|
||||
#else
|
||||
#define LEN 0
|
||||
#endif
|
||||
|
||||
tmplen = c_gets(el, &tmpbuf[LEN]) + LEN;
|
||||
ch = tmpbuf[tmplen];
|
||||
tmpbuf[tmplen] = '\0';
|
||||
|
||||
if (tmplen == LEN) {
|
||||
/*
|
||||
* Use the old pattern, but wild-card it.
|
||||
*/
|
||||
if (el->el_search.patlen == 0) {
|
||||
el->el_line.buffer[0] = '\0';
|
||||
el->el_line.lastchar = el->el_line.buffer;
|
||||
el->el_line.cursor = el->el_line.buffer;
|
||||
re_refresh(el);
|
||||
return (CC_ERROR);
|
||||
}
|
||||
#ifdef ANCHOR
|
||||
if (el->el_search.patbuf[0] != '.' &&
|
||||
el->el_search.patbuf[0] != '*') {
|
||||
(void) strncpy(tmpbuf, el->el_search.patbuf,
|
||||
sizeof(tmpbuf) - 1);
|
||||
el->el_search.patbuf[0] = '.';
|
||||
el->el_search.patbuf[1] = '*';
|
||||
(void) strncpy(&el->el_search.patbuf[2], tmpbuf,
|
||||
EL_BUFSIZ - 3);
|
||||
el->el_search.patlen++;
|
||||
el->el_search.patbuf[el->el_search.patlen++] = '.';
|
||||
el->el_search.patbuf[el->el_search.patlen++] = '*';
|
||||
el->el_search.patbuf[el->el_search.patlen] = '\0';
|
||||
}
|
||||
#endif
|
||||
} else {
|
||||
#ifdef ANCHOR
|
||||
tmpbuf[tmplen++] = '.';
|
||||
tmpbuf[tmplen++] = '*';
|
||||
#endif
|
||||
tmpbuf[tmplen] = '\0';
|
||||
(void) strncpy(el->el_search.patbuf, tmpbuf, EL_BUFSIZ - 1);
|
||||
el->el_search.patlen = tmplen;
|
||||
}
|
||||
el->el_state.lastcmd = (el_action_t) dir; /* avoid c_setpat */
|
||||
el->el_line.cursor = el->el_line.lastchar = el->el_line.buffer;
|
||||
if ((dir == ED_SEARCH_PREV_HISTORY ? ed_search_prev_history(el, 0) :
|
||||
ed_search_next_history(el, 0)) == CC_ERROR) {
|
||||
re_refresh(el);
|
||||
return (CC_ERROR);
|
||||
} else {
|
||||
if (ch == 0033) {
|
||||
re_refresh(el);
|
||||
*el->el_line.lastchar++ = '\n';
|
||||
*el->el_line.lastchar = '\0';
|
||||
re_goto_bottom(el);
|
||||
return (CC_NEWLINE);
|
||||
} else
|
||||
return (CC_REFRESH);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/* ce_search_line():
|
||||
* Look for a pattern inside a line
|
||||
*/
|
||||
protected el_action_t
|
||||
ce_search_line(EditLine *el, char *pattern, int dir)
|
||||
{
|
||||
char *cp;
|
||||
|
||||
if (dir == ED_SEARCH_PREV_HISTORY) {
|
||||
for (cp = el->el_line.cursor; cp >= el->el_line.buffer; cp--)
|
||||
if (el_match(cp, pattern)) {
|
||||
el->el_line.cursor = cp;
|
||||
return (CC_NORM);
|
||||
}
|
||||
return (CC_ERROR);
|
||||
} else {
|
||||
for (cp = el->el_line.cursor; *cp != '\0' &&
|
||||
cp < el->el_line.limit; cp++)
|
||||
if (el_match(cp, pattern)) {
|
||||
el->el_line.cursor = cp;
|
||||
return (CC_NORM);
|
||||
}
|
||||
return (CC_ERROR);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/* cv_repeat_srch():
|
||||
* Vi repeat search
|
||||
*/
|
||||
protected el_action_t
|
||||
cv_repeat_srch(EditLine *el, int c)
|
||||
{
|
||||
|
||||
#ifdef SDEBUG
|
||||
(void) fprintf(el->el_errfile, "dir %d patlen %d patbuf %s\n",
|
||||
c, el->el_search.patlen, el->el_search.patbuf);
|
||||
#endif
|
||||
|
||||
el->el_state.lastcmd = (el_action_t) c; /* Hack to stop c_setpat */
|
||||
el->el_line.lastchar = el->el_line.buffer;
|
||||
|
||||
switch (c) {
|
||||
case ED_SEARCH_NEXT_HISTORY:
|
||||
return (ed_search_next_history(el, 0));
|
||||
case ED_SEARCH_PREV_HISTORY:
|
||||
return (ed_search_prev_history(el, 0));
|
||||
default:
|
||||
return (CC_ERROR);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/* cv_csearch_back():
|
||||
* Vi character search reverse
|
||||
*/
|
||||
protected el_action_t
|
||||
cv_csearch_back(EditLine *el, int ch, int count, int tflag)
|
||||
{
|
||||
char *cp;
|
||||
|
||||
cp = el->el_line.cursor;
|
||||
while (count--) {
|
||||
if (*cp == ch)
|
||||
cp--;
|
||||
while (cp > el->el_line.buffer && *cp != ch)
|
||||
cp--;
|
||||
}
|
||||
|
||||
if (cp < el->el_line.buffer || (cp == el->el_line.buffer && *cp != ch))
|
||||
return (CC_ERROR);
|
||||
|
||||
if (*cp == ch && tflag)
|
||||
cp++;
|
||||
|
||||
el->el_line.cursor = cp;
|
||||
|
||||
if (el->el_chared.c_vcmd.action & DELETE) {
|
||||
el->el_line.cursor++;
|
||||
cv_delfini(el);
|
||||
return (CC_REFRESH);
|
||||
}
|
||||
re_refresh_cursor(el);
|
||||
return (CC_NORM);
|
||||
}
|
||||
|
||||
|
||||
/* cv_csearch_fwd():
|
||||
* Vi character search forward
|
||||
*/
|
||||
protected el_action_t
|
||||
cv_csearch_fwd(EditLine *el, int ch, int count, int tflag)
|
||||
{
|
||||
char *cp;
|
||||
|
||||
cp = el->el_line.cursor;
|
||||
while (count--) {
|
||||
if (*cp == ch)
|
||||
cp++;
|
||||
while (cp < el->el_line.lastchar && *cp != ch)
|
||||
cp++;
|
||||
}
|
||||
|
||||
if (cp >= el->el_line.lastchar)
|
||||
return (CC_ERROR);
|
||||
|
||||
if (*cp == ch && tflag)
|
||||
cp--;
|
||||
|
||||
el->el_line.cursor = cp;
|
||||
|
||||
if (el->el_chared.c_vcmd.action & DELETE) {
|
||||
el->el_line.cursor++;
|
||||
cv_delfini(el);
|
||||
return (CC_REFRESH);
|
||||
}
|
||||
re_refresh_cursor(el);
|
||||
return (CC_NORM);
|
||||
}
|
@@ -1,70 +0,0 @@
|
||||
/* $NetBSD: search.h,v 1.5 2000/09/04 22:06:32 lukem Exp $ */
|
||||
|
||||
/*-
|
||||
* Copyright (c) 1992, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* This code is derived from software contributed to Berkeley by
|
||||
* Christos Zoulas of Cornell University.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
* 3. All advertising materials mentioning features or use of this software
|
||||
* must display the following acknowledgement:
|
||||
* This product includes software developed by the University of
|
||||
* California, Berkeley and its contributors.
|
||||
* 4. Neither the name of the University nor the names of its contributors
|
||||
* may be used to endorse or promote products derived from this software
|
||||
* without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
|
||||
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
* ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
|
||||
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
|
||||
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* @(#)search.h 8.1 (Berkeley) 6/4/93
|
||||
*/
|
||||
|
||||
/*
|
||||
* el.search.h: Line and history searching utilities
|
||||
*/
|
||||
#ifndef _h_el_search
|
||||
#define _h_el_search
|
||||
|
||||
#include "histedit.h"
|
||||
|
||||
typedef struct el_search_t {
|
||||
char *patbuf; /* The pattern buffer */
|
||||
size_t patlen; /* Length of the pattern buffer */
|
||||
int patdir; /* Direction of the last search */
|
||||
int chadir; /* Character search direction */
|
||||
char chacha; /* Character we are looking for */
|
||||
} el_search_t;
|
||||
|
||||
|
||||
protected int el_match(const char *, const char *);
|
||||
protected int search_init(EditLine *);
|
||||
protected void search_end(EditLine *);
|
||||
protected int c_hmatch(EditLine *, const char *);
|
||||
protected void c_setpat(EditLine *);
|
||||
protected el_action_t ce_inc_search(EditLine *, int);
|
||||
protected el_action_t cv_search(EditLine *, int);
|
||||
protected el_action_t ce_search_line(EditLine *, char *, int);
|
||||
protected el_action_t cv_repeat_srch(EditLine *, int);
|
||||
protected el_action_t cv_csearch_back(EditLine *, int, int, int);
|
||||
protected el_action_t cv_csearch_fwd(EditLine *, int, int, int);
|
||||
|
||||
#endif /* _h_el_search */
|
@@ -1,198 +0,0 @@
|
||||
/* $NetBSD: sig.c,v 1.9 2002/03/18 16:00:58 christos Exp $ */
|
||||
|
||||
/*-
|
||||
* Copyright (c) 1992, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* This code is derived from software contributed to Berkeley by
|
||||
* Christos Zoulas of Cornell University.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
* 3. All advertising materials mentioning features or use of this software
|
||||
* must display the following acknowledgement:
|
||||
* This product includes software developed by the University of
|
||||
* California, Berkeley and its contributors.
|
||||
* 4. Neither the name of the University nor the names of its contributors
|
||||
* may be used to endorse or promote products derived from this software
|
||||
* without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
|
||||
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
* ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
|
||||
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
|
||||
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*/
|
||||
|
||||
#include "config.h"
|
||||
#if !defined(lint) && !defined(SCCSID)
|
||||
#if 0
|
||||
static char sccsid[] = "@(#)sig.c 8.1 (Berkeley) 6/4/93";
|
||||
#else
|
||||
__RCSID("$NetBSD: sig.c,v 1.9 2002/03/18 16:00:58 christos Exp $");
|
||||
#endif
|
||||
#endif /* not lint && not SCCSID */
|
||||
|
||||
/*
|
||||
* sig.c: Signal handling stuff.
|
||||
* our policy is to trap all signals, set a good state
|
||||
* and pass the ball to our caller.
|
||||
*/
|
||||
#include "el.h"
|
||||
#include <stdlib.h>
|
||||
|
||||
private EditLine *sel = NULL;
|
||||
|
||||
private const int sighdl[] = {
|
||||
#define _DO(a) (a),
|
||||
ALLSIGS
|
||||
#undef _DO
|
||||
- 1
|
||||
};
|
||||
|
||||
private void sig_handler(int);
|
||||
|
||||
/* sig_handler():
|
||||
* This is the handler called for all signals
|
||||
* XXX: we cannot pass any data so we just store the old editline
|
||||
* state in a private variable
|
||||
*/
|
||||
private void
|
||||
sig_handler(int signo)
|
||||
{
|
||||
int i;
|
||||
sigset_t nset, oset;
|
||||
|
||||
(void) sigemptyset(&nset);
|
||||
(void) sigaddset(&nset, signo);
|
||||
(void) sigprocmask(SIG_BLOCK, &nset, &oset);
|
||||
|
||||
switch (signo) {
|
||||
case SIGCONT:
|
||||
tty_rawmode(sel);
|
||||
if (ed_redisplay(sel, 0) == CC_REFRESH)
|
||||
re_refresh(sel);
|
||||
term__flush();
|
||||
break;
|
||||
|
||||
case SIGWINCH:
|
||||
el_resize(sel);
|
||||
break;
|
||||
|
||||
default:
|
||||
tty_cookedmode(sel);
|
||||
break;
|
||||
}
|
||||
|
||||
for (i = 0; sighdl[i] != -1; i++)
|
||||
if (signo == sighdl[i])
|
||||
break;
|
||||
|
||||
(void) signal(signo, sel->el_signal[i]);
|
||||
(void) sigprocmask(SIG_SETMASK, &oset, NULL);
|
||||
(void) kill(0, signo);
|
||||
}
|
||||
|
||||
|
||||
/* sig_init():
|
||||
* Initialize all signal stuff
|
||||
*/
|
||||
protected int
|
||||
sig_init(EditLine *el)
|
||||
{
|
||||
int i;
|
||||
sigset_t nset, oset;
|
||||
|
||||
(void) sigemptyset(&nset);
|
||||
#define _DO(a) (void) sigaddset(&nset, a);
|
||||
ALLSIGS
|
||||
#undef _DO
|
||||
(void) sigprocmask(SIG_BLOCK, &nset, &oset);
|
||||
|
||||
#define SIGSIZE (sizeof(sighdl) / sizeof(sighdl[0]) * sizeof(sig_t))
|
||||
|
||||
el->el_signal = (sig_t *) el_malloc(SIGSIZE);
|
||||
if (el->el_signal == NULL)
|
||||
return (-1);
|
||||
for (i = 0; sighdl[i] != -1; i++)
|
||||
el->el_signal[i] = SIG_ERR;
|
||||
|
||||
(void) sigprocmask(SIG_SETMASK, &oset, NULL);
|
||||
|
||||
return (0);
|
||||
}
|
||||
|
||||
|
||||
/* sig_end():
|
||||
* Clear all signal stuff
|
||||
*/
|
||||
protected void
|
||||
sig_end(EditLine *el)
|
||||
{
|
||||
|
||||
el_free((ptr_t) el->el_signal);
|
||||
el->el_signal = NULL;
|
||||
}
|
||||
|
||||
|
||||
/* sig_set():
|
||||
* set all the signal handlers
|
||||
*/
|
||||
protected void
|
||||
sig_set(EditLine *el)
|
||||
{
|
||||
int i;
|
||||
sigset_t nset, oset;
|
||||
|
||||
(void) sigemptyset(&nset);
|
||||
#define _DO(a) (void) sigaddset(&nset, a);
|
||||
ALLSIGS
|
||||
#undef _DO
|
||||
(void) sigprocmask(SIG_BLOCK, &nset, &oset);
|
||||
|
||||
for (i = 0; sighdl[i] != -1; i++) {
|
||||
sig_t s;
|
||||
/* This could happen if we get interrupted */
|
||||
if ((s = signal(sighdl[i], sig_handler)) != sig_handler)
|
||||
el->el_signal[i] = s;
|
||||
}
|
||||
sel = el;
|
||||
(void) sigprocmask(SIG_SETMASK, &oset, NULL);
|
||||
}
|
||||
|
||||
|
||||
/* sig_clr():
|
||||
* clear all the signal handlers
|
||||
*/
|
||||
protected void
|
||||
sig_clr(EditLine *el)
|
||||
{
|
||||
int i;
|
||||
sigset_t nset, oset;
|
||||
|
||||
(void) sigemptyset(&nset);
|
||||
#define _DO(a) (void) sigaddset(&nset, a);
|
||||
ALLSIGS
|
||||
#undef _DO
|
||||
(void) sigprocmask(SIG_BLOCK, &nset, &oset);
|
||||
|
||||
for (i = 0; sighdl[i] != -1; i++)
|
||||
if (el->el_signal[i] != SIG_ERR)
|
||||
(void) signal(sighdl[i], el->el_signal[i]);
|
||||
|
||||
sel = NULL; /* we are going to die if the handler is
|
||||
* called */
|
||||
(void) sigprocmask(SIG_SETMASK, &oset, NULL);
|
||||
}
|
@@ -1,72 +0,0 @@
|
||||
/* $NetBSD: sig.h,v 1.3 2000/09/04 22:06:32 lukem Exp $ */
|
||||
|
||||
/*-
|
||||
* Copyright (c) 1992, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* This code is derived from software contributed to Berkeley by
|
||||
* Christos Zoulas of Cornell University.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
* 3. All advertising materials mentioning features or use of this software
|
||||
* must display the following acknowledgement:
|
||||
* This product includes software developed by the University of
|
||||
* California, Berkeley and its contributors.
|
||||
* 4. Neither the name of the University nor the names of its contributors
|
||||
* may be used to endorse or promote products derived from this software
|
||||
* without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
|
||||
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
* ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
|
||||
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
|
||||
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* @(#)sig.h 8.1 (Berkeley) 6/4/93
|
||||
*/
|
||||
|
||||
/*
|
||||
* el.sig.h: Signal handling functions
|
||||
*/
|
||||
#ifndef _h_el_sig
|
||||
#define _h_el_sig
|
||||
|
||||
#include <signal.h>
|
||||
|
||||
#include "histedit.h"
|
||||
|
||||
/*
|
||||
* Define here all the signals we are going to handle
|
||||
* The _DO macro is used to iterate in the source code
|
||||
*/
|
||||
#define ALLSIGS \
|
||||
_DO(SIGINT) \
|
||||
_DO(SIGTSTP) \
|
||||
_DO(SIGSTOP) \
|
||||
_DO(SIGQUIT) \
|
||||
_DO(SIGHUP) \
|
||||
_DO(SIGTERM) \
|
||||
_DO(SIGCONT) \
|
||||
_DO(SIGWINCH)
|
||||
|
||||
typedef sig_t *el_signal_t;
|
||||
|
||||
protected void sig_end(EditLine*);
|
||||
protected int sig_init(EditLine*);
|
||||
protected void sig_set(EditLine*);
|
||||
protected void sig_clr(EditLine*);
|
||||
|
||||
#endif /* _h_el_sig */
|
@@ -1,135 +0,0 @@
|
||||
/* $NetBSD: sys.h,v 1.5 2002/03/18 16:00:59 christos Exp $ */
|
||||
|
||||
/*-
|
||||
* Copyright (c) 1992, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* This code is derived from software contributed to Berkeley by
|
||||
* Christos Zoulas of Cornell University.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
* 3. All advertising materials mentioning features or use of this software
|
||||
* must display the following acknowledgement:
|
||||
* This product includes software developed by the University of
|
||||
* California, Berkeley and its contributors.
|
||||
* 4. Neither the name of the University nor the names of its contributors
|
||||
* may be used to endorse or promote products derived from this software
|
||||
* without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
|
||||
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
* ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
|
||||
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
|
||||
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* @(#)sys.h 8.1 (Berkeley) 6/4/93
|
||||
*/
|
||||
|
||||
/*
|
||||
* sys.h: Put all the stupid compiler and system dependencies here...
|
||||
*/
|
||||
#ifndef _h_sys
|
||||
#define _h_sys
|
||||
|
||||
#ifndef public
|
||||
# define public /* Externally visible functions/variables */
|
||||
#endif
|
||||
|
||||
#ifndef private
|
||||
# define private static /* Always hidden internals */
|
||||
#endif
|
||||
|
||||
#ifndef protected
|
||||
# define protected /* Redefined from elsewhere to "static" */
|
||||
/* When we want to hide everything */
|
||||
#endif
|
||||
|
||||
#ifndef _PTR_T
|
||||
# define _PTR_T
|
||||
typedef void *ptr_t;
|
||||
#endif
|
||||
|
||||
#ifndef _IOCTL_T
|
||||
# define _IOCTL_T
|
||||
typedef void *ioctl_t;
|
||||
#endif
|
||||
|
||||
#include <stdio.h>
|
||||
|
||||
#ifndef HAVE_FGETLN
|
||||
#define fgetln libedit_fgetln
|
||||
char *fgetln(FILE *fp, size_t *len);
|
||||
#endif
|
||||
|
||||
#ifndef HAVE_STRLCPY
|
||||
#undef strlcpy /* We define this in top-level Asterisk to point towards ast_copy_string */
|
||||
#define strlcpy libedit_strlcpy
|
||||
size_t strlcpy(char *dst, const char *src, size_t siz);
|
||||
#endif
|
||||
|
||||
#ifndef HAVE_STRLCAT
|
||||
#undef strlcat /* We define this in top-level Asterisk to point towards the ast_str_* APIs */
|
||||
#define strlcat libedit_strlcat
|
||||
size_t strlcat(char *dst, const char *src, size_t siz);
|
||||
#endif
|
||||
|
||||
#define REGEX /* Use POSIX.2 regular expression functions */
|
||||
#undef REGEXP /* Use UNIX V8 regular expression functions */
|
||||
|
||||
#ifdef SUNOS
|
||||
# undef REGEX
|
||||
# undef REGEXP
|
||||
/* # include <malloc.h> XXX Removed for Solaris build XXX */
|
||||
typedef void (*sig_t)(int);
|
||||
# ifdef __GNUC__
|
||||
/*
|
||||
* Broken hdrs.
|
||||
*/
|
||||
#ifndef SOLARIS
|
||||
extern int tgetent(const char *bp, char *name);
|
||||
extern int tgetflag(const char *id);
|
||||
extern int tgetnum(const char *id);
|
||||
extern char *tgetstr(const char *id, char **area);
|
||||
#endif
|
||||
extern char *tgoto(const char *cap, int col, int row);
|
||||
extern int tputs(const char *str, int affcnt, int (*putc)(int));
|
||||
extern char *getenv(const char *);
|
||||
extern int fprintf(FILE *, const char *, ...);
|
||||
extern int sigsetmask(int);
|
||||
extern int sigblock(int);
|
||||
extern int fputc(int, FILE *);
|
||||
extern int fgetc(FILE *);
|
||||
extern int fflush(FILE *);
|
||||
extern int tolower(int);
|
||||
extern int toupper(int);
|
||||
extern int errno, sys_nerr;
|
||||
extern char *sys_errlist[];
|
||||
extern void perror(const char *);
|
||||
# include <string.h>
|
||||
# define strerror(e) sys_errlist[e]
|
||||
# endif
|
||||
# ifdef SABER
|
||||
extern ptr_t memcpy(ptr_t, const ptr_t, size_t);
|
||||
extern ptr_t memset(ptr_t, int, size_t);
|
||||
# endif
|
||||
extern char *fgetline(FILE *, int *);
|
||||
#endif
|
||||
|
||||
#ifdef HAVE_SYS_CDEFS_H
|
||||
#include <sys/cdefs.h>
|
||||
#endif
|
||||
|
||||
#endif /* _h_sys */
|
1587
main/editline/term.c
1587
main/editline/term.c
File diff suppressed because it is too large
Load Diff
@@ -1,124 +0,0 @@
|
||||
/* $NetBSD: term.h,v 1.13 2002/03/18 16:01:00 christos Exp $ */
|
||||
|
||||
/*-
|
||||
* Copyright (c) 1992, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* This code is derived from software contributed to Berkeley by
|
||||
* Christos Zoulas of Cornell University.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
* 3. All advertising materials mentioning features or use of this software
|
||||
* must display the following acknowledgement:
|
||||
* This product includes software developed by the University of
|
||||
* California, Berkeley and its contributors.
|
||||
* 4. Neither the name of the University nor the names of its contributors
|
||||
* may be used to endorse or promote products derived from this software
|
||||
* without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
|
||||
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
* ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
|
||||
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
|
||||
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* @(#)term.h 8.1 (Berkeley) 6/4/93
|
||||
*/
|
||||
|
||||
/*
|
||||
* el.term.h: Termcap header
|
||||
*/
|
||||
#ifndef _h_el_term
|
||||
#define _h_el_term
|
||||
|
||||
#include "histedit.h"
|
||||
|
||||
typedef struct { /* Symbolic function key bindings */
|
||||
const char *name; /* name of the key */
|
||||
int key; /* Index in termcap table */
|
||||
key_value_t fun; /* Function bound to it */
|
||||
int type; /* Type of function */
|
||||
} fkey_t;
|
||||
|
||||
typedef struct {
|
||||
coord_t t_size; /* # lines and cols */
|
||||
int t_flags;
|
||||
#define TERM_CAN_INSERT 0x001 /* Has insert cap */
|
||||
#define TERM_CAN_DELETE 0x002 /* Has delete cap */
|
||||
#define TERM_CAN_CEOL 0x004 /* Has CEOL cap */
|
||||
#define TERM_CAN_TAB 0x008 /* Can use tabs */
|
||||
#define TERM_CAN_ME 0x010 /* Can turn all attrs. */
|
||||
#define TERM_CAN_UP 0x020 /* Can move up */
|
||||
#define TERM_HAS_META 0x040 /* Has a meta key */
|
||||
#define TERM_HAS_AUTO_MARGINS 0x080 /* Has auto margins */
|
||||
#define TERM_HAS_MAGIC_MARGINS 0x100 /* Has magic margins */
|
||||
char *t_buf; /* Termcap buffer */
|
||||
int t_loc; /* location used */
|
||||
char **t_str; /* termcap strings */
|
||||
int *t_val; /* termcap values */
|
||||
char *t_cap; /* Termcap buffer */
|
||||
fkey_t *t_fkey; /* Array of keys */
|
||||
} el_term_t;
|
||||
|
||||
/*
|
||||
* fKey indexes
|
||||
*/
|
||||
#define A_K_DN 0
|
||||
#define A_K_UP 1
|
||||
#define A_K_LT 2
|
||||
#define A_K_RT 3
|
||||
#define A_K_HO 4
|
||||
#define A_K_EN 5
|
||||
#define A_K_NKEYS 6
|
||||
|
||||
protected void term_move_to_line(EditLine *, int);
|
||||
protected void term_move_to_char(EditLine *, int);
|
||||
protected void term_clear_EOL(EditLine *, int);
|
||||
protected void term_overwrite(EditLine *, const char *, int);
|
||||
protected void term_insertwrite(EditLine *, char *, int);
|
||||
protected void term_deletechars(EditLine *, int);
|
||||
protected void term_clear_screen(EditLine *);
|
||||
protected void term_beep(EditLine *);
|
||||
protected int term_change_size(EditLine *, int, int);
|
||||
protected int term_get_size(EditLine *, int *, int *);
|
||||
protected int term_init(EditLine *);
|
||||
protected void term_bind_arrow(EditLine *);
|
||||
protected void term_print_arrow(EditLine *, const char *);
|
||||
protected int term_clear_arrow(EditLine *, const char *);
|
||||
protected int term_set_arrow(EditLine *, const char *, key_value_t *, int);
|
||||
protected void term_end(EditLine *);
|
||||
protected int term_set(EditLine *, const char *);
|
||||
protected int term_settc(EditLine *, int, const char **);
|
||||
protected int term_telltc(EditLine *, int, const char **);
|
||||
protected int term_echotc(EditLine *, int, const char **);
|
||||
protected int term__putc(int);
|
||||
protected void term__flush(void);
|
||||
|
||||
/*
|
||||
* Easy access macros
|
||||
*/
|
||||
#define EL_FLAGS (el)->el_term.t_flags
|
||||
|
||||
#define EL_CAN_INSERT (EL_FLAGS & TERM_CAN_INSERT)
|
||||
#define EL_CAN_DELETE (EL_FLAGS & TERM_CAN_DELETE)
|
||||
#define EL_CAN_CEOL (EL_FLAGS & TERM_CAN_CEOL)
|
||||
#define EL_CAN_TAB (EL_FLAGS & TERM_CAN_TAB)
|
||||
#define EL_CAN_ME (EL_FLAGS & TERM_CAN_ME)
|
||||
#define EL_HAS_META (EL_FLAGS & TERM_HAS_META)
|
||||
#define EL_HAS_AUTO_MARGINS (EL_FLAGS & TERM_HAS_AUTO_MARGINS)
|
||||
#define EL_HAS_MAGIC_MARGINS (EL_FLAGS & TERM_HAS_MAGIC_MARGINS)
|
||||
|
||||
#endif /* _h_el_term */
|
@@ -1,397 +0,0 @@
|
||||
/* $NetBSD: tokenizer.c,v 1.10 2002/03/18 16:01:00 christos Exp $ */
|
||||
|
||||
/*-
|
||||
* Copyright (c) 1992, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* This code is derived from software contributed to Berkeley by
|
||||
* Christos Zoulas of Cornell University.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
* 3. All advertising materials mentioning features or use of this software
|
||||
* must display the following acknowledgement:
|
||||
* This product includes software developed by the University of
|
||||
* California, Berkeley and its contributors.
|
||||
* 4. Neither the name of the University nor the names of its contributors
|
||||
* may be used to endorse or promote products derived from this software
|
||||
* without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
|
||||
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
* ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
|
||||
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
|
||||
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*/
|
||||
|
||||
#include "config.h"
|
||||
#if !defined(lint) && !defined(SCCSID)
|
||||
#if 0
|
||||
static char sccsid[] = "@(#)tokenizer.c 8.1 (Berkeley) 6/4/93";
|
||||
#else
|
||||
__RCSID("$NetBSD: tokenizer.c,v 1.10 2002/03/18 16:01:00 christos Exp $");
|
||||
#endif
|
||||
#endif /* not lint && not SCCSID */
|
||||
|
||||
/*
|
||||
* tokenize.c: Bourne shell like tokenizer
|
||||
*/
|
||||
#include <string.h>
|
||||
#include <stdlib.h>
|
||||
#include "tokenizer.h"
|
||||
|
||||
typedef enum {
|
||||
Q_none, Q_single, Q_double, Q_one, Q_doubleone
|
||||
} quote_t;
|
||||
|
||||
#define IFS "\t \n"
|
||||
|
||||
#define TOK_KEEP 1
|
||||
#define TOK_EAT 2
|
||||
|
||||
#define WINCR 20
|
||||
#define AINCR 10
|
||||
|
||||
#define tok_malloc(a) malloc(a)
|
||||
#define tok_free(a) free(a)
|
||||
#define tok_realloc(a, b) realloc(a, b)
|
||||
|
||||
|
||||
struct tokenizer {
|
||||
char *ifs; /* In field separator */
|
||||
int argc, amax; /* Current and maximum number of args */
|
||||
char **argv; /* Argument list */
|
||||
char *wptr, *wmax; /* Space and limit on the word buffer */
|
||||
char *wstart; /* Beginning of next word */
|
||||
char *wspace; /* Space of word buffer */
|
||||
quote_t quote; /* Quoting state */
|
||||
int flags; /* flags; */
|
||||
};
|
||||
|
||||
|
||||
private void tok_finish(Tokenizer *);
|
||||
|
||||
|
||||
/* tok_finish():
|
||||
* Finish a word in the tokenizer.
|
||||
*/
|
||||
private void
|
||||
tok_finish(Tokenizer *tok)
|
||||
{
|
||||
|
||||
*tok->wptr = '\0';
|
||||
if ((tok->flags & TOK_KEEP) || tok->wptr != tok->wstart) {
|
||||
tok->argv[tok->argc++] = tok->wstart;
|
||||
tok->argv[tok->argc] = NULL;
|
||||
tok->wstart = ++tok->wptr;
|
||||
}
|
||||
tok->flags &= ~TOK_KEEP;
|
||||
}
|
||||
|
||||
|
||||
/* tok_init():
|
||||
* Initialize the tokenizer
|
||||
*/
|
||||
public Tokenizer *
|
||||
tok_init(const char *ifs)
|
||||
{
|
||||
Tokenizer *tok = (Tokenizer *) tok_malloc(sizeof(Tokenizer));
|
||||
|
||||
tok->ifs = strdup(ifs ? ifs : IFS);
|
||||
tok->argc = 0;
|
||||
tok->amax = AINCR;
|
||||
tok->argv = (char **) tok_malloc(sizeof(char *) * tok->amax);
|
||||
if (tok->argv == NULL)
|
||||
return (NULL);
|
||||
tok->argv[0] = NULL;
|
||||
tok->wspace = (char *) tok_malloc(WINCR);
|
||||
if (tok->wspace == NULL)
|
||||
return (NULL);
|
||||
tok->wmax = tok->wspace + WINCR;
|
||||
tok->wstart = tok->wspace;
|
||||
tok->wptr = tok->wspace;
|
||||
tok->flags = 0;
|
||||
tok->quote = Q_none;
|
||||
|
||||
return (tok);
|
||||
}
|
||||
|
||||
|
||||
/* tok_reset():
|
||||
* Reset the tokenizer
|
||||
*/
|
||||
public void
|
||||
tok_reset(Tokenizer *tok)
|
||||
{
|
||||
|
||||
tok->argc = 0;
|
||||
tok->wstart = tok->wspace;
|
||||
tok->wptr = tok->wspace;
|
||||
tok->flags = 0;
|
||||
tok->quote = Q_none;
|
||||
}
|
||||
|
||||
|
||||
/* tok_end():
|
||||
* Clean up
|
||||
*/
|
||||
public void
|
||||
tok_end(Tokenizer *tok)
|
||||
{
|
||||
|
||||
tok_free((ptr_t) tok->ifs);
|
||||
tok_free((ptr_t) tok->wspace);
|
||||
tok_free((ptr_t) tok->argv);
|
||||
tok_free((ptr_t) tok);
|
||||
}
|
||||
|
||||
|
||||
|
||||
/* tok_line():
|
||||
* Bourne shell like tokenizing
|
||||
* Return:
|
||||
* -1: Internal error
|
||||
* 3: Quoted return
|
||||
* 2: Unmatched double quote
|
||||
* 1: Unmatched single quote
|
||||
* 0: Ok
|
||||
*/
|
||||
public int
|
||||
tok_line(Tokenizer *tok, const char *line, int *argc, const char ***argv)
|
||||
{
|
||||
const char *ptr;
|
||||
|
||||
for (;;) {
|
||||
switch (*(ptr = line++)) {
|
||||
case '\'':
|
||||
tok->flags |= TOK_KEEP;
|
||||
tok->flags &= ~TOK_EAT;
|
||||
switch (tok->quote) {
|
||||
case Q_none:
|
||||
tok->quote = Q_single; /* Enter single quote
|
||||
* mode */
|
||||
break;
|
||||
|
||||
case Q_single: /* Exit single quote mode */
|
||||
tok->quote = Q_none;
|
||||
break;
|
||||
|
||||
case Q_one: /* Quote this ' */
|
||||
tok->quote = Q_none;
|
||||
*tok->wptr++ = *ptr;
|
||||
break;
|
||||
|
||||
case Q_double: /* Stay in double quote mode */
|
||||
*tok->wptr++ = *ptr;
|
||||
break;
|
||||
|
||||
case Q_doubleone: /* Quote this ' */
|
||||
tok->quote = Q_double;
|
||||
*tok->wptr++ = *ptr;
|
||||
break;
|
||||
|
||||
default:
|
||||
return (-1);
|
||||
}
|
||||
break;
|
||||
|
||||
case '"':
|
||||
tok->flags &= ~TOK_EAT;
|
||||
tok->flags |= TOK_KEEP;
|
||||
switch (tok->quote) {
|
||||
case Q_none: /* Enter double quote mode */
|
||||
tok->quote = Q_double;
|
||||
break;
|
||||
|
||||
case Q_double: /* Exit double quote mode */
|
||||
tok->quote = Q_none;
|
||||
break;
|
||||
|
||||
case Q_one: /* Quote this " */
|
||||
tok->quote = Q_none;
|
||||
*tok->wptr++ = *ptr;
|
||||
break;
|
||||
|
||||
case Q_single: /* Stay in single quote mode */
|
||||
*tok->wptr++ = *ptr;
|
||||
break;
|
||||
|
||||
case Q_doubleone: /* Quote this " */
|
||||
tok->quote = Q_double;
|
||||
*tok->wptr++ = *ptr;
|
||||
break;
|
||||
|
||||
default:
|
||||
return (-1);
|
||||
}
|
||||
break;
|
||||
|
||||
case '\\':
|
||||
tok->flags |= TOK_KEEP;
|
||||
tok->flags &= ~TOK_EAT;
|
||||
switch (tok->quote) {
|
||||
case Q_none: /* Quote next character */
|
||||
tok->quote = Q_one;
|
||||
break;
|
||||
|
||||
case Q_double: /* Quote next character */
|
||||
tok->quote = Q_doubleone;
|
||||
break;
|
||||
|
||||
case Q_one: /* Quote this, restore state */
|
||||
*tok->wptr++ = *ptr;
|
||||
tok->quote = Q_none;
|
||||
break;
|
||||
|
||||
case Q_single: /* Stay in single quote mode */
|
||||
*tok->wptr++ = *ptr;
|
||||
break;
|
||||
|
||||
case Q_doubleone: /* Quote this \ */
|
||||
tok->quote = Q_double;
|
||||
*tok->wptr++ = *ptr;
|
||||
break;
|
||||
|
||||
default:
|
||||
return (-1);
|
||||
}
|
||||
break;
|
||||
|
||||
case '\n':
|
||||
tok->flags &= ~TOK_EAT;
|
||||
switch (tok->quote) {
|
||||
case Q_none:
|
||||
tok_finish(tok);
|
||||
*argv = (const char **)tok->argv;
|
||||
*argc = tok->argc;
|
||||
return (0);
|
||||
|
||||
case Q_single:
|
||||
case Q_double:
|
||||
*tok->wptr++ = *ptr; /* Add the return */
|
||||
break;
|
||||
|
||||
case Q_doubleone: /* Back to double, eat the '\n' */
|
||||
tok->flags |= TOK_EAT;
|
||||
tok->quote = Q_double;
|
||||
break;
|
||||
|
||||
case Q_one: /* No quote, more eat the '\n' */
|
||||
tok->flags |= TOK_EAT;
|
||||
tok->quote = Q_none;
|
||||
break;
|
||||
|
||||
default:
|
||||
return (0);
|
||||
}
|
||||
break;
|
||||
|
||||
case '\0':
|
||||
switch (tok->quote) {
|
||||
case Q_none:
|
||||
/* Finish word and return */
|
||||
if (tok->flags & TOK_EAT) {
|
||||
tok->flags &= ~TOK_EAT;
|
||||
return (3);
|
||||
}
|
||||
tok_finish(tok);
|
||||
*argv = (const char **)tok->argv;
|
||||
*argc = tok->argc;
|
||||
return (0);
|
||||
|
||||
case Q_single:
|
||||
return (1);
|
||||
|
||||
case Q_double:
|
||||
return (2);
|
||||
|
||||
case Q_doubleone:
|
||||
tok->quote = Q_double;
|
||||
*tok->wptr++ = *ptr;
|
||||
break;
|
||||
|
||||
case Q_one:
|
||||
tok->quote = Q_none;
|
||||
*tok->wptr++ = *ptr;
|
||||
break;
|
||||
|
||||
default:
|
||||
return (-1);
|
||||
}
|
||||
break;
|
||||
|
||||
default:
|
||||
tok->flags &= ~TOK_EAT;
|
||||
switch (tok->quote) {
|
||||
case Q_none:
|
||||
if (strchr(tok->ifs, *ptr) != NULL)
|
||||
tok_finish(tok);
|
||||
else
|
||||
*tok->wptr++ = *ptr;
|
||||
break;
|
||||
|
||||
case Q_single:
|
||||
case Q_double:
|
||||
*tok->wptr++ = *ptr;
|
||||
break;
|
||||
|
||||
|
||||
case Q_doubleone:
|
||||
*tok->wptr++ = '\\';
|
||||
tok->quote = Q_double;
|
||||
*tok->wptr++ = *ptr;
|
||||
break;
|
||||
|
||||
case Q_one:
|
||||
tok->quote = Q_none;
|
||||
*tok->wptr++ = *ptr;
|
||||
break;
|
||||
|
||||
default:
|
||||
return (-1);
|
||||
|
||||
}
|
||||
break;
|
||||
}
|
||||
|
||||
if (tok->wptr >= tok->wmax - 4) {
|
||||
size_t size = tok->wmax - tok->wspace + WINCR;
|
||||
char *s = (char *) tok_realloc(tok->wspace, size);
|
||||
if (s == NULL)
|
||||
return (-1);
|
||||
|
||||
if (s != tok->wspace) {
|
||||
int i;
|
||||
for (i = 0; i < tok->argc; i++) {
|
||||
tok->argv[i] =
|
||||
(tok->argv[i] - tok->wspace) + s;
|
||||
}
|
||||
tok->wptr = (tok->wptr - tok->wspace) + s;
|
||||
tok->wstart = (tok->wstart - tok->wspace) + s;
|
||||
tok->wspace = s;
|
||||
}
|
||||
tok->wmax = s + size;
|
||||
}
|
||||
if (tok->argc >= tok->amax - 4) {
|
||||
char **p;
|
||||
tok->amax += AINCR;
|
||||
p = (char **) tok_realloc(tok->argv,
|
||||
tok->amax * sizeof(char *));
|
||||
if (p == NULL)
|
||||
return (-1);
|
||||
tok->argv = p;
|
||||
}
|
||||
}
|
||||
}
|
@@ -1,54 +0,0 @@
|
||||
/* $NetBSD: tokenizer.h,v 1.5 2002/03/18 16:01:00 christos Exp $ */
|
||||
|
||||
/*-
|
||||
* Copyright (c) 1992, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* This code is derived from software contributed to Berkeley by
|
||||
* Christos Zoulas of Cornell University.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
* 3. All advertising materials mentioning features or use of this software
|
||||
* must display the following acknowledgement:
|
||||
* This product includes software developed by the University of
|
||||
* California, Berkeley and its contributors.
|
||||
* 4. Neither the name of the University nor the names of its contributors
|
||||
* may be used to endorse or promote products derived from this software
|
||||
* without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
|
||||
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
* ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
|
||||
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
|
||||
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* @(#)tokenizer.h 8.1 (Berkeley) 6/4/93
|
||||
*/
|
||||
|
||||
/*
|
||||
* tokenizer.h: Header file for tokenizer routines
|
||||
*/
|
||||
#ifndef _h_tokenizer
|
||||
#define _h_tokenizer
|
||||
|
||||
typedef struct tokenizer Tokenizer;
|
||||
|
||||
Tokenizer *tok_init(const char *);
|
||||
void tok_reset(Tokenizer *);
|
||||
void tok_end(Tokenizer *);
|
||||
int tok_line(Tokenizer *, const char *, int *, const char ***);
|
||||
|
||||
#endif /* _h_tokenizer */
|
1182
main/editline/tty.c
1182
main/editline/tty.c
File diff suppressed because it is too large
Load Diff
@@ -1,484 +0,0 @@
|
||||
/* $NetBSD: tty.h,v 1.9 2002/03/18 16:01:01 christos Exp $ */
|
||||
|
||||
/*-
|
||||
* Copyright (c) 1992, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* This code is derived from software contributed to Berkeley by
|
||||
* Christos Zoulas of Cornell University.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
* 3. All advertising materials mentioning features or use of this software
|
||||
* must display the following acknowledgement:
|
||||
* This product includes software developed by the University of
|
||||
* California, Berkeley and its contributors.
|
||||
* 4. Neither the name of the University nor the names of its contributors
|
||||
* may be used to endorse or promote products derived from this software
|
||||
* without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
|
||||
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
* ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
|
||||
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
|
||||
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* @(#)tty.h 8.1 (Berkeley) 6/4/93
|
||||
*/
|
||||
|
||||
/*
|
||||
* el.tty.h: Local terminal header
|
||||
*/
|
||||
#ifndef _h_el_tty
|
||||
#define _h_el_tty
|
||||
|
||||
#include "histedit.h"
|
||||
#include <termios.h>
|
||||
#include <unistd.h>
|
||||
|
||||
/* Define our own since everyone gets it wrong! */
|
||||
#define CONTROL(A) ((A) & 037)
|
||||
|
||||
/*
|
||||
* Aix compatible names
|
||||
*/
|
||||
# if defined(VWERSE) && !defined(VWERASE)
|
||||
# define VWERASE VWERSE
|
||||
# endif /* VWERSE && !VWERASE */
|
||||
|
||||
# if defined(VDISCRD) && !defined(VDISCARD)
|
||||
# define VDISCARD VDISCRD
|
||||
# endif /* VDISCRD && !VDISCARD */
|
||||
|
||||
# if defined(VFLUSHO) && !defined(VDISCARD)
|
||||
# define VDISCARD VFLUSHO
|
||||
# endif /* VFLUSHO && VDISCARD */
|
||||
|
||||
# if defined(VSTRT) && !defined(VSTART)
|
||||
# define VSTART VSTRT
|
||||
# endif /* VSTRT && ! VSTART */
|
||||
|
||||
# if defined(VSTAT) && !defined(VSTATUS)
|
||||
# define VSTATUS VSTAT
|
||||
# endif /* VSTAT && ! VSTATUS */
|
||||
|
||||
# ifndef ONLRET
|
||||
# define ONLRET 0
|
||||
# endif /* ONLRET */
|
||||
|
||||
# ifndef TAB3
|
||||
# ifdef OXTABS
|
||||
# define TAB3 OXTABS
|
||||
# else
|
||||
# define TAB3 0
|
||||
# endif /* OXTABS */
|
||||
# endif /* !TAB3 */
|
||||
|
||||
# if defined(OXTABS) && !defined(XTABS)
|
||||
# define XTABS OXTABS
|
||||
# endif /* OXTABS && !XTABS */
|
||||
|
||||
# ifndef ONLCR
|
||||
# define ONLCR 0
|
||||
# endif /* ONLCR */
|
||||
|
||||
# ifndef IEXTEN
|
||||
# define IEXTEN 0
|
||||
# endif /* IEXTEN */
|
||||
|
||||
# ifndef ECHOCTL
|
||||
# define ECHOCTL 0
|
||||
# endif /* ECHOCTL */
|
||||
|
||||
# ifndef PARENB
|
||||
# define PARENB 0
|
||||
# endif /* PARENB */
|
||||
|
||||
# ifndef EXTPROC
|
||||
# define EXTPROC 0
|
||||
# endif /* EXTPROC */
|
||||
|
||||
# ifndef FLUSHO
|
||||
# define FLUSHO 0
|
||||
# endif /* FLUSHO */
|
||||
|
||||
|
||||
# if defined(VDISABLE) && !defined(_POSIX_VDISABLE)
|
||||
# define _POSIX_VDISABLE VDISABLE
|
||||
# endif /* VDISABLE && ! _POSIX_VDISABLE */
|
||||
|
||||
/*
|
||||
* Work around ISC's definition of IEXTEN which is
|
||||
* XCASE!
|
||||
*/
|
||||
# ifdef ISC
|
||||
# if defined(IEXTEN) && defined(XCASE)
|
||||
# if IEXTEN == XCASE
|
||||
# undef IEXTEN
|
||||
# define IEXTEN 0
|
||||
# endif /* IEXTEN == XCASE */
|
||||
# endif /* IEXTEN && XCASE */
|
||||
# if defined(IEXTEN) && !defined(XCASE)
|
||||
# define XCASE IEXTEN
|
||||
# undef IEXTEN
|
||||
# define IEXTEN 0
|
||||
# endif /* IEXTEN && !XCASE */
|
||||
# endif /* ISC */
|
||||
|
||||
/*
|
||||
* Work around convex weirdness where turning off IEXTEN makes us
|
||||
* lose all postprocessing!
|
||||
*/
|
||||
#if defined(convex) || defined(__convex__)
|
||||
# if defined(IEXTEN) && IEXTEN != 0
|
||||
# undef IEXTEN
|
||||
# define IEXTEN 0
|
||||
# endif /* IEXTEN != 0 */
|
||||
#endif /* convex || __convex__ */
|
||||
|
||||
/*
|
||||
* So that we don't lose job control.
|
||||
*/
|
||||
#ifdef __SVR4
|
||||
# undef CSWTCH
|
||||
#endif
|
||||
|
||||
#ifndef _POSIX_VDISABLE
|
||||
# define _POSIX_VDISABLE ((unsigned char) -1)
|
||||
#endif /* _POSIX_VDISABLE */
|
||||
|
||||
#if !defined(CREPRINT) && defined(CRPRNT)
|
||||
# define CREPRINT CRPRNT
|
||||
#endif /* !CREPRINT && CRPRNT */
|
||||
#if !defined(CDISCARD) && defined(CFLUSH)
|
||||
# define CDISCARD CFLUSH
|
||||
#endif /* !CDISCARD && CFLUSH */
|
||||
|
||||
#ifndef CINTR
|
||||
# define CINTR CONTROL('c')
|
||||
#endif /* CINTR */
|
||||
#ifndef CQUIT
|
||||
# define CQUIT 034 /* ^\ */
|
||||
#endif /* CQUIT */
|
||||
#ifndef CERASE
|
||||
# define CERASE 0177 /* ^? */
|
||||
#endif /* CERASE */
|
||||
#ifndef CKILL
|
||||
# define CKILL CONTROL('u')
|
||||
#endif /* CKILL */
|
||||
#ifndef CEOF
|
||||
# define CEOF CONTROL('d')
|
||||
#endif /* CEOF */
|
||||
#ifndef CEOL
|
||||
# define CEOL _POSIX_VDISABLE
|
||||
#endif /* CEOL */
|
||||
#ifndef CEOL2
|
||||
# define CEOL2 _POSIX_VDISABLE
|
||||
#endif /* CEOL2 */
|
||||
#ifndef CSWTCH
|
||||
# define CSWTCH _POSIX_VDISABLE
|
||||
#endif /* CSWTCH */
|
||||
#ifndef CDSWTCH
|
||||
# define CDSWTCH _POSIX_VDISABLE
|
||||
#endif /* CDSWTCH */
|
||||
#ifndef CERASE2
|
||||
# define CERASE2 _POSIX_VDISABLE
|
||||
#endif /* CERASE2 */
|
||||
#ifndef CSTART
|
||||
# define CSTART CONTROL('q')
|
||||
#endif /* CSTART */
|
||||
#ifndef CSTOP
|
||||
# define CSTOP CONTROL('s')
|
||||
#endif /* CSTOP */
|
||||
#ifndef CSUSP
|
||||
# define CSUSP CONTROL('z')
|
||||
#endif /* CSUSP */
|
||||
#ifndef CDSUSP
|
||||
# define CDSUSP CONTROL('y')
|
||||
#endif /* CDSUSP */
|
||||
|
||||
#ifdef hpux
|
||||
|
||||
# ifndef CREPRINT
|
||||
# define CREPRINT _POSIX_VDISABLE
|
||||
# endif /* CREPRINT */
|
||||
# ifndef CDISCARD
|
||||
# define CDISCARD _POSIX_VDISABLE
|
||||
# endif /* CDISCARD */
|
||||
# ifndef CLNEXT
|
||||
# define CLNEXT _POSIX_VDISABLE
|
||||
# endif /* CLNEXT */
|
||||
# ifndef CWERASE
|
||||
# define CWERASE _POSIX_VDISABLE
|
||||
# endif /* CWERASE */
|
||||
|
||||
#else /* !hpux */
|
||||
|
||||
# ifndef CREPRINT
|
||||
# define CREPRINT CONTROL('r')
|
||||
# endif /* CREPRINT */
|
||||
# ifndef CDISCARD
|
||||
# define CDISCARD CONTROL('o')
|
||||
# endif /* CDISCARD */
|
||||
# ifndef CLNEXT
|
||||
# define CLNEXT CONTROL('v')
|
||||
# endif /* CLNEXT */
|
||||
# ifndef CWERASE
|
||||
# define CWERASE CONTROL('w')
|
||||
# endif /* CWERASE */
|
||||
|
||||
#endif /* hpux */
|
||||
|
||||
#ifndef CSTATUS
|
||||
# define CSTATUS CONTROL('t')
|
||||
#endif /* CSTATUS */
|
||||
#ifndef CPAGE
|
||||
# define CPAGE ' '
|
||||
#endif /* CPAGE */
|
||||
#ifndef CPGOFF
|
||||
# define CPGOFF CONTROL('m')
|
||||
#endif /* CPGOFF */
|
||||
#ifndef CKILL2
|
||||
# define CKILL2 _POSIX_VDISABLE
|
||||
#endif /* CKILL2 */
|
||||
#ifndef CBRK
|
||||
# ifndef masscomp
|
||||
# define CBRK 0377
|
||||
# else
|
||||
# define CBRK '\0'
|
||||
# endif /* masscomp */
|
||||
#endif /* CBRK */
|
||||
#ifndef CMIN
|
||||
# define CMIN CEOF
|
||||
#endif /* CMIN */
|
||||
#ifndef CTIME
|
||||
# define CTIME CEOL
|
||||
#endif /* CTIME */
|
||||
|
||||
/*
|
||||
* Fix for sun inconsistency. On termio VSUSP and the rest of the
|
||||
* ttychars > NCC are defined. So we undefine them.
|
||||
*/
|
||||
#if defined(TERMIO) || defined(POSIX)
|
||||
# if defined(POSIX) && defined(NCCS)
|
||||
# define NUMCC NCCS
|
||||
# else
|
||||
# ifdef NCC
|
||||
# define NUMCC NCC
|
||||
# endif /* NCC */
|
||||
# endif /* POSIX && NCCS */
|
||||
# ifdef NUMCC
|
||||
# ifdef VINTR
|
||||
# if NUMCC <= VINTR
|
||||
# undef VINTR
|
||||
# endif /* NUMCC <= VINTR */
|
||||
# endif /* VINTR */
|
||||
# ifdef VQUIT
|
||||
# if NUMCC <= VQUIT
|
||||
# undef VQUIT
|
||||
# endif /* NUMCC <= VQUIT */
|
||||
# endif /* VQUIT */
|
||||
# ifdef VERASE
|
||||
# if NUMCC <= VERASE
|
||||
# undef VERASE
|
||||
# endif /* NUMCC <= VERASE */
|
||||
# endif /* VERASE */
|
||||
# ifdef VKILL
|
||||
# if NUMCC <= VKILL
|
||||
# undef VKILL
|
||||
# endif /* NUMCC <= VKILL */
|
||||
# endif /* VKILL */
|
||||
# ifdef VEOF
|
||||
# if NUMCC <= VEOF
|
||||
# undef VEOF
|
||||
# endif /* NUMCC <= VEOF */
|
||||
# endif /* VEOF */
|
||||
# ifdef VEOL
|
||||
# if NUMCC <= VEOL
|
||||
# undef VEOL
|
||||
# endif /* NUMCC <= VEOL */
|
||||
# endif /* VEOL */
|
||||
# ifdef VEOL2
|
||||
# if NUMCC <= VEOL2
|
||||
# undef VEOL2
|
||||
# endif /* NUMCC <= VEOL2 */
|
||||
# endif /* VEOL2 */
|
||||
# ifdef VSWTCH
|
||||
# if NUMCC <= VSWTCH
|
||||
# undef VSWTCH
|
||||
# endif /* NUMCC <= VSWTCH */
|
||||
# endif /* VSWTCH */
|
||||
# ifdef VDSWTCH
|
||||
# if NUMCC <= VDSWTCH
|
||||
# undef VDSWTCH
|
||||
# endif /* NUMCC <= VDSWTCH */
|
||||
# endif /* VDSWTCH */
|
||||
# ifdef VERASE2
|
||||
# if NUMCC <= VERASE2
|
||||
# undef VERASE2
|
||||
# endif /* NUMCC <= VERASE2 */
|
||||
# endif /* VERASE2 */
|
||||
# ifdef VSTART
|
||||
# if NUMCC <= VSTART
|
||||
# undef VSTART
|
||||
# endif /* NUMCC <= VSTART */
|
||||
# endif /* VSTART */
|
||||
# ifdef VSTOP
|
||||
# if NUMCC <= VSTOP
|
||||
# undef VSTOP
|
||||
# endif /* NUMCC <= VSTOP */
|
||||
# endif /* VSTOP */
|
||||
# ifdef VWERASE
|
||||
# if NUMCC <= VWERASE
|
||||
# undef VWERASE
|
||||
# endif /* NUMCC <= VWERASE */
|
||||
# endif /* VWERASE */
|
||||
# ifdef VSUSP
|
||||
# if NUMCC <= VSUSP
|
||||
# undef VSUSP
|
||||
# endif /* NUMCC <= VSUSP */
|
||||
# endif /* VSUSP */
|
||||
# ifdef VDSUSP
|
||||
# if NUMCC <= VDSUSP
|
||||
# undef VDSUSP
|
||||
# endif /* NUMCC <= VDSUSP */
|
||||
# endif /* VDSUSP */
|
||||
# ifdef VREPRINT
|
||||
# if NUMCC <= VREPRINT
|
||||
# undef VREPRINT
|
||||
# endif /* NUMCC <= VREPRINT */
|
||||
# endif /* VREPRINT */
|
||||
# ifdef VDISCARD
|
||||
# if NUMCC <= VDISCARD
|
||||
# undef VDISCARD
|
||||
# endif /* NUMCC <= VDISCARD */
|
||||
# endif /* VDISCARD */
|
||||
# ifdef VLNEXT
|
||||
# if NUMCC <= VLNEXT
|
||||
# undef VLNEXT
|
||||
# endif /* NUMCC <= VLNEXT */
|
||||
# endif /* VLNEXT */
|
||||
# ifdef VSTATUS
|
||||
# if NUMCC <= VSTATUS
|
||||
# undef VSTATUS
|
||||
# endif /* NUMCC <= VSTATUS */
|
||||
# endif /* VSTATUS */
|
||||
# ifdef VPAGE
|
||||
# if NUMCC <= VPAGE
|
||||
# undef VPAGE
|
||||
# endif /* NUMCC <= VPAGE */
|
||||
# endif /* VPAGE */
|
||||
# ifdef VPGOFF
|
||||
# if NUMCC <= VPGOFF
|
||||
# undef VPGOFF
|
||||
# endif /* NUMCC <= VPGOFF */
|
||||
# endif /* VPGOFF */
|
||||
# ifdef VKILL2
|
||||
# if NUMCC <= VKILL2
|
||||
# undef VKILL2
|
||||
# endif /* NUMCC <= VKILL2 */
|
||||
# endif /* VKILL2 */
|
||||
# ifdef VBRK
|
||||
# if NUMCC <= VBRK
|
||||
# undef VBRK
|
||||
# endif /* NUMCC <= VBRK */
|
||||
# endif /* VBRK */
|
||||
# ifdef VMIN
|
||||
# if NUMCC <= VMIN
|
||||
# undef VMIN
|
||||
# endif /* NUMCC <= VMIN */
|
||||
# endif /* VMIN */
|
||||
# ifdef VTIME
|
||||
# if NUMCC <= VTIME
|
||||
# undef VTIME
|
||||
# endif /* NUMCC <= VTIME */
|
||||
# endif /* VTIME */
|
||||
# endif /* NUMCC */
|
||||
#endif /* !POSIX */
|
||||
|
||||
#define C_INTR 0
|
||||
#define C_QUIT 1
|
||||
#define C_ERASE 2
|
||||
#define C_KILL 3
|
||||
#define C_EOF 4
|
||||
#define C_EOL 5
|
||||
#define C_EOL2 6
|
||||
#define C_SWTCH 7
|
||||
#define C_DSWTCH 8
|
||||
#define C_ERASE2 9
|
||||
#define C_START 10
|
||||
#define C_STOP 11
|
||||
#define C_WERASE 12
|
||||
#define C_SUSP 13
|
||||
#define C_DSUSP 14
|
||||
#define C_REPRINT 15
|
||||
#define C_DISCARD 16
|
||||
#define C_LNEXT 17
|
||||
#define C_STATUS 18
|
||||
#define C_PAGE 19
|
||||
#define C_PGOFF 20
|
||||
#define C_KILL2 21
|
||||
#define C_BRK 22
|
||||
#define C_MIN 23
|
||||
#define C_TIME 24
|
||||
#define C_NCC 25
|
||||
#define C_SH(A) (1 << (A))
|
||||
|
||||
/*
|
||||
* Terminal dependend data structures
|
||||
*/
|
||||
#define EX_IO 0 /* while we are executing */
|
||||
#define ED_IO 1 /* while we are editing */
|
||||
#define TS_IO 2 /* new mode from terminal */
|
||||
#define QU_IO 2 /* used only for quoted chars */
|
||||
#define NN_IO 3 /* The number of entries */
|
||||
|
||||
#define MD_INP 0
|
||||
#define MD_OUT 1
|
||||
#define MD_CTL 2
|
||||
#define MD_LIN 3
|
||||
#define MD_CHAR 4
|
||||
#define MD_NN 5
|
||||
|
||||
typedef struct {
|
||||
const char *t_name;
|
||||
u_int t_setmask;
|
||||
u_int t_clrmask;
|
||||
} ttyperm_t[NN_IO][MD_NN];
|
||||
|
||||
typedef unsigned char ttychar_t[NN_IO][C_NCC];
|
||||
|
||||
protected int tty_init(EditLine *);
|
||||
protected void tty_end(EditLine *);
|
||||
protected int tty_stty(EditLine *, int, const char **);
|
||||
protected int tty_rawmode(EditLine *);
|
||||
protected int tty_cookedmode(EditLine *);
|
||||
protected int tty_quotemode(EditLine *);
|
||||
protected int tty_noquotemode(EditLine *);
|
||||
protected void tty_bind_char(EditLine *, int);
|
||||
|
||||
typedef struct {
|
||||
ttyperm_t t_t;
|
||||
ttychar_t t_c;
|
||||
struct termios t_ex, t_ed, t_ts;
|
||||
int t_tabs;
|
||||
int t_eight;
|
||||
speed_t t_speed;
|
||||
int t_mode;
|
||||
unsigned char t_vdisable;
|
||||
} el_tty_t;
|
||||
|
||||
|
||||
#endif /* _h_el_tty */
|
@@ -1,941 +0,0 @@
|
||||
/* $NetBSD: vi.c,v 1.9 2002/03/18 16:01:01 christos Exp $ */
|
||||
|
||||
/*-
|
||||
* Copyright (c) 1992, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* This code is derived from software contributed to Berkeley by
|
||||
* Christos Zoulas of Cornell University.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
* 3. All advertising materials mentioning features or use of this software
|
||||
* must display the following acknowledgement:
|
||||
* This product includes software developed by the University of
|
||||
* California, Berkeley and its contributors.
|
||||
* 4. Neither the name of the University nor the names of its contributors
|
||||
* may be used to endorse or promote products derived from this software
|
||||
* without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
|
||||
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
* ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
|
||||
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
|
||||
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*/
|
||||
|
||||
#include "config.h"
|
||||
#if !defined(lint) && !defined(SCCSID)
|
||||
#if 0
|
||||
static char sccsid[] = "@(#)vi.c 8.1 (Berkeley) 6/4/93";
|
||||
#else
|
||||
__RCSID("$NetBSD: vi.c,v 1.9 2002/03/18 16:01:01 christos Exp $");
|
||||
#endif
|
||||
#endif /* not lint && not SCCSID */
|
||||
|
||||
/*
|
||||
* vi.c: Vi mode commands.
|
||||
*/
|
||||
#include "el.h"
|
||||
|
||||
private el_action_t cv_action(EditLine *, int);
|
||||
private el_action_t cv_paste(EditLine *, int);
|
||||
|
||||
/* cv_action():
|
||||
* Handle vi actions.
|
||||
*/
|
||||
private el_action_t
|
||||
cv_action(EditLine *el, int c)
|
||||
{
|
||||
char *cp, *kp;
|
||||
|
||||
if (el->el_chared.c_vcmd.action & DELETE) {
|
||||
el->el_chared.c_vcmd.action = NOP;
|
||||
el->el_chared.c_vcmd.pos = 0;
|
||||
|
||||
el->el_chared.c_undo.isize = 0;
|
||||
el->el_chared.c_undo.dsize = 0;
|
||||
kp = el->el_chared.c_undo.buf;
|
||||
for (cp = el->el_line.buffer; cp < el->el_line.lastchar; cp++) {
|
||||
*kp++ = *cp;
|
||||
el->el_chared.c_undo.dsize++;
|
||||
}
|
||||
|
||||
el->el_chared.c_undo.action = INSERT;
|
||||
el->el_chared.c_undo.ptr = el->el_line.buffer;
|
||||
el->el_line.lastchar = el->el_line.buffer;
|
||||
el->el_line.cursor = el->el_line.buffer;
|
||||
if (c & INSERT)
|
||||
el->el_map.current = el->el_map.key;
|
||||
|
||||
return (CC_REFRESH);
|
||||
}
|
||||
el->el_chared.c_vcmd.pos = el->el_line.cursor;
|
||||
el->el_chared.c_vcmd.action = c;
|
||||
return (CC_ARGHACK);
|
||||
|
||||
#ifdef notdef
|
||||
/*
|
||||
* I don't think that this is needed. But we keep it for now
|
||||
*/
|
||||
else
|
||||
if (el_chared.c_vcmd.action == NOP) {
|
||||
el->el_chared.c_vcmd.pos = el->el_line.cursor;
|
||||
el->el_chared.c_vcmd.action = c;
|
||||
return (CC_ARGHACK);
|
||||
} else {
|
||||
el->el_chared.c_vcmd.action = 0;
|
||||
el->el_chared.c_vcmd.pos = 0;
|
||||
return (CC_ERROR);
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
|
||||
/* cv_paste():
|
||||
* Paste previous deletion before or after the cursor
|
||||
*/
|
||||
private el_action_t
|
||||
cv_paste(EditLine *el, int c)
|
||||
{
|
||||
char *ptr;
|
||||
c_undo_t *un = &el->el_chared.c_undo;
|
||||
|
||||
#ifdef DEBUG_PASTE
|
||||
(void) fprintf(el->el_errfile, "Paste: %x \"%s\" +%d -%d\n",
|
||||
un->action, un->buf, un->isize, un->dsize);
|
||||
#endif
|
||||
if (un->isize == 0)
|
||||
return (CC_ERROR);
|
||||
|
||||
if (!c && el->el_line.cursor < el->el_line.lastchar)
|
||||
el->el_line.cursor++;
|
||||
ptr = el->el_line.cursor;
|
||||
|
||||
c_insert(el, (int) un->isize);
|
||||
if (el->el_line.cursor + un->isize > el->el_line.lastchar)
|
||||
return (CC_ERROR);
|
||||
(void) memcpy(ptr, un->buf, un->isize);
|
||||
return (CC_REFRESH);
|
||||
}
|
||||
|
||||
|
||||
/* vi_paste_next():
|
||||
* Vi paste previous deletion to the right of the cursor
|
||||
* [p]
|
||||
*/
|
||||
protected el_action_t
|
||||
/*ARGSUSED*/
|
||||
vi_paste_next(EditLine *el, int c)
|
||||
{
|
||||
|
||||
return (cv_paste(el, 0));
|
||||
}
|
||||
|
||||
|
||||
/* vi_paste_prev():
|
||||
* Vi paste previous deletion to the left of the cursor
|
||||
* [P]
|
||||
*/
|
||||
protected el_action_t
|
||||
/*ARGSUSED*/
|
||||
vi_paste_prev(EditLine *el, int c)
|
||||
{
|
||||
|
||||
return (cv_paste(el, 1));
|
||||
}
|
||||
|
||||
|
||||
/* vi_prev_space_word():
|
||||
* Vi move to the previous space delimited word
|
||||
* [B]
|
||||
*/
|
||||
protected el_action_t
|
||||
/*ARGSUSED*/
|
||||
vi_prev_space_word(EditLine *el, int c)
|
||||
{
|
||||
|
||||
if (el->el_line.cursor == el->el_line.buffer)
|
||||
return (CC_ERROR);
|
||||
|
||||
el->el_line.cursor = cv_prev_word(el, el->el_line.cursor,
|
||||
el->el_line.buffer,
|
||||
el->el_state.argument,
|
||||
cv__isword);
|
||||
|
||||
if (el->el_chared.c_vcmd.action & DELETE) {
|
||||
cv_delfini(el);
|
||||
return (CC_REFRESH);
|
||||
}
|
||||
return (CC_CURSOR);
|
||||
}
|
||||
|
||||
|
||||
/* vi_prev_word():
|
||||
* Vi move to the previous word
|
||||
* [B]
|
||||
*/
|
||||
protected el_action_t
|
||||
/*ARGSUSED*/
|
||||
vi_prev_word(EditLine *el, int c)
|
||||
{
|
||||
|
||||
if (el->el_line.cursor == el->el_line.buffer)
|
||||
return (CC_ERROR);
|
||||
|
||||
el->el_line.cursor = cv_prev_word(el, el->el_line.cursor,
|
||||
el->el_line.buffer,
|
||||
el->el_state.argument,
|
||||
ce__isword);
|
||||
|
||||
if (el->el_chared.c_vcmd.action & DELETE) {
|
||||
cv_delfini(el);
|
||||
return (CC_REFRESH);
|
||||
}
|
||||
return (CC_CURSOR);
|
||||
}
|
||||
|
||||
|
||||
/* vi_next_space_word():
|
||||
* Vi move to the next space delimited word
|
||||
* [W]
|
||||
*/
|
||||
protected el_action_t
|
||||
/*ARGSUSED*/
|
||||
vi_next_space_word(EditLine *el, int c)
|
||||
{
|
||||
|
||||
if (el->el_line.cursor == el->el_line.lastchar)
|
||||
return (CC_ERROR);
|
||||
|
||||
el->el_line.cursor = cv_next_word(el, el->el_line.cursor,
|
||||
el->el_line.lastchar,
|
||||
el->el_state.argument,
|
||||
cv__isword);
|
||||
|
||||
if (el->el_map.type == MAP_VI)
|
||||
if (el->el_chared.c_vcmd.action & DELETE) {
|
||||
cv_delfini(el);
|
||||
return (CC_REFRESH);
|
||||
}
|
||||
return (CC_CURSOR);
|
||||
}
|
||||
|
||||
|
||||
/* vi_next_word():
|
||||
* Vi move to the next word
|
||||
* [w]
|
||||
*/
|
||||
protected el_action_t
|
||||
/*ARGSUSED*/
|
||||
vi_next_word(EditLine *el, int c)
|
||||
{
|
||||
|
||||
if (el->el_line.cursor == el->el_line.lastchar)
|
||||
return (CC_ERROR);
|
||||
|
||||
el->el_line.cursor = cv_next_word(el, el->el_line.cursor,
|
||||
el->el_line.lastchar,
|
||||
el->el_state.argument,
|
||||
ce__isword);
|
||||
|
||||
if (el->el_map.type == MAP_VI)
|
||||
if (el->el_chared.c_vcmd.action & DELETE) {
|
||||
cv_delfini(el);
|
||||
return (CC_REFRESH);
|
||||
}
|
||||
return (CC_CURSOR);
|
||||
}
|
||||
|
||||
|
||||
/* vi_change_case():
|
||||
* Vi change case of character under the cursor and advance one character
|
||||
* [~]
|
||||
*/
|
||||
protected el_action_t
|
||||
vi_change_case(EditLine *el, int c)
|
||||
{
|
||||
|
||||
if (el->el_line.cursor < el->el_line.lastchar) {
|
||||
c = *el->el_line.cursor;
|
||||
if (isupper(c))
|
||||
*el->el_line.cursor++ = tolower(c);
|
||||
else if (islower(c))
|
||||
*el->el_line.cursor++ = toupper(c);
|
||||
else
|
||||
el->el_line.cursor++;
|
||||
re_fastaddc(el);
|
||||
return (CC_NORM);
|
||||
}
|
||||
return (CC_ERROR);
|
||||
}
|
||||
|
||||
|
||||
/* vi_change_meta():
|
||||
* Vi change prefix command
|
||||
* [c]
|
||||
*/
|
||||
protected el_action_t
|
||||
/*ARGSUSED*/
|
||||
vi_change_meta(EditLine *el, int c)
|
||||
{
|
||||
|
||||
/*
|
||||
* Delete with insert == change: first we delete and then we leave in
|
||||
* insert mode.
|
||||
*/
|
||||
return (cv_action(el, DELETE | INSERT));
|
||||
}
|
||||
|
||||
|
||||
/* vi_insert_at_bol():
|
||||
* Vi enter insert mode at the beginning of line
|
||||
* [I]
|
||||
*/
|
||||
protected el_action_t
|
||||
/*ARGSUSED*/
|
||||
vi_insert_at_bol(EditLine *el, int c)
|
||||
{
|
||||
|
||||
el->el_line.cursor = el->el_line.buffer;
|
||||
el->el_chared.c_vcmd.ins = el->el_line.cursor;
|
||||
|
||||
el->el_chared.c_undo.ptr = el->el_line.cursor;
|
||||
el->el_chared.c_undo.action = DELETE;
|
||||
|
||||
el->el_map.current = el->el_map.key;
|
||||
return (CC_CURSOR);
|
||||
}
|
||||
|
||||
|
||||
/* vi_replace_char():
|
||||
* Vi replace character under the cursor with the next character typed
|
||||
* [r]
|
||||
*/
|
||||
protected el_action_t
|
||||
/*ARGSUSED*/
|
||||
vi_replace_char(EditLine *el, int c)
|
||||
{
|
||||
|
||||
el->el_map.current = el->el_map.key;
|
||||
el->el_state.inputmode = MODE_REPLACE_1;
|
||||
el->el_chared.c_undo.action = CHANGE;
|
||||
el->el_chared.c_undo.ptr = el->el_line.cursor;
|
||||
el->el_chared.c_undo.isize = 0;
|
||||
el->el_chared.c_undo.dsize = 0;
|
||||
return (CC_NORM);
|
||||
}
|
||||
|
||||
|
||||
/* vi_replace_mode():
|
||||
* Vi enter replace mode
|
||||
* [R]
|
||||
*/
|
||||
protected el_action_t
|
||||
/*ARGSUSED*/
|
||||
vi_replace_mode(EditLine *el, int c)
|
||||
{
|
||||
|
||||
el->el_map.current = el->el_map.key;
|
||||
el->el_state.inputmode = MODE_REPLACE;
|
||||
el->el_chared.c_undo.action = CHANGE;
|
||||
el->el_chared.c_undo.ptr = el->el_line.cursor;
|
||||
el->el_chared.c_undo.isize = 0;
|
||||
el->el_chared.c_undo.dsize = 0;
|
||||
return (CC_NORM);
|
||||
}
|
||||
|
||||
|
||||
/* vi_substitute_char():
|
||||
* Vi replace character under the cursor and enter insert mode
|
||||
* [r]
|
||||
*/
|
||||
protected el_action_t
|
||||
/*ARGSUSED*/
|
||||
vi_substitute_char(EditLine *el, int c)
|
||||
{
|
||||
|
||||
c_delafter(el, el->el_state.argument);
|
||||
el->el_map.current = el->el_map.key;
|
||||
return (CC_REFRESH);
|
||||
}
|
||||
|
||||
|
||||
/* vi_substitute_line():
|
||||
* Vi substitute entire line
|
||||
* [S]
|
||||
*/
|
||||
protected el_action_t
|
||||
/*ARGSUSED*/
|
||||
vi_substitute_line(EditLine *el, int c)
|
||||
{
|
||||
|
||||
(void) em_kill_line(el, 0);
|
||||
el->el_map.current = el->el_map.key;
|
||||
return (CC_REFRESH);
|
||||
}
|
||||
|
||||
|
||||
/* vi_change_to_eol():
|
||||
* Vi change to end of line
|
||||
* [C]
|
||||
*/
|
||||
protected el_action_t
|
||||
/*ARGSUSED*/
|
||||
vi_change_to_eol(EditLine *el, int c)
|
||||
{
|
||||
|
||||
(void) ed_kill_line(el, 0);
|
||||
el->el_map.current = el->el_map.key;
|
||||
return (CC_REFRESH);
|
||||
}
|
||||
|
||||
|
||||
/* vi_insert():
|
||||
* Vi enter insert mode
|
||||
* [i]
|
||||
*/
|
||||
protected el_action_t
|
||||
/*ARGSUSED*/
|
||||
vi_insert(EditLine *el, int c)
|
||||
{
|
||||
|
||||
el->el_map.current = el->el_map.key;
|
||||
|
||||
el->el_chared.c_vcmd.ins = el->el_line.cursor;
|
||||
el->el_chared.c_undo.ptr = el->el_line.cursor;
|
||||
el->el_chared.c_undo.action = DELETE;
|
||||
|
||||
return (CC_NORM);
|
||||
}
|
||||
|
||||
|
||||
/* vi_add():
|
||||
* Vi enter insert mode after the cursor
|
||||
* [a]
|
||||
*/
|
||||
protected el_action_t
|
||||
/*ARGSUSED*/
|
||||
vi_add(EditLine *el, int c)
|
||||
{
|
||||
int ret;
|
||||
|
||||
el->el_map.current = el->el_map.key;
|
||||
if (el->el_line.cursor < el->el_line.lastchar) {
|
||||
el->el_line.cursor++;
|
||||
if (el->el_line.cursor > el->el_line.lastchar)
|
||||
el->el_line.cursor = el->el_line.lastchar;
|
||||
ret = CC_CURSOR;
|
||||
} else
|
||||
ret = CC_NORM;
|
||||
|
||||
el->el_chared.c_vcmd.ins = el->el_line.cursor;
|
||||
el->el_chared.c_undo.ptr = el->el_line.cursor;
|
||||
el->el_chared.c_undo.action = DELETE;
|
||||
|
||||
return (ret);
|
||||
}
|
||||
|
||||
|
||||
/* vi_add_at_eol():
|
||||
* Vi enter insert mode at end of line
|
||||
* [A]
|
||||
*/
|
||||
protected el_action_t
|
||||
/*ARGSUSED*/
|
||||
vi_add_at_eol(EditLine *el, int c)
|
||||
{
|
||||
|
||||
el->el_map.current = el->el_map.key;
|
||||
el->el_line.cursor = el->el_line.lastchar;
|
||||
|
||||
/* Mark where insertion begins */
|
||||
el->el_chared.c_vcmd.ins = el->el_line.lastchar;
|
||||
el->el_chared.c_undo.ptr = el->el_line.lastchar;
|
||||
el->el_chared.c_undo.action = DELETE;
|
||||
return (CC_CURSOR);
|
||||
}
|
||||
|
||||
|
||||
/* vi_delete_meta():
|
||||
* Vi delete prefix command
|
||||
* [d]
|
||||
*/
|
||||
protected el_action_t
|
||||
/*ARGSUSED*/
|
||||
vi_delete_meta(EditLine *el, int c)
|
||||
{
|
||||
|
||||
return (cv_action(el, DELETE));
|
||||
}
|
||||
|
||||
|
||||
/* vi_end_word():
|
||||
* Vi move to the end of the current space delimited word
|
||||
* [E]
|
||||
*/
|
||||
protected el_action_t
|
||||
/*ARGSUSED*/
|
||||
vi_end_word(EditLine *el, int c)
|
||||
{
|
||||
|
||||
if (el->el_line.cursor == el->el_line.lastchar)
|
||||
return (CC_ERROR);
|
||||
|
||||
el->el_line.cursor = cv__endword(el->el_line.cursor,
|
||||
el->el_line.lastchar, el->el_state.argument);
|
||||
|
||||
if (el->el_chared.c_vcmd.action & DELETE) {
|
||||
el->el_line.cursor++;
|
||||
cv_delfini(el);
|
||||
return (CC_REFRESH);
|
||||
}
|
||||
return (CC_CURSOR);
|
||||
}
|
||||
|
||||
|
||||
/* vi_to_end_word():
|
||||
* Vi move to the end of the current word
|
||||
* [e]
|
||||
*/
|
||||
protected el_action_t
|
||||
/*ARGSUSED*/
|
||||
vi_to_end_word(EditLine *el, int c)
|
||||
{
|
||||
|
||||
if (el->el_line.cursor == el->el_line.lastchar)
|
||||
return (CC_ERROR);
|
||||
|
||||
el->el_line.cursor = cv__endword(el->el_line.cursor,
|
||||
el->el_line.lastchar, el->el_state.argument);
|
||||
|
||||
if (el->el_chared.c_vcmd.action & DELETE) {
|
||||
el->el_line.cursor++;
|
||||
cv_delfini(el);
|
||||
return (CC_REFRESH);
|
||||
}
|
||||
return (CC_CURSOR);
|
||||
}
|
||||
|
||||
|
||||
/* vi_undo():
|
||||
* Vi undo last change
|
||||
* [u]
|
||||
*/
|
||||
protected el_action_t
|
||||
/*ARGSUSED*/
|
||||
vi_undo(EditLine *el, int c)
|
||||
{
|
||||
char *cp, *kp;
|
||||
char temp;
|
||||
int i, size;
|
||||
c_undo_t *un = &el->el_chared.c_undo;
|
||||
|
||||
#ifdef DEBUG_UNDO
|
||||
(void) fprintf(el->el_errfile, "Undo: %x \"%s\" +%d -%d\n",
|
||||
un->action, un->buf, un->isize, un->dsize);
|
||||
#endif
|
||||
switch (un->action) {
|
||||
case DELETE:
|
||||
if (un->dsize == 0)
|
||||
return (CC_NORM);
|
||||
|
||||
(void) memcpy(un->buf, un->ptr, un->dsize);
|
||||
for (cp = un->ptr; cp <= el->el_line.lastchar; cp++)
|
||||
*cp = cp[un->dsize];
|
||||
|
||||
el->el_line.lastchar -= un->dsize;
|
||||
el->el_line.cursor = un->ptr;
|
||||
|
||||
un->action = INSERT;
|
||||
un->isize = un->dsize;
|
||||
un->dsize = 0;
|
||||
break;
|
||||
|
||||
case DELETE | INSERT:
|
||||
size = un->isize - un->dsize;
|
||||
if (size > 0)
|
||||
i = un->dsize;
|
||||
else
|
||||
i = un->isize;
|
||||
cp = un->ptr;
|
||||
kp = un->buf;
|
||||
while (i-- > 0) {
|
||||
temp = *kp;
|
||||
*kp++ = *cp;
|
||||
*cp++ = temp;
|
||||
}
|
||||
if (size > 0) {
|
||||
el->el_line.cursor = cp;
|
||||
c_insert(el, size);
|
||||
while (size-- > 0 && cp < el->el_line.lastchar) {
|
||||
temp = *kp;
|
||||
*kp++ = *cp;
|
||||
*cp++ = temp;
|
||||
}
|
||||
} else if (size < 0) {
|
||||
size = -size;
|
||||
for (; cp <= el->el_line.lastchar; cp++) {
|
||||
*kp++ = *cp;
|
||||
*cp = cp[size];
|
||||
}
|
||||
el->el_line.lastchar -= size;
|
||||
}
|
||||
el->el_line.cursor = un->ptr;
|
||||
i = un->dsize;
|
||||
un->dsize = un->isize;
|
||||
un->isize = i;
|
||||
break;
|
||||
|
||||
case INSERT:
|
||||
if (un->isize == 0)
|
||||
return (CC_NORM);
|
||||
|
||||
el->el_line.cursor = un->ptr;
|
||||
c_insert(el, (int) un->isize);
|
||||
(void) memcpy(un->ptr, un->buf, un->isize);
|
||||
un->action = DELETE;
|
||||
un->dsize = un->isize;
|
||||
un->isize = 0;
|
||||
break;
|
||||
|
||||
case CHANGE:
|
||||
if (un->isize == 0)
|
||||
return (CC_NORM);
|
||||
|
||||
el->el_line.cursor = un->ptr;
|
||||
size = (int) (el->el_line.cursor - el->el_line.lastchar);
|
||||
if (size < un->isize)
|
||||
size = un->isize;
|
||||
cp = un->ptr;
|
||||
kp = un->buf;
|
||||
for (i = 0; i < size; i++) {
|
||||
temp = *kp;
|
||||
*kp++ = *cp;
|
||||
*cp++ = temp;
|
||||
}
|
||||
un->dsize = 0;
|
||||
break;
|
||||
|
||||
default:
|
||||
return (CC_ERROR);
|
||||
}
|
||||
|
||||
return (CC_REFRESH);
|
||||
}
|
||||
|
||||
|
||||
/* vi_command_mode():
|
||||
* Vi enter command mode (use alternative key bindings)
|
||||
* [<ESC>]
|
||||
*/
|
||||
protected el_action_t
|
||||
/*ARGSUSED*/
|
||||
vi_command_mode(EditLine *el, int c)
|
||||
{
|
||||
int size;
|
||||
|
||||
/* [Esc] cancels pending action */
|
||||
el->el_chared.c_vcmd.ins = 0;
|
||||
el->el_chared.c_vcmd.action = NOP;
|
||||
el->el_chared.c_vcmd.pos = 0;
|
||||
|
||||
el->el_state.doingarg = 0;
|
||||
size = el->el_chared.c_undo.ptr - el->el_line.cursor;
|
||||
if (size < 0)
|
||||
size = -size;
|
||||
if (el->el_chared.c_undo.action == (INSERT | DELETE) ||
|
||||
el->el_chared.c_undo.action == DELETE)
|
||||
el->el_chared.c_undo.dsize = size;
|
||||
else
|
||||
el->el_chared.c_undo.isize = size;
|
||||
|
||||
el->el_state.inputmode = MODE_INSERT;
|
||||
el->el_map.current = el->el_map.alt;
|
||||
#ifdef VI_MOVE
|
||||
if (el->el_line.cursor > el->el_line.buffer)
|
||||
el->el_line.cursor--;
|
||||
#endif
|
||||
return (CC_CURSOR);
|
||||
}
|
||||
|
||||
|
||||
/* vi_zero():
|
||||
* Vi move to the beginning of line
|
||||
* [0]
|
||||
*/
|
||||
protected el_action_t
|
||||
vi_zero(EditLine *el, int c)
|
||||
{
|
||||
|
||||
if (el->el_state.doingarg) {
|
||||
if (el->el_state.argument > 1000000)
|
||||
return (CC_ERROR);
|
||||
el->el_state.argument =
|
||||
(el->el_state.argument * 10) + (c - '0');
|
||||
return (CC_ARGHACK);
|
||||
} else {
|
||||
el->el_line.cursor = el->el_line.buffer;
|
||||
if (el->el_chared.c_vcmd.action & DELETE) {
|
||||
cv_delfini(el);
|
||||
return (CC_REFRESH);
|
||||
}
|
||||
return (CC_CURSOR);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/* vi_delete_prev_char():
|
||||
* Vi move to previous character (backspace)
|
||||
* [^H]
|
||||
*/
|
||||
protected el_action_t
|
||||
/*ARGSUSED*/
|
||||
vi_delete_prev_char(EditLine *el, int c)
|
||||
{
|
||||
|
||||
if (el->el_chared.c_vcmd.ins == 0)
|
||||
return (CC_ERROR);
|
||||
|
||||
if (el->el_chared.c_vcmd.ins >
|
||||
el->el_line.cursor - el->el_state.argument)
|
||||
return (CC_ERROR);
|
||||
|
||||
c_delbefore(el, el->el_state.argument);
|
||||
el->el_line.cursor -= el->el_state.argument;
|
||||
|
||||
return (CC_REFRESH);
|
||||
}
|
||||
|
||||
|
||||
/* vi_list_or_eof():
|
||||
* Vi list choices for completion or indicate end of file if empty line
|
||||
* [^D]
|
||||
*/
|
||||
protected el_action_t
|
||||
/*ARGSUSED*/
|
||||
vi_list_or_eof(EditLine *el, int c)
|
||||
{
|
||||
|
||||
#ifdef notyet
|
||||
if (el->el_line.cursor == el->el_line.lastchar &&
|
||||
el->el_line.cursor == el->el_line.buffer) {
|
||||
#endif
|
||||
term_overwrite(el, STReof, 4); /* then do a EOF */
|
||||
term__flush();
|
||||
return (CC_EOF);
|
||||
#ifdef notyet
|
||||
} else {
|
||||
re_goto_bottom(el);
|
||||
*el->el_line.lastchar = '\0'; /* just in case */
|
||||
return (CC_LIST_CHOICES);
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
|
||||
/* vi_kill_line_prev():
|
||||
* Vi cut from beginning of line to cursor
|
||||
* [^U]
|
||||
*/
|
||||
protected el_action_t
|
||||
/*ARGSUSED*/
|
||||
vi_kill_line_prev(EditLine *el, int c)
|
||||
{
|
||||
char *kp, *cp;
|
||||
|
||||
cp = el->el_line.buffer;
|
||||
kp = el->el_chared.c_kill.buf;
|
||||
while (cp < el->el_line.cursor)
|
||||
*kp++ = *cp++; /* copy it */
|
||||
el->el_chared.c_kill.last = kp;
|
||||
c_delbefore(el, el->el_line.cursor - el->el_line.buffer);
|
||||
el->el_line.cursor = el->el_line.buffer; /* zap! */
|
||||
return (CC_REFRESH);
|
||||
}
|
||||
|
||||
|
||||
/* vi_search_prev():
|
||||
* Vi search history previous
|
||||
* [?]
|
||||
*/
|
||||
protected el_action_t
|
||||
/*ARGSUSED*/
|
||||
vi_search_prev(EditLine *el, int c)
|
||||
{
|
||||
|
||||
return (cv_search(el, ED_SEARCH_PREV_HISTORY));
|
||||
}
|
||||
|
||||
|
||||
/* vi_search_next():
|
||||
* Vi search history next
|
||||
* [/]
|
||||
*/
|
||||
protected el_action_t
|
||||
/*ARGSUSED*/
|
||||
vi_search_next(EditLine *el, int c)
|
||||
{
|
||||
|
||||
return (cv_search(el, ED_SEARCH_NEXT_HISTORY));
|
||||
}
|
||||
|
||||
|
||||
/* vi_repeat_search_next():
|
||||
* Vi repeat current search in the same search direction
|
||||
* [n]
|
||||
*/
|
||||
protected el_action_t
|
||||
/*ARGSUSED*/
|
||||
vi_repeat_search_next(EditLine *el, int c)
|
||||
{
|
||||
|
||||
if (el->el_search.patlen == 0)
|
||||
return (CC_ERROR);
|
||||
else
|
||||
return (cv_repeat_srch(el, el->el_search.patdir));
|
||||
}
|
||||
|
||||
|
||||
/* vi_repeat_search_prev():
|
||||
* Vi repeat current search in the opposite search direction
|
||||
* [N]
|
||||
*/
|
||||
/*ARGSUSED*/
|
||||
protected el_action_t
|
||||
vi_repeat_search_prev(EditLine *el, int c)
|
||||
{
|
||||
|
||||
if (el->el_search.patlen == 0)
|
||||
return (CC_ERROR);
|
||||
else
|
||||
return (cv_repeat_srch(el,
|
||||
el->el_search.patdir == ED_SEARCH_PREV_HISTORY ?
|
||||
ED_SEARCH_NEXT_HISTORY : ED_SEARCH_PREV_HISTORY));
|
||||
}
|
||||
|
||||
|
||||
/* vi_next_char():
|
||||
* Vi move to the character specified next
|
||||
* [f]
|
||||
*/
|
||||
protected el_action_t
|
||||
/*ARGSUSED*/
|
||||
vi_next_char(EditLine *el, int c)
|
||||
{
|
||||
char ch;
|
||||
|
||||
if (el_getc(el, &ch) != 1)
|
||||
return (ed_end_of_file(el, 0));
|
||||
|
||||
el->el_search.chadir = CHAR_FWD;
|
||||
el->el_search.chacha = ch;
|
||||
|
||||
return (cv_csearch_fwd(el, ch, el->el_state.argument, 0));
|
||||
|
||||
}
|
||||
|
||||
|
||||
/* vi_prev_char():
|
||||
* Vi move to the character specified previous
|
||||
* [F]
|
||||
*/
|
||||
protected el_action_t
|
||||
/*ARGSUSED*/
|
||||
vi_prev_char(EditLine *el, int c)
|
||||
{
|
||||
char ch;
|
||||
|
||||
if (el_getc(el, &ch) != 1)
|
||||
return (ed_end_of_file(el, 0));
|
||||
|
||||
el->el_search.chadir = CHAR_BACK;
|
||||
el->el_search.chacha = ch;
|
||||
|
||||
return (cv_csearch_back(el, ch, el->el_state.argument, 0));
|
||||
}
|
||||
|
||||
|
||||
/* vi_to_next_char():
|
||||
* Vi move up to the character specified next
|
||||
* [t]
|
||||
*/
|
||||
protected el_action_t
|
||||
/*ARGSUSED*/
|
||||
vi_to_next_char(EditLine *el, int c)
|
||||
{
|
||||
char ch;
|
||||
|
||||
if (el_getc(el, &ch) != 1)
|
||||
return (ed_end_of_file(el, 0));
|
||||
|
||||
return (cv_csearch_fwd(el, ch, el->el_state.argument, 1));
|
||||
|
||||
}
|
||||
|
||||
|
||||
/* vi_to_prev_char():
|
||||
* Vi move up to the character specified previous
|
||||
* [T]
|
||||
*/
|
||||
protected el_action_t
|
||||
/*ARGSUSED*/
|
||||
vi_to_prev_char(EditLine *el, int c)
|
||||
{
|
||||
char ch;
|
||||
|
||||
if (el_getc(el, &ch) != 1)
|
||||
return (ed_end_of_file(el, 0));
|
||||
|
||||
return (cv_csearch_back(el, ch, el->el_state.argument, 1));
|
||||
}
|
||||
|
||||
|
||||
/* vi_repeat_next_char():
|
||||
* Vi repeat current character search in the same search direction
|
||||
* [;]
|
||||
*/
|
||||
protected el_action_t
|
||||
/*ARGSUSED*/
|
||||
vi_repeat_next_char(EditLine *el, int c)
|
||||
{
|
||||
|
||||
if (el->el_search.chacha == 0)
|
||||
return (CC_ERROR);
|
||||
|
||||
return (el->el_search.chadir == CHAR_FWD
|
||||
? cv_csearch_fwd(el, el->el_search.chacha,
|
||||
el->el_state.argument, 0)
|
||||
: cv_csearch_back(el, el->el_search.chacha,
|
||||
el->el_state.argument, 0));
|
||||
}
|
||||
|
||||
|
||||
/* vi_repeat_prev_char():
|
||||
* Vi repeat current character search in the opposite search direction
|
||||
* [,]
|
||||
*/
|
||||
protected el_action_t
|
||||
/*ARGSUSED*/
|
||||
vi_repeat_prev_char(EditLine *el, int c)
|
||||
{
|
||||
|
||||
if (el->el_search.chacha == 0)
|
||||
return (CC_ERROR);
|
||||
|
||||
return el->el_search.chadir == CHAR_BACK ?
|
||||
cv_csearch_fwd(el, el->el_search.chacha, el->el_state.argument, 0) :
|
||||
cv_csearch_back(el, el->el_search.chacha, el->el_state.argument, 0);
|
||||
}
|
Reference in New Issue
Block a user