Imported from ../bash-1.14.7.tar.gz.

This commit is contained in:
Jari Aalto 1996-08-26 18:22:31 +00:00
commit 726f63884d
402 changed files with 150297 additions and 0 deletions

23
lib/doc-support/Makefile Normal file
View file

@ -0,0 +1,23 @@
GETOPT = ${topdir}/builtins/getopt.o
OBJECTS = texindex.o $(GETOPT)
SOURCES = texindex.c
LDFLAGS = -g
srcdir = .
VPATH = .:$(srcdir)
.c.o:
rm -f $@
$(CC) $(CFLAGS) -c $<
all: texindex
texindex: texindex.o
$(CC) $(LDFLAGS) -o $@ $(OBJECTS) $(LIBS)
clean:
rm -f texindex.o
realclean distclean maintainer-clean: clean
rm -f texindex

129
lib/doc-support/getopt.h Normal file
View file

@ -0,0 +1,129 @@
/* Declarations for getopt.
Copyright (C) 1989, 1990, 1991, 1992, 1993 Free Software Foundation, Inc.
This program is free software; you can redistribute it and/or modify it
under the terms of the GNU General Public License as published by the
Free Software Foundation; either version 2, or (at your option) any
later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, 675 Mass Ave, Cambridge, MA 02139, USA. */
#ifndef _GETOPT_H
#define _GETOPT_H 1
#ifdef __cplusplus
extern "C" {
#endif
/* For communication from `getopt' to the caller.
When `getopt' finds an option that takes an argument,
the argument value is returned here.
Also, when `ordering' is RETURN_IN_ORDER,
each non-option ARGV-element is returned here. */
extern char *optarg;
/* Index in ARGV of the next element to be scanned.
This is used for communication to and from the caller
and for communication between successive calls to `getopt'.
On entry to `getopt', zero means this is the first call; initialize.
When `getopt' returns EOF, this is the index of the first of the
non-option elements that the caller should itself scan.
Otherwise, `optind' communicates from one call to the next
how much of ARGV has been scanned so far. */
extern int optind;
/* Callers store zero here to inhibit the error message `getopt' prints
for unrecognized options. */
extern int opterr;
/* Set to an option character which was unrecognized. */
extern int optopt;
/* Describe the long-named options requested by the application.
The LONG_OPTIONS argument to getopt_long or getopt_long_only is a vector
of `struct option' terminated by an element containing a name which is
zero.
The field `has_arg' is:
no_argument (or 0) if the option does not take an argument,
required_argument (or 1) if the option requires an argument,
optional_argument (or 2) if the option takes an optional argument.
If the field `flag' is not NULL, it points to a variable that is set
to the value given in the field `val' when the option is found, but
left unchanged if the option is not found.
To have a long-named option do something other than set an `int' to
a compiled-in constant, such as set a value from `optarg', set the
option's `flag' field to zero and its `val' field to a nonzero
value (the equivalent single-letter option character, if there is
one). For long options that have a zero `flag' field, `getopt'
returns the contents of the `val' field. */
struct option
{
#if __STDC__
const char *name;
#else
char *name;
#endif
/* has_arg can't be an enum because some compilers complain about
type mismatches in all the code that assumes it is an int. */
int has_arg;
int *flag;
int val;
};
/* Names for the values of the `has_arg' field of `struct option'. */
#define no_argument 0
#define required_argument 1
#define optional_argument 2
#if __STDC__
#if defined(__GNU_LIBRARY__)
/* Many other libraries have conflicting prototypes for getopt, with
differences in the consts, in stdlib.h. To avoid compilation
errors, only prototype getopt for the GNU C library. */
extern int getopt (int argc, char *const *argv, const char *shortopts);
#else /* not __GNU_LIBRARY__ */
extern int getopt ();
#endif /* not __GNU_LIBRARY__ */
extern int getopt_long (int argc, char *const *argv, const char *shortopts,
const struct option *longopts, int *longind);
extern int getopt_long_only (int argc, char *const *argv,
const char *shortopts,
const struct option *longopts, int *longind);
/* Internal only. Users should not call this directly. */
extern int _getopt_internal (int argc, char *const *argv,
const char *shortopts,
const struct option *longopts, int *longind,
int long_only);
#else /* not __STDC__ */
extern int getopt ();
extern int getopt_long ();
extern int getopt_long_only ();
extern int _getopt_internal ();
#endif /* not __STDC__ */
#ifdef __cplusplus
}
#endif
#endif /* _GETOPT_H */

1666
lib/doc-support/texindex.c Normal file

File diff suppressed because it is too large Load diff

13
lib/glob/ChangeLog Normal file
View file

@ -0,0 +1,13 @@
Thu Oct 29 08:58:12 1992 Brian Fox (bfox@cubit)
* glob.c (glob_filename): Fix tiny memory leak. Rework some
comments.
Mon Jul 20 10:57:36 1992 Brian Fox (bfox@cubit)
* glob.c: (glob_filename) Change use of rindex () to strrchr ().
Thu Jul 9 10:02:47 1992 Brian Fox (bfox@cubit)
* fnmatch.c: (fnmatch) Only process `[' as the start of a bracket
expression if there is a closing `]' present in the string.

95
lib/glob/Makefile Normal file
View file

@ -0,0 +1,95 @@
## -*- text -*- ####################################################
# #
# Makefile for the GNU Glob Library. #
# #
####################################################################
# This Makefile is hand made from a template file, found in
# ../template. Each library must provide several Makefile
# targets: `all', `clean', `documentation', `install', and
# `what-tar'. The `what-tar' target reports the names of the
# files that need to be included in a tarfile to build the full
# code and documentation for this library.
# Please note that the values for INCLUDES, CC, AR, RM, CP,
# RANLIB, and selfdir are passed in from ../Makefile, and do
# not need to be defined here.
srcdir = .
VPATH = .:$(srcdir)
# Here is a rule for making .o files from .c files that doesn't force
# the type of the machine (like -sun3) into the flags.
.c.o:
$(CC) -c $(CFLAGS) $(INCLUDES) $(LOCAL_DEFINES) $(CPPFLAGS) $<
# LOCAL_DEFINES are flags that are specific to this library.
# Define -DUSG if you are using a System V operating system.
LOCAL_DEFINES = $(LOCAL_INCLUDES) #-DUSG
# For libraries which include headers from other libraries.
LOCAL_INCLUDES = -I..
# The name of the library target.
LIBRARY_NAME = libglob.a
# The C code source files for this library.
CSOURCES = $(srcdir)glob.c $(srcdir)fnmatch.c
# The header files for this library.
HSOURCES = $(srcdir)fnmatch.h
OBJECTS = glob.o fnmatch.o
# The texinfo files which document this library.
DOCSOURCE = doc/glob.texi
DOCOBJECT = doc/glob.dvi
DOCSUPPORT = doc/Makefile
DOCUMENTATION = $(DOCSOURCE) $(DOCOBJECT) $(DOCSUPPORT)
SUPPORT = Makefile ChangeLog $(DOCSUPPORT)
SOURCES = $(CSOURCES) $(HSOURCES) $(DOCSOURCE)
THINGS_TO_TAR = $(SOURCES) $(SUPPORT)
######################################################################
all: $(LIBRARY_NAME)
$(LIBRARY_NAME): $(OBJECTS)
$(RM) -f $@
$(AR) cq $@ $(OBJECTS)
-[ -n "$(RANLIB)" ] && $(RANLIB) $@
what-tar:
@for file in $(THINGS_TO_TAR); do \
echo $(selfdir)$$file; \
done
documentation: force
-(cd doc && $(MAKE) $(MFLAGS))
force:
# The rule for 'includes' is written funny so that the if statement
# always returns TRUE unless there really was an error installing the
# include files.
install:
-$(MV) $(bindir)/$(LIBRARY_NAME) $(bindir)/$(LIBRARY_NAME)-old
$(CP) $(LIBRARY_NAME) $(bindir)/$(LIBRARY_NAME)
-[ -n "$(RANLIB)" ] && $(RANLIB) -t $(bindir)/$(LIBRARY_NAME)
clean:
rm -f $(OBJECTS) $(LIBRARY_NAME)
-(cd doc && $(MAKE) $(MFLAGS) $@)
maintainer-clean realclean mostlyclean distclean: clean
-(cd doc && $(MAKE) $(MFLAGS) $@)
######################################################################
# #
# Dependencies for the object files which make up this library. #
# #
######################################################################
fnmatch.o: fnmatch.c fnmatch.h

5
lib/glob/doc/Makefile Normal file
View file

@ -0,0 +1,5 @@
all:
cp glob.texi glob.info
maintainer-clean realclean distclean clean:
rm -f glob.?? glob.info

1
lib/glob/doc/glob.texi Normal file
View file

@ -0,0 +1 @@
Nothing happens here.

189
lib/glob/fnmatch.c Normal file
View file

@ -0,0 +1,189 @@
/* Copyright (C) 1991 Free Software Foundation, Inc.
This file is part of the GNU C Library.
The GNU C Library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public License as
published by the Free Software Foundation; either version 2 of the
License, or (at your option) any later version.
The GNU C Library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with the GNU C Library; see the file COPYING.LIB. If
not, write to the Free Software Foundation, Inc., 675 Mass Ave,
Cambridge, MA 02139, USA. */
#include <errno.h>
#include "fnmatch.h"
#if !defined (__GNU_LIBRARY__) && !defined (STDC_HEADERS)
# if !defined (errno)
extern int errno;
# endif /* !errno */
#endif
/* Match STRING against the filename pattern PATTERN, returning zero if
it matches, FNM_NOMATCH if not. */
int
fnmatch (pattern, string, flags)
char *pattern;
char *string;
int flags;
{
register char *p = pattern, *n = string;
register char c;
if ((flags & ~__FNM_FLAGS) != 0)
{
errno = EINVAL;
return (-1);
}
while ((c = *p++) != '\0')
{
switch (c)
{
case '?':
if (*n == '\0')
return (FNM_NOMATCH);
else if ((flags & FNM_PATHNAME) && *n == '/')
return (FNM_NOMATCH);
else if ((flags & FNM_PERIOD) && *n == '.' &&
(n == string || ((flags & FNM_PATHNAME) && n[-1] == '/')))
return (FNM_NOMATCH);
break;
case '\\':
if (!(flags & FNM_NOESCAPE))
c = *p++;
if (*n != c)
return (FNM_NOMATCH);
break;
case '*':
if ((flags & FNM_PERIOD) && *n == '.' &&
(n == string || ((flags & FNM_PATHNAME) && n[-1] == '/')))
return (FNM_NOMATCH);
for (c = *p++; c == '?' || c == '*'; c = *p++, ++n)
if (((flags & FNM_PATHNAME) && *n == '/') ||
(c == '?' && *n == '\0'))
return (FNM_NOMATCH);
if (c == '\0')
return (0);
{
char c1 = (!(flags & FNM_NOESCAPE) && c == '\\') ? *p : c;
for (--p; *n != '\0'; ++n)
if ((c == '[' || *n == c1) &&
fnmatch (p, n, flags & ~FNM_PERIOD) == 0)
return (0);
return (FNM_NOMATCH);
}
case '[':
{
/* Nonzero if the sense of the character class is inverted. */
register int not;
if (*n == '\0')
return (FNM_NOMATCH);
if ((flags & FNM_PERIOD) && *n == '.' &&
(n == string || ((flags & FNM_PATHNAME) && n[-1] == '/')))
return (FNM_NOMATCH);
/* Make sure there is a closing `]'. If there isn't, the `['
is just a character to be matched. */
{
register char *np;
for (np = p; np && *np && *np != ']'; np++);
if (np && !*np)
{
if (*n != '[')
return (FNM_NOMATCH);
goto next_char;
}
}
not = (*p == '!' || *p == '^');
if (not)
++p;
c = *p++;
for (;;)
{
register char cstart = c, cend = c;
if (!(flags & FNM_NOESCAPE) && c == '\\')
cstart = cend = *p++;
if (c == '\0')
/* [ (unterminated) loses. */
return (FNM_NOMATCH);
c = *p++;
if ((flags & FNM_PATHNAME) && c == '/')
/* [/] can never match. */
return (FNM_NOMATCH);
if (c == '-' && *p != ']')
{
cend = *p++;
if (!(flags & FNM_NOESCAPE) && cend == '\\')
cend = *p++;
if (cend == '\0')
return (FNM_NOMATCH);
c = *p++;
}
if (*n >= cstart && *n <= cend)
goto matched;
if (c == ']')
break;
}
if (!not)
return (FNM_NOMATCH);
next_char:
break;
matched:
/* Skip the rest of the [...] that already matched. */
while (c != ']')
{
if (c == '\0')
/* [... (unterminated) loses. */
return (FNM_NOMATCH);
c = *p++;
if (!(flags & FNM_NOESCAPE) && c == '\\')
/* 1003.2d11 is unclear if this is right. %%% */
++p;
}
if (not)
return (FNM_NOMATCH);
}
break;
default:
if (c != *n)
return (FNM_NOMATCH);
}
++n;
}
if (*n == '\0')
return (0);
return (FNM_NOMATCH);
}

36
lib/glob/fnmatch.h Normal file
View file

@ -0,0 +1,36 @@
/* Copyright (C) 1991 Free Software Foundation, Inc.
This file is part of the GNU C Library.
The GNU C Library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public License as
published by the Free Software Foundation; either version 2 of the
License, or (at your option) any later version.
The GNU C Library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with the GNU C Library; see the file COPYING.LIB. If
not, write to the Free Software Foundation, Inc., 675 Mass Ave,
Cambridge, MA 02139, USA. */
#ifndef _FNMATCH_H
#define _FNMATCH_H 1
/* Bits set in the FLAGS argument to `fnmatch'. */
#define FNM_PATHNAME (1 << 0)/* No wildcard can ever match `/'. */
#define FNM_NOESCAPE (1 << 1)/* Backslashes don't quote special chars. */
#define FNM_PERIOD (1 << 2)/* Leading `.' is matched only explicitly. */
#define __FNM_FLAGS (FNM_PATHNAME|FNM_NOESCAPE|FNM_PERIOD)
/* Value returned by `fnmatch' if STRING does not match PATTERN. */
#define FNM_NOMATCH 1
/* Match STRING against the filename pattern PATTERN,
returning zero if it matches, FNM_NOMATCH if not. */
extern int fnmatch();
#endif /* fnmatch.h */

574
lib/glob/glob.c Normal file
View file

@ -0,0 +1,574 @@
/* File-name wildcard pattern matching for GNU.
Copyright (C) 1985, 1988, 1989 Free Software Foundation, Inc.
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 1, or (at your option)
any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */
/* To whomever it may concern: I have never seen the code which most
Unix programs use to perform this function. I wrote this from scratch
based on specifications for the pattern matching. --RMS. */
#if defined (SHELL)
# if defined (HAVE_STDLIB_H)
# include <stdlib.h>
# else
# include "ansi_stdlib.h"
# endif /* HAVE_STDLIB_H */
# include <config.h>
#endif
#include <sys/types.h>
#if !defined (SHELL) && (defined (_POSIX_VERSION) || defined (USGr3))
# if !defined (HAVE_DIRENT_H)
# define HAVE_DIRENT_H
# endif /* !HAVE_DIRENT_H */
#endif /* !SHELL && (_POSIX_VERSION || USGr3) */
#if defined (HAVE_DIRENT_H)
# include <dirent.h>
# if !defined (direct)
# define direct dirent
# endif /* !direct */
# define D_NAMLEN(d) strlen ((d)->d_name)
#else /* !HAVE_DIRENT_H */
# define D_NAMLEN(d) ((d)->d_namlen)
# if defined (USG)
# if defined (Xenix)
# include <sys/ndir.h>
# else /* !Xenix (but USG...) */
# include "ndir.h"
# endif /* !Xenix */
# else /* !USG */
# include <sys/dir.h>
# endif /* !USG */
#endif /* !HAVE_DIRENT_H */
#if defined (_POSIX_SOURCE)
/* Posix does not require that the d_ino field be present, and some
systems do not provide it. */
# define REAL_DIR_ENTRY(dp) 1
#else
# define REAL_DIR_ENTRY(dp) (dp->d_ino != 0)
#endif /* _POSIX_SOURCE */
#if defined (USG) || defined (NeXT)
# if !defined (HAVE_STRING_H)
# define HAVE_STRING_H
# endif /* !HAVE_STRING_H */
#endif /* USG || NeXT */
#if defined (HAVE_STRING_H)
# include <string.h>
#else /* !HAVE_STRING_H */
# include <strings.h>
#endif /* !HAVE_STRING_H */
#if defined (USG)
# if !defined (isc386)
# include <memory.h>
# endif /* !isc386 */
# if defined (RISC6000)
extern void bcopy ();
# else /* !RISC6000 */
# define bcopy(s, d, n) ((void) memcpy ((d), (s), (n)))
# endif /* !RISC6000 */
#endif /* USG */
#include "fnmatch.h"
/* If the opendir () on your system lets you open non-directory files,
then we consider that not robust. Define OPENDIR_NOT_ROBUST in the
SYSDEP_CFLAGS for your machines entry in machines.h. */
#if defined (OPENDIR_NOT_ROBUST)
# if defined (SHELL)
# include "posixstat.h"
# else /* !SHELL */
# include <sys/stat.h>
# endif /* !SHELL */
#endif /* OPENDIR_NOT_ROBUST */
#if !defined (HAVE_STDLIB_H)
extern char *malloc (), *realloc ();
extern void free ();
#endif /* !HAVE_STDLIB_H */
#if !defined (NULL)
# if defined (__STDC__)
# define NULL ((void *) 0)
# else
# define NULL 0x0
# endif /* __STDC__ */
#endif /* !NULL */
#if defined (SHELL)
extern int interrupt_state;
#endif /* SHELL */
/* Global variable which controls whether or not * matches .*.
Non-zero means don't match .*. */
int noglob_dot_filenames = 1;
/* Global variable to return to signify an error in globbing. */
char *glob_error_return;
/* Return nonzero if PATTERN has any special globbing chars in it. */
int
glob_pattern_p (pattern)
char *pattern;
{
register char *p = pattern;
register char c;
int open = 0;
while ((c = *p++) != '\0')
switch (c)
{
case '?':
case '*':
return (1);
case '[': /* Only accept an open brace if there is a close */
open++; /* brace to match it. Bracket expressions must be */
continue; /* complete, according to Posix.2 */
case ']':
if (open)
return (1);
continue;
case '\\':
if (*p++ == '\0')
return (0);
}
return (0);
}
/* Remove backslashes quoting characters in PATHNAME by modifying PATHNAME. */
static void
dequote_pathname (pathname)
char *pathname;
{
register int i, j;
for (i = j = 0; pathname && pathname[i]; )
{
if (pathname[i] == '\\')
i++;
pathname[j++] = pathname[i++];
if (!pathname[i - 1])
break;
}
pathname[j] = '\0';
}
/* Return a vector of names of files in directory DIR
whose names match glob pattern PAT.
The names are not in any particular order.
Wildcards at the beginning of PAT do not match an initial period.
The vector is terminated by an element that is a null pointer.
To free the space allocated, first free the vector's elements,
then free the vector.
Return 0 if cannot get enough memory to hold the pointer
and the names.
Return -1 if cannot access directory DIR.
Look in errno for more information. */
char **
glob_vector (pat, dir)
char *pat;
char *dir;
{
struct globval
{
struct globval *next;
char *name;
};
DIR *d;
register struct direct *dp;
struct globval *lastlink;
register struct globval *nextlink;
register char *nextname;
unsigned int count;
int lose, skip;
register char **name_vector;
register unsigned int i;
#if defined (OPENDIR_NOT_ROBUST)
struct stat finfo;
if (stat (dir, &finfo) < 0)
return ((char **) &glob_error_return);
if (!S_ISDIR (finfo.st_mode))
return ((char **) &glob_error_return);
#endif /* OPENDIR_NOT_ROBUST */
d = opendir (dir);
if (d == NULL)
return ((char **) &glob_error_return);
lastlink = 0;
count = 0;
lose = 0;
skip = 0;
/* If PAT is empty, skip the loop, but return one (empty) filename. */
if (!pat || !*pat)
{
nextlink = (struct globval *)alloca (sizeof (struct globval));
nextlink->next = lastlink;
nextname = (char *) malloc (1);
if (!nextname)
lose = 1;
else
{
lastlink = nextlink;
nextlink->name = nextname;
nextname[0] = '\0';
count++;
}
skip = 1;
}
/* Scan the directory, finding all names that match.
For each name that matches, allocate a struct globval
on the stack and store the name in it.
Chain those structs together; lastlink is the front of the chain. */
while (!skip)
{
int flags; /* Flags passed to fnmatch (). */
#if defined (SHELL)
/* Make globbing interruptible in the bash shell. */
if (interrupt_state)
{
closedir (d);
lose = 1;
goto lost;
}
#endif /* SHELL */
dp = readdir (d);
if (dp == NULL)
break;
/* If this directory entry is not to be used, try again. */
if (!REAL_DIR_ENTRY (dp))
continue;
/* If a dot must be explicity matched, check to see if they do. */
if (noglob_dot_filenames && dp->d_name[0] == '.' && pat[0] != '.')
continue;
flags = (noglob_dot_filenames ? FNM_PERIOD : 0) | FNM_PATHNAME;
if (fnmatch (pat, dp->d_name, flags) != FNM_NOMATCH)
{
nextlink = (struct globval *) alloca (sizeof (struct globval));
nextlink->next = lastlink;
nextname = (char *) malloc (D_NAMLEN (dp) + 1);
if (nextname == NULL)
{
lose = 1;
break;
}
lastlink = nextlink;
nextlink->name = nextname;
bcopy (dp->d_name, nextname, D_NAMLEN (dp) + 1);
++count;
}
}
(void) closedir (d);
if (!lose)
{
name_vector = (char **) malloc ((count + 1) * sizeof (char *));
lose |= name_vector == NULL;
}
/* Have we run out of memory? */
lost:
if (lose)
{
/* Here free the strings we have got. */
while (lastlink)
{
free (lastlink->name);
lastlink = lastlink->next;
}
#if defined (SHELL)
if (interrupt_state)
throw_to_top_level ();
#endif /* SHELL */
return (NULL);
}
/* Copy the name pointers from the linked list into the vector. */
for (i = 0; i < count; ++i)
{
name_vector[i] = lastlink->name;
lastlink = lastlink->next;
}
name_vector[count] = NULL;
return (name_vector);
}
/* Return a new array which is the concatenation of each string in ARRAY
to DIR. This function expects you to pass in an allocated ARRAY, and
it takes care of free()ing that array. Thus, you might think of this
function as side-effecting ARRAY. */
static char **
glob_dir_to_array (dir, array)
char *dir, **array;
{
register unsigned int i, l;
int add_slash;
char **result;
l = strlen (dir);
if (l == 0)
return (array);
add_slash = dir[l - 1] != '/';
i = 0;
while (array[i] != NULL)
++i;
result = (char **) malloc ((i + 1) * sizeof (char *));
if (result == NULL)
return (NULL);
for (i = 0; array[i] != NULL; i++)
{
result[i] = (char *) malloc (l + (add_slash ? 1 : 0)
+ strlen (array[i]) + 1);
if (result[i] == NULL)
return (NULL);
sprintf (result[i], "%s%s%s", dir, add_slash ? "/" : "", array[i]);
}
result[i] = NULL;
/* Free the input array. */
for (i = 0; array[i] != NULL; i++)
free (array[i]);
free ((char *) array);
return (result);
}
/* Do globbing on PATHNAME. Return an array of pathnames that match,
marking the end of the array with a null-pointer as an element.
If no pathnames match, then the array is empty (first element is null).
If there isn't enough memory, then return NULL.
If a file system error occurs, return -1; `errno' has the error code. */
char **
glob_filename (pathname)
char *pathname;
{
char **result;
unsigned int result_size;
char *directory_name, *filename;
unsigned int directory_len;
result = (char **) malloc (sizeof (char *));
result_size = 1;
if (result == NULL)
return (NULL);
result[0] = NULL;
/* Find the filename. */
filename = strrchr (pathname, '/');
if (filename == NULL)
{
filename = pathname;
directory_name = "";
directory_len = 0;
}
else
{
directory_len = (filename - pathname) + 1;
directory_name = (char *) alloca (directory_len + 1);
bcopy (pathname, directory_name, directory_len);
directory_name[directory_len] = '\0';
++filename;
}
/* If directory_name contains globbing characters, then we
have to expand the previous levels. Just recurse. */
if (glob_pattern_p (directory_name))
{
char **directories;
register unsigned int i;
if (directory_name[directory_len - 1] == '/')
directory_name[directory_len - 1] = '\0';
directories = glob_filename (directory_name);
if (directories == NULL)
goto memory_error;
else if (directories == (char **)&glob_error_return)
{
free ((char *)result);
return ((char **) &glob_error_return);
}
else if (*directories == NULL)
{
free ((char *) directories);
free ((char *) result);
return ((char **) &glob_error_return);
}
/* We have successfully globbed the preceding directory name.
For each name in DIRECTORIES, call glob_vector on it and
FILENAME. Concatenate the results together. */
for (i = 0; directories[i] != NULL; ++i)
{
char **temp_results;
/* Scan directory even on a NULL pathname. That way, `*h/'
returns only directories ending in `h', instead of all
files ending in `h' with a `/' appended. */
temp_results = glob_vector (filename, directories[i]);
/* Handle error cases. */
if (temp_results == NULL)
goto memory_error;
else if (temp_results == (char **)&glob_error_return)
/* This filename is probably not a directory. Ignore it. */
;
else
{
char **array;
register unsigned int l;
array = glob_dir_to_array (directories[i], temp_results);
l = 0;
while (array[l] != NULL)
++l;
result =
(char **)realloc (result, (result_size + l) * sizeof (char *));
if (result == NULL)
goto memory_error;
for (l = 0; array[l] != NULL; ++l)
result[result_size++ - 1] = array[l];
result[result_size - 1] = NULL;
/* Note that the elements of ARRAY are not freed. */
free ((char *) array);
}
}
/* Free the directories. */
for (i = 0; directories[i]; i++)
free (directories[i]);
free ((char *) directories);
return (result);
}
/* If there is only a directory name, return it. */
if (*filename == '\0')
{
result = (char **) realloc ((char *) result, 2 * sizeof (char *));
if (result == NULL)
return (NULL);
result[0] = (char *) malloc (directory_len + 1);
if (result[0] == NULL)
goto memory_error;
bcopy (directory_name, result[0], directory_len + 1);
result[1] = NULL;
return (result);
}
else
{
char **temp_results;
/* There are no unquoted globbing characters in DIRECTORY_NAME.
Dequote it before we try to open the directory since there may
be quoted globbing characters which should be treated verbatim. */
if (directory_len > 0)
dequote_pathname (directory_name);
/* We allocated a small array called RESULT, which we won't be using.
Free that memory now. */
free (result);
/* Just return what glob_vector () returns appended to the
directory name. */
temp_results =
glob_vector (filename, (directory_len == 0 ? "." : directory_name));
if (temp_results == NULL || temp_results == (char **)&glob_error_return)
return (temp_results);
return (glob_dir_to_array (directory_name, temp_results));
}
/* We get to memory_error if the program has run out of memory, or
if this is the shell, and we have been interrupted. */
memory_error:
if (result != NULL)
{
register unsigned int i;
for (i = 0; result[i] != NULL; ++i)
free (result[i]);
free ((char *) result);
}
#if defined (SHELL)
if (interrupt_state)
throw_to_top_level ();
#endif /* SHELL */
return (NULL);
}
#if defined (TEST)
main (argc, argv)
int argc;
char **argv;
{
unsigned int i;
for (i = 1; i < argc; ++i)
{
char **value = glob_filename (argv[i]);
if (value == NULL)
puts ("Out of memory.");
else if (value == &glob_error_return)
perror (argv[i]);
else
for (i = 0; value[i] != NULL; i++)
puts (value[i]);
}
exit (0);
}
#endif /* TEST. */

50
lib/glob/ndir.h Normal file
View file

@ -0,0 +1,50 @@
/* <dir.h> -- definitions for 4.2BSD-compatible directory access.
last edit: 09-Jul-1983 D A Gwyn. */
#if defined (VMS)
# if !defined (FAB$C_BID)
# include <fab.h>
# endif
# if !defined (NAM$C_BID)
# include <nam.h>
# endif
# if !defined (RMS$_SUC)
# include <rmsdef.h>
# endif
# include "dir.h"
#endif /* VMS */
/* Size of directory block. */
#define DIRBLKSIZ 512
/* NOTE: MAXNAMLEN must be one less than a multiple of 4 */
#if defined (VMS)
# define MAXNAMLEN (DIR$S_NAME + 7) /* 80 plus room for version #. */
# define MAXFULLSPEC NAM$C_MAXRSS /* Maximum full spec */
#else
# define MAXNAMLEN 15 /* Maximum filename length. */
#endif /* VMS */
/* Data from readdir (). */
struct direct {
long d_ino; /* Inode number of entry. */
unsigned short d_reclen; /* Length of this record. */
unsigned short d_namlen; /* Length of string in d_name. */
char d_name[MAXNAMLEN + 1]; /* Name of file. */
};
/* Stream data from opendir (). */
typedef struct {
int dd_fd; /* File descriptor. */
int dd_loc; /* Offset in block. */
int dd_size; /* Amount of valid data. */
char dd_buf[DIRBLKSIZ]; /* Directory block. */
} DIR;
extern DIR *opendir ();
extern struct direct *readdir ();
extern long telldir ();
extern void seekdir (), closedir ();
#define rewinddir(dirp) seekdir (dirp, 0L)

28
lib/malloc/Makefile Normal file
View file

@ -0,0 +1,28 @@
# Skeleton Makefile for the GNU malloc code
#
# Maybe this should really create a library instead of just compiling
# source files
srcdir = .
VPATH = .:$(srcdir)
.c.o:
$(CC) $(CFLAGS) $(CPPFLAGS) -c $<
.s.o:
$(CC) $(CFLAGS) $(CPPFLAGS) -c $<
MALLOC_SOURCE = malloc.c
ALLOCA_SOURCE = alloca.c
ALLOCA_OBJECT = alloca.o
malloc.o: malloc.c getpagesize.h
$(ALLOCA_OBJECT): $(ALLOCA_SOURCE)
alloca.o: $(ALLOCA_SOURCE)
$(CC) $(CFLAGS) $(CPPFLAGS) -c $<
@- if [ "$(ALLOCA_OBJECT)" != alloca.o ]; then \
mv $(ALLOCA_OBJECT) alloca.o >/dev/null 2>&1 ; \
fi

480
lib/malloc/alloca.c Normal file
View file

@ -0,0 +1,480 @@
/* alloca.c -- allocate automatically reclaimed memory
(Mostly) portable public-domain implementation -- D A Gwyn
This implementation of the PWB library alloca function,
which is used to allocate space off the run-time stack so
that it is automatically reclaimed upon procedure exit,
was inspired by discussions with J. Q. Johnson of Cornell.
J.Otto Tennant <jot@cray.com> contributed the Cray support.
There are some preprocessor constants that can
be defined when compiling for your specific system, for
improved efficiency; however, the defaults should be okay.
The general concept of this implementation is to keep
track of all alloca-allocated blocks, and reclaim any
that are found to be deeper in the stack than the current
invocation. This heuristic does not reclaim storage as
soon as it becomes invalid, but it will do so eventually.
As a special case, alloca(0) reclaims storage without
allocating any. It is a good idea to use alloca(0) in
your main control loop, etc. to force garbage collection. */
#ifdef HAVE_CONFIG_H
#include "config.h"
#endif
/* If compiling with GCC 2, this file's not needed. */
#if !defined (__GNUC__) || __GNUC__ < 2
/* If alloca is defined somewhere, this file is not needed. */
#ifndef alloca
#ifdef emacs
#ifdef static
/* actually, only want this if static is defined as ""
-- this is for usg, in which emacs must undefine static
in order to make unexec workable
*/
#ifndef STACK_DIRECTION
you
lose
-- must know STACK_DIRECTION at compile-time
#endif /* STACK_DIRECTION undefined */
#endif /* static */
#endif /* emacs */
/* If your stack is a linked list of frames, you have to
provide an "address metric" ADDRESS_FUNCTION macro. */
#if defined (CRAY) && defined (CRAY_STACKSEG_END)
long i00afunc ();
#define ADDRESS_FUNCTION(arg) (char *) i00afunc (&(arg))
#else
#define ADDRESS_FUNCTION(arg) &(arg)
#endif /* CRAY && CRAY_STACKSEG_END */
#if __STDC__
typedef void *pointer;
#else
typedef char *pointer;
#endif
#define NULL 0
/* Different portions of Emacs need to call different versions of
malloc. The Emacs executable needs alloca to call xmalloc, because
ordinary malloc isn't protected from input signals. On the other
hand, the utilities in lib-src need alloca to call malloc; some of
them are very simple, and don't have an xmalloc routine.
Non-Emacs programs expect this to call use xmalloc.
Callers below should use malloc. */
#ifndef emacs
#define malloc xmalloc
extern pointer xmalloc ();
#endif
/* Define STACK_DIRECTION if you know the direction of stack
growth for your system; otherwise it will be automatically
deduced at run-time.
STACK_DIRECTION > 0 => grows toward higher addresses
STACK_DIRECTION < 0 => grows toward lower addresses
STACK_DIRECTION = 0 => direction of growth unknown */
#ifndef STACK_DIRECTION
#define STACK_DIRECTION 0 /* Direction unknown. */
#endif
#if STACK_DIRECTION != 0
#define STACK_DIR STACK_DIRECTION /* Known at compile-time. */
#else /* STACK_DIRECTION == 0; need run-time code. */
static int stack_dir; /* 1 or -1 once known. */
#define STACK_DIR stack_dir
static void
find_stack_direction ()
{
static char *addr = NULL; /* Address of first `dummy', once known. */
auto char dummy; /* To get stack address. */
if (addr == NULL)
{ /* Initial entry. */
addr = ADDRESS_FUNCTION (dummy);
find_stack_direction (); /* Recurse once. */
}
else
{
/* Second entry. */
if (ADDRESS_FUNCTION (dummy) > addr)
stack_dir = 1; /* Stack grew upward. */
else
stack_dir = -1; /* Stack grew downward. */
}
}
#endif /* STACK_DIRECTION == 0 */
/* An "alloca header" is used to:
(a) chain together all alloca'ed blocks;
(b) keep track of stack depth.
It is very important that sizeof(header) agree with malloc
alignment chunk size. The following default should work okay. */
#ifndef ALIGN_SIZE
#define ALIGN_SIZE sizeof(double)
#endif
typedef union hdr
{
char align[ALIGN_SIZE]; /* To force sizeof(header). */
struct
{
union hdr *next; /* For chaining headers. */
char *deep; /* For stack depth measure. */
} h;
} header;
static header *last_alloca_header = NULL; /* -> last alloca header. */
/* Return a pointer to at least SIZE bytes of storage,
which will be automatically reclaimed upon exit from
the procedure that called alloca. Originally, this space
was supposed to be taken from the current stack frame of the
caller, but that method cannot be made to work for some
implementations of C, for example under Gould's UTX/32. */
pointer
alloca (size)
unsigned size;
{
auto char probe; /* Probes stack depth: */
register char *depth = ADDRESS_FUNCTION (probe);
#if STACK_DIRECTION == 0
if (STACK_DIR == 0) /* Unknown growth direction. */
find_stack_direction ();
#endif
/* Reclaim garbage, defined as all alloca'd storage that
was allocated from deeper in the stack than currently. */
{
register header *hp; /* Traverses linked list. */
for (hp = last_alloca_header; hp != NULL;)
if ((STACK_DIR > 0 && hp->h.deep > depth)
|| (STACK_DIR < 0 && hp->h.deep < depth))
{
register header *np = hp->h.next;
free ((pointer) hp); /* Collect garbage. */
hp = np; /* -> next header. */
}
else
break; /* Rest are not deeper. */
last_alloca_header = hp; /* -> last valid storage. */
}
if (size == 0)
return NULL; /* No allocation required. */
/* Allocate combined header + user data storage. */
{
register pointer new = malloc (sizeof (header) + size);
/* Address of header. */
((header *) new)->h.next = last_alloca_header;
((header *) new)->h.deep = depth;
last_alloca_header = (header *) new;
/* User storage begins just after header. */
return (pointer) ((char *) new + sizeof (header));
}
}
#if defined (CRAY) && defined (CRAY_STACKSEG_END)
#ifdef DEBUG_I00AFUNC
#include <stdio.h>
#endif
#ifndef CRAY_STACK
#define CRAY_STACK
#ifndef CRAY2
/* Stack structures for CRAY-1, CRAY X-MP, and CRAY Y-MP */
struct stack_control_header
{
long shgrow:32; /* Number of times stack has grown. */
long shaseg:32; /* Size of increments to stack. */
long shhwm:32; /* High water mark of stack. */
long shsize:32; /* Current size of stack (all segments). */
};
/* The stack segment linkage control information occurs at
the high-address end of a stack segment. (The stack
grows from low addresses to high addresses.) The initial
part of the stack segment linkage control information is
0200 (octal) words. This provides for register storage
for the routine which overflows the stack. */
struct stack_segment_linkage
{
long ss[0200]; /* 0200 overflow words. */
long sssize:32; /* Number of words in this segment. */
long ssbase:32; /* Offset to stack base. */
long:32;
long sspseg:32; /* Offset to linkage control of previous
segment of stack. */
long:32;
long sstcpt:32; /* Pointer to task common address block. */
long sscsnm; /* Private control structure number for
microtasking. */
long ssusr1; /* Reserved for user. */
long ssusr2; /* Reserved for user. */
long sstpid; /* Process ID for pid based multi-tasking. */
long ssgvup; /* Pointer to multitasking thread giveup. */
long sscray[7]; /* Reserved for Cray Research. */
long ssa0;
long ssa1;
long ssa2;
long ssa3;
long ssa4;
long ssa5;
long ssa6;
long ssa7;
long sss0;
long sss1;
long sss2;
long sss3;
long sss4;
long sss5;
long sss6;
long sss7;
};
#else /* CRAY2 */
/* The following structure defines the vector of words
returned by the STKSTAT library routine. */
struct stk_stat
{
long now; /* Current total stack size. */
long maxc; /* Amount of contiguous space which would
be required to satisfy the maximum
stack demand to date. */
long high_water; /* Stack high-water mark. */
long overflows; /* Number of stack overflow ($STKOFEN) calls. */
long hits; /* Number of internal buffer hits. */
long extends; /* Number of block extensions. */
long stko_mallocs; /* Block allocations by $STKOFEN. */
long underflows; /* Number of stack underflow calls ($STKRETN). */
long stko_free; /* Number of deallocations by $STKRETN. */
long stkm_free; /* Number of deallocations by $STKMRET. */
long segments; /* Current number of stack segments. */
long maxs; /* Maximum number of stack segments so far. */
long pad_size; /* Stack pad size. */
long current_address; /* Current stack segment address. */
long current_size; /* Current stack segment size. This
number is actually corrupted by STKSTAT to
include the fifteen word trailer area. */
long initial_address; /* Address of initial segment. */
long initial_size; /* Size of initial segment. */
};
/* The following structure describes the data structure which trails
any stack segment. I think that the description in 'asdef' is
out of date. I only describe the parts that I am sure about. */
struct stk_trailer
{
long this_address; /* Address of this block. */
long this_size; /* Size of this block (does not include
this trailer). */
long unknown2;
long unknown3;
long link; /* Address of trailer block of previous
segment. */
long unknown5;
long unknown6;
long unknown7;
long unknown8;
long unknown9;
long unknown10;
long unknown11;
long unknown12;
long unknown13;
long unknown14;
};
#endif /* CRAY2 */
#endif /* not CRAY_STACK */
#ifdef CRAY2
/* Determine a "stack measure" for an arbitrary ADDRESS.
I doubt that "lint" will like this much. */
static long
i00afunc (long *address)
{
struct stk_stat status;
struct stk_trailer *trailer;
long *block, size;
long result = 0;
/* We want to iterate through all of the segments. The first
step is to get the stack status structure. We could do this
more quickly and more directly, perhaps, by referencing the
$LM00 common block, but I know that this works. */
STKSTAT (&status);
/* Set up the iteration. */
trailer = (struct stk_trailer *) (status.current_address
+ status.current_size
- 15);
/* There must be at least one stack segment. Therefore it is
a fatal error if "trailer" is null. */
if (trailer == 0)
abort ();
/* Discard segments that do not contain our argument address. */
while (trailer != 0)
{
block = (long *) trailer->this_address;
size = trailer->this_size;
if (block == 0 || size == 0)
abort ();
trailer = (struct stk_trailer *) trailer->link;
if ((block <= address) && (address < (block + size)))
break;
}
/* Set the result to the offset in this segment and add the sizes
of all predecessor segments. */
result = address - block;
if (trailer == 0)
{
return result;
}
do
{
if (trailer->this_size <= 0)
abort ();
result += trailer->this_size;
trailer = (struct stk_trailer *) trailer->link;
}
while (trailer != 0);
/* We are done. Note that if you present a bogus address (one
not in any segment), you will get a different number back, formed
from subtracting the address of the first block. This is probably
not what you want. */
return (result);
}
#else /* not CRAY2 */
/* Stack address function for a CRAY-1, CRAY X-MP, or CRAY Y-MP.
Determine the number of the cell within the stack,
given the address of the cell. The purpose of this
routine is to linearize, in some sense, stack addresses
for alloca. */
static long
i00afunc (long address)
{
long stkl = 0;
long size, pseg, this_segment, stack;
long result = 0;
struct stack_segment_linkage *ssptr;
/* Register B67 contains the address of the end of the
current stack segment. If you (as a subprogram) store
your registers on the stack and find that you are past
the contents of B67, you have overflowed the segment.
B67 also points to the stack segment linkage control
area, which is what we are really interested in. */
/* This might be _getb67() or GETB67 () or getb67 () */
stkl = CRAY_STACKSEG_END ();
ssptr = (struct stack_segment_linkage *) stkl;
/* If one subtracts 'size' from the end of the segment,
one has the address of the first word of the segment.
If this is not the first segment, 'pseg' will be
nonzero. */
pseg = ssptr->sspseg;
size = ssptr->sssize;
this_segment = stkl - size;
/* It is possible that calling this routine itself caused
a stack overflow. Discard stack segments which do not
contain the target address. */
while (!(this_segment <= address && address <= stkl))
{
#ifdef DEBUG_I00AFUNC
fprintf (stderr, "%011o %011o %011o\n", this_segment, address, stkl);
#endif
if (pseg == 0)
break;
stkl = stkl - pseg;
ssptr = (struct stack_segment_linkage *) stkl;
size = ssptr->sssize;
pseg = ssptr->sspseg;
this_segment = stkl - size;
}
result = address - this_segment;
/* If you subtract pseg from the current end of the stack,
you get the address of the previous stack segment's end.
This seems a little convoluted to me, but I'll bet you save
a cycle somewhere. */
while (pseg != 0)
{
#ifdef DEBUG_I00AFUNC
fprintf (stderr, "%011o %011o\n", pseg, size);
#endif
stkl = stkl - pseg;
ssptr = (struct stack_segment_linkage *) stkl;
size = ssptr->sssize;
pseg = ssptr->sspseg;
result += size;
}
return (result);
}
#endif /* not CRAY2 */
#endif /* CRAY && CRAY_STACKSEG_END */
#endif /* no alloca */
#endif /* !__GNUC__ || __GNUC__ < 2 */

49
lib/malloc/getpagesize.h Normal file
View file

@ -0,0 +1,49 @@
/* Emulation of getpagesize() for systems that need it.
Copyright (C) 1991 Free Software Foundation, Inc.
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */
#if defined (HAVE_UNISTD_H)
# include <unistd.h>
# if defined (_SC_PAGESIZE)
# define getpagesize() sysconf(_SC_PAGESIZE)
# endif /* _SC_PAGESIZE */
#endif
#if !defined (getpagesize)
# include <sys/param.h>
# if defined (PAGESIZE)
# define getpagesize() PAGESIZE
# else /* !PAGESIZE */
# if defined (EXEC_PAGESIZE)
# define getpagesize() EXEC_PAGESIZE
# else /* !EXEC_PAGESIZE */
# if defined (NBPG)
# if !defined (CLSIZE)
# define CLSIZE 1
# endif /* !CLSIZE */
# define getpagesize() (NBPG * CLSIZE)
# else /* !NBPG */
# if defined (NBPC)
# define getpagesize() NBPC
# endif /* NBPC */
# endif /* !NBPG */
# endif /* !EXEC_PAGESIZE */
# endif /* !PAGESIZE */
#endif /* !getpagesize */
#if !defined (getpagesize)
# define getpagesize() 4096 /* Just punt and use reasonable value */
#endif

16
lib/malloc/i386-alloca.s Normal file
View file

@ -0,0 +1,16 @@
.file "alloca.s"
.text
.align 4
.def alloca; .val alloca; .scl 2; .type 044; .endef
.globl alloca
alloca:
popl %edx
popl %eax
addl $3,%eax
andl $0xfffffffc,%eax
subl %eax,%esp
movl %esp,%eax
pushl %eax
pushl %edx
ret
.def alloca; .val .; .scl -1; .endef

668
lib/malloc/malloc.c Normal file
View file

@ -0,0 +1,668 @@
/* dynamic memory allocation for GNU. */
/* Copyright (C) 1985, 1987 Free Software Foundation, Inc.
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 1, or (at your option)
any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
In other words, you are welcome to use, share and improve this program.
You are forbidden to forbid anyone else to use, share and improve
what you give them. Help stamp out software-hoarding! */
/*
* @(#)nmalloc.c 1 (Caltech) 2/21/82
*
* U of M Modified: 20 Jun 1983 ACT: strange hacks for Emacs
*
* Nov 1983, Mike@BRL, Added support for 4.1C/4.2 BSD.
*
* This is a very fast storage allocator. It allocates blocks of a small
* number of different sizes, and keeps free lists of each size. Blocks
* that don't exactly fit are passed up to the next larger size. In this
* implementation, the available sizes are (2^n)-4 (or -16) bytes long.
* This is designed for use in a program that uses vast quantities of
* memory, but bombs when it runs out. To make it a little better, it
* warns the user when he starts to get near the end.
*
* June 84, ACT: modified rcheck code to check the range given to malloc,
* rather than the range determined by the 2-power used.
*
* Jan 85, RMS: calls malloc_warning to issue warning on nearly full.
* No longer Emacs-specific; can serve as all-purpose malloc for GNU.
* You should call malloc_init to reinitialize after loading dumped Emacs.
* Call malloc_stats to get info on memory stats if MSTATS turned on.
* realloc knows how to return same block given, just changing its size,
* if the power of 2 is correct.
*/
/*
* nextf[i] is the pointer to the next free block of size 2^(i+3). The
* smallest allocatable block is 8 bytes. The overhead information will
* go in the first int of the block, and the returned pointer will point
* to the second.
*
#ifdef MSTATS
* nmalloc[i] is the difference between the number of mallocs and frees
* for a given block size.
#endif
*/
#if defined (emacs) || defined (HAVE_CONFIG_H)
# include "config.h"
#endif /* emacs */
#if !defined (USG)
# if defined (HPUX) || defined (UnixPC) || defined (Xenix)
# define USG
# endif /* HPUX || UnixPC || Xenix */
#endif /* !USG */
/* Determine which kind of system this is. */
#include <sys/types.h>
#include <signal.h>
#if !defined (USG) && !defined (USGr4)
# ifndef SIGTSTP
# ifndef USG
# define USG
# endif /* !USG */
# else /* SIGTSTP */
# ifdef SIGIO
# define BSD4_2
# endif /* SIGIO */
# endif /* SIGTSTP */
#endif /* !USG && !USGr4 */
#ifndef BSD4_2
/* Define getpagesize () if the system does not. */
# include "getpagesize.h"
#endif
#if defined (HAVE_RESOURCE)
# include <sys/time.h>
# include <sys/resource.h>
#endif /* HAVE_RESOURCE */
/* Check for the needed symbols. If they aren't present, this
system's <sys/resource.h> isn't very useful to us. */
#if !defined (RLIMIT_DATA)
# undef HAVE_RESOURCE
#endif
#define start_of_data() &etext
#define ISALLOC ((char) 0xf7) /* magic byte that implies allocation */
#define ISFREE ((char) 0x54) /* magic byte that implies free block */
/* this is for error checking only */
#define ISMEMALIGN ((char) 0xd6) /* Stored before the value returned by
memalign, with the rest of the word
being the distance to the true
beginning of the block. */
extern char etext;
#if !defined (NO_SBRK_DECL)
extern char *sbrk ();
#endif /* !NO_SBRK_DECL */
/* These two are for user programs to look at, when they are interested. */
unsigned int malloc_sbrk_used; /* amount of data space used now */
unsigned int malloc_sbrk_unused; /* amount more we can have */
/* start of data space; can be changed by calling init_malloc */
static char *data_space_start;
static void get_lim_data ();
#ifdef MSTATS
static int nmalloc[30];
static int nmal, nfre;
#endif /* MSTATS */
/* If range checking is not turned on, all we have is a flag indicating
whether memory is allocated, an index in nextf[], and a size field; to
realloc() memory we copy either size bytes or 1<<(index+3) bytes depending
on whether the former can hold the exact size (given the value of
'index'). If range checking is on, we always need to know how much space
is allocated, so the 'size' field is never used. */
struct mhead {
char mh_alloc; /* ISALLOC or ISFREE */
char mh_index; /* index in nextf[] */
/* Remainder are valid only when block is allocated */
unsigned short mh_size; /* size, if < 0x10000 */
#ifdef rcheck
unsigned mh_nbytes; /* number of bytes allocated */
int mh_magic4; /* should be == MAGIC4 */
#endif /* rcheck */
};
/* Access free-list pointer of a block.
It is stored at block + 4.
This is not a field in the mhead structure
because we want sizeof (struct mhead)
to describe the overhead for when the block is in use,
and we do not want the free-list pointer to count in that. */
#define CHAIN(a) \
(*(struct mhead **) (sizeof (char *) + (char *) (a)))
#ifdef rcheck
# include <stdio.h>
# if !defined (botch)
# define botch(x) abort ()
# endif /* botch */
# if !defined (__STRING)
# if defined (__STDC__)
# define __STRING(x) #x
# else
# define __STRING(x) "x"
# endif
# endif
/* To implement range checking, we write magic values in at the beginning
and end of each allocated block, and make sure they are undisturbed
whenever a free or a realloc occurs. */
/* Written in each of the 4 bytes following the block's real space */
# define MAGIC1 0x55
/* Written in the 4 bytes before the block's real space */
# define MAGIC4 0x55555555
# define ASSERT(p) if (!(p)) botch(__STRING(p)); else
# define EXTRA 4 /* 4 bytes extra for MAGIC1s */
#else /* !rcheck */
# define ASSERT(p)
# define EXTRA 0
#endif /* rcheck */
/* nextf[i] is free list of blocks of size 2**(i + 3) */
static struct mhead *nextf[30];
/* busy[i] is nonzero while allocation of block size i is in progress. */
static char busy[30];
/* Number of bytes of writable memory we can expect to be able to get */
static unsigned int lim_data;
/* Level number of warnings already issued.
0 -- no warnings issued.
1 -- 75% warning already issued.
2 -- 85% warning already issued.
*/
static int warnlevel;
/* Function to call to issue a warning;
0 means don't issue them. */
static void (*warnfunction) ();
/* nonzero once initial bunch of free blocks made */
static int gotpool;
char *_malloc_base;
static void getpool ();
/* Cause reinitialization based on job parameters;
also declare where the end of pure storage is. */
void
malloc_init (start, warnfun)
char *start;
void (*warnfun) ();
{
if (start)
data_space_start = start;
lim_data = 0;
warnlevel = 0;
warnfunction = warnfun;
}
/* Return the maximum size to which MEM can be realloc'd
without actually requiring copying. */
int
malloc_usable_size (mem)
char *mem;
{
int blocksize = 8 << (((struct mhead *) mem) - 1) -> mh_index;
return blocksize - sizeof (struct mhead) - EXTRA;
}
static void
morecore (nu) /* ask system for more memory */
register int nu; /* size index to get more of */
{
register char *cp;
register int nblks;
register unsigned int siz;
int oldmask;
#if defined (BSD4_2)
oldmask = sigsetmask (-1);
#endif /* BSD4_2 */
if (!data_space_start)
{
data_space_start = start_of_data ();
}
if (lim_data == 0)
get_lim_data ();
/* On initial startup, get two blocks of each size up to 1k bytes */
if (!gotpool)
{ getpool (); getpool (); gotpool = 1; }
/* Find current end of memory and issue warning if getting near max */
cp = sbrk (0);
siz = cp - data_space_start;
malloc_sbrk_used = siz;
malloc_sbrk_unused = lim_data - siz;
if (warnfunction)
switch (warnlevel)
{
case 0:
if (siz > (lim_data / 4) * 3)
{
warnlevel++;
(*warnfunction) ("Warning: past 75% of memory limit");
}
break;
case 1:
if (siz > (lim_data / 20) * 17)
{
warnlevel++;
(*warnfunction) ("Warning: past 85% of memory limit");
}
break;
case 2:
if (siz > (lim_data / 20) * 19)
{
warnlevel++;
(*warnfunction) ("Warning: past 95% of memory limit");
}
break;
}
if ((int) cp & 0x3ff) /* land on 1K boundaries */
sbrk (1024 - ((int) cp & 0x3ff));
/* Take at least 2k, and figure out how many blocks of the desired size
we're about to get */
nblks = 1;
if ((siz = nu) < 8)
nblks = 1 << ((siz = 8) - nu);
if ((cp = sbrk (1 << (siz + 3))) == (char *) -1)
return; /* no more room! */
if ((int) cp & 7)
{ /* shouldn't happen, but just in case */
cp = (char *) (((int) cp + 8) & ~7);
nblks--;
}
/* save new header and link the nblks blocks together */
nextf[nu] = (struct mhead *) cp;
siz = 1 << (nu + 3);
while (1)
{
((struct mhead *) cp) -> mh_alloc = ISFREE;
((struct mhead *) cp) -> mh_index = nu;
if (--nblks <= 0) break;
CHAIN ((struct mhead *) cp) = (struct mhead *) (cp + siz);
cp += siz;
}
CHAIN ((struct mhead *) cp) = 0;
#if defined (BSD4_2)
sigsetmask (oldmask);
#endif /* BSD4_2 */
}
static void
getpool ()
{
register int nu;
register char *cp = sbrk (0);
if ((int) cp & 0x3ff) /* land on 1K boundaries */
sbrk (1024 - ((int) cp & 0x3ff));
/* Record address of start of space allocated by malloc. */
if (_malloc_base == 0)
_malloc_base = cp;
/* Get 2k of storage */
cp = sbrk (04000);
if (cp == (char *) -1)
return;
/* Divide it into an initial 8-word block
plus one block of size 2**nu for nu = 3 ... 10. */
CHAIN (cp) = nextf[0];
nextf[0] = (struct mhead *) cp;
((struct mhead *) cp) -> mh_alloc = ISFREE;
((struct mhead *) cp) -> mh_index = 0;
cp += 8;
for (nu = 0; nu < 7; nu++)
{
CHAIN (cp) = nextf[nu];
nextf[nu] = (struct mhead *) cp;
((struct mhead *) cp) -> mh_alloc = ISFREE;
((struct mhead *) cp) -> mh_index = nu;
cp += 8 << nu;
}
}
char *
malloc (n) /* get a block */
unsigned n;
{
register struct mhead *p;
register unsigned int nbytes;
register int nunits = 0;
/* Figure out how many bytes are required, rounding up to the nearest
multiple of 4, then figure out which nextf[] area to use */
nbytes = (n + sizeof *p + EXTRA + 3) & ~3;
{
register unsigned int shiftr = (nbytes - 1) >> 2;
while (shiftr >>= 1)
nunits++;
}
/* In case this is reentrant use of malloc from signal handler,
pick a block size that no other malloc level is currently
trying to allocate. That's the easiest harmless way not to
interfere with the other level of execution. */
while (busy[nunits]) nunits++;
busy[nunits] = 1;
/* If there are no blocks of the appropriate size, go get some */
/* COULD SPLIT UP A LARGER BLOCK HERE ... ACT */
if (nextf[nunits] == 0)
morecore (nunits);
/* Get one block off the list, and set the new list head */
if ((p = nextf[nunits]) == 0)
{
busy[nunits] = 0;
return 0;
}
nextf[nunits] = CHAIN (p);
busy[nunits] = 0;
/* Check for free block clobbered */
/* If not for this check, we would gobble a clobbered free chain ptr */
/* and bomb out on the NEXT allocate of this size block */
if (p -> mh_alloc != ISFREE || p -> mh_index != nunits)
#ifdef rcheck
botch ("block on free list clobbered");
#else /* not rcheck */
abort ();
#endif /* not rcheck */
/* Fill in the info, and if range checking, set up the magic numbers */
p -> mh_alloc = ISALLOC;
#ifdef rcheck
p -> mh_nbytes = n;
p -> mh_magic4 = MAGIC4;
{
register char *m = (char *) (p + 1) + n;
*m++ = MAGIC1, *m++ = MAGIC1, *m++ = MAGIC1, *m = MAGIC1;
}
#else /* not rcheck */
p -> mh_size = n;
#endif /* not rcheck */
#ifdef MSTATS
nmalloc[nunits]++;
nmal++;
#endif /* MSTATS */
return (char *) (p + 1);
}
void
free (mem)
char *mem;
{
register struct mhead *p;
{
register char *ap = mem;
if (ap == 0)
return;
p = (struct mhead *) ap - 1;
if (p -> mh_alloc == ISMEMALIGN)
{
#ifdef rcheck
ap -= p->mh_nbytes;
#endif
p = (struct mhead *) ap - 1;
}
#ifndef rcheck
if (p -> mh_alloc != ISALLOC)
abort ();
#else /* rcheck */
if (p -> mh_alloc != ISALLOC)
{
if (p -> mh_alloc == ISFREE)
botch ("free: Called with already freed block argument\n");
else
botch ("free: Called with bad argument\n");
}
ASSERT (p -> mh_magic4 == MAGIC4);
ap += p -> mh_nbytes;
ASSERT (*ap++ == MAGIC1); ASSERT (*ap++ == MAGIC1);
ASSERT (*ap++ == MAGIC1); ASSERT (*ap == MAGIC1);
#endif /* rcheck */
}
{
register int nunits = p -> mh_index;
ASSERT (nunits <= 29);
p -> mh_alloc = ISFREE;
/* Protect against signal handlers calling malloc. */
busy[nunits] = 1;
/* Put this block on the free list. */
CHAIN (p) = nextf[nunits];
nextf[nunits] = p;
busy[nunits] = 0;
#ifdef MSTATS
nmalloc[nunits]--;
nfre++;
#endif /* MSTATS */
}
}
char *
realloc (mem, n)
char *mem;
register unsigned n;
{
register struct mhead *p;
register unsigned int tocopy;
register unsigned int nbytes;
register int nunits;
if ((p = (struct mhead *) mem) == 0)
return malloc (n);
p--;
nunits = p -> mh_index;
ASSERT (p -> mh_alloc == ISALLOC);
#ifdef rcheck
ASSERT (p -> mh_magic4 == MAGIC4);
{
register char *m = mem + (tocopy = p -> mh_nbytes);
ASSERT (*m++ == MAGIC1); ASSERT (*m++ == MAGIC1);
ASSERT (*m++ == MAGIC1); ASSERT (*m == MAGIC1);
}
#else /* not rcheck */
if (p -> mh_index >= 13)
tocopy = (1 << (p -> mh_index + 3)) - sizeof *p;
else
tocopy = p -> mh_size;
#endif /* not rcheck */
/* See if desired size rounds to same power of 2 as actual size. */
nbytes = (n + sizeof *p + EXTRA + 7) & ~7;
/* If ok, use the same block, just marking its size as changed. */
if (nbytes > (4 << nunits) && nbytes <= (8 << nunits))
{
#ifdef rcheck
register char *m = mem + tocopy;
*m++ = 0; *m++ = 0; *m++ = 0; *m++ = 0;
p-> mh_nbytes = n;
m = mem + n;
*m++ = MAGIC1; *m++ = MAGIC1; *m++ = MAGIC1; *m++ = MAGIC1;
#else /* not rcheck */
p -> mh_size = n;
#endif /* not rcheck */
return mem;
}
if (n < tocopy)
tocopy = n;
{
register char *new;
if ((new = malloc (n)) == 0)
return 0;
bcopy (mem, new, tocopy);
free (mem);
return new;
}
}
char *
memalign (alignment, size)
unsigned alignment, size;
{
register char *ptr = malloc (size + alignment);
register char *aligned;
register struct mhead *p;
if (ptr == 0)
return 0;
/* If entire block has the desired alignment, just accept it. */
if (((int) ptr & (alignment - 1)) == 0)
return ptr;
/* Otherwise, get address of byte in the block that has that alignment. */
aligned = (char *) (((int) ptr + alignment - 1) & -alignment);
/* Store a suitable indication of how to free the block,
so that free can find the true beginning of it. */
p = (struct mhead *) aligned - 1;
p -> mh_size = aligned - ptr;
p -> mh_alloc = ISMEMALIGN;
return aligned;
}
#if !defined (HPUX) && !defined (Multimax) && !defined (Multimax32k)
/* This runs into trouble with getpagesize on HPUX, and Multimax machines.
Patching out seems cleaner than the ugly fix needed. */
char *
valloc (size)
{
return memalign (getpagesize (), size);
}
#endif /* !HPUX && !Multimax && !Multimax32k */
#ifdef MSTATS
/* Return statistics describing allocation of blocks of size 2**n. */
struct mstats_value
{
int blocksize;
int nfree;
int nused;
};
struct mstats_value
malloc_stats (size)
int size;
{
struct mstats_value v;
register int i;
register struct mhead *p;
v.nfree = 0;
if (size < 0 || size >= 30)
{
v.blocksize = 0;
v.nused = 0;
return v;
}
v.blocksize = 1 << (size + 3);
v.nused = nmalloc[size];
for (p = nextf[size]; p; p = CHAIN (p))
v.nfree++;
return v;
}
#endif /* MSTATS */
/*
* This function returns the total number of bytes that the process
* will be allowed to allocate via the sbrk(2) system call. On
* BSD systems this is the total space allocatable to stack and
* data. On USG systems this is the data space only.
*/
#if !defined (HAVE_RESOURCE)
extern long ulimit ();
static void
get_lim_data ()
{
lim_data = ulimit (3, 0);
lim_data -= (long) data_space_start;
}
#else /* HAVE_RESOURCE */
static void
get_lim_data ()
{
struct rlimit XXrlimit;
getrlimit (RLIMIT_DATA, &XXrlimit);
#ifdef RLIM_INFINITY
lim_data = XXrlimit.rlim_cur & RLIM_INFINITY; /* soft limit */
#else
lim_data = XXrlimit.rlim_cur; /* soft limit */
#endif
}
#endif /* HAVE_RESOURCE */

63
lib/malloc/x386-alloca.s Normal file
View file

@ -0,0 +1,63 @@
;; alloca386.s 1.2
;; GNU-compatible stack allocation function for Xenix/386.
;; Written by Chip Salzenberg at ComDev.
;; Last modified 90/01/11
;;> Is your alloca clearly better than the one in i386-alloca.s? I haven't
;;> looked at either.
;;
;;They're different because Xenix/386 has a different assembler. SCO
;;Xenix has the Microsoft C compiler and the Microsoft macro assembler,
;;called "masm". MASM's assembler syntax is quite different from AT&T's
;;in all sorts of ways. Xenix people can't use the AT&T version.
;;--
;;Chip Salzenberg at ComDev/TCT <chip@tct.uucp>, <uunet!ateng!tct!chip>
TITLE $alloca386
.386
DGROUP GROUP CONST, _BSS, _DATA
_DATA SEGMENT DWORD USE32 PUBLIC 'DATA'
_DATA ENDS
_BSS SEGMENT DWORD USE32 PUBLIC 'BSS'
_BSS ENDS
CONST SEGMENT DWORD USE32 PUBLIC 'CONST'
CONST ENDS
_TEXT SEGMENT DWORD USE32 PUBLIC 'CODE'
ASSUME CS: _TEXT, DS: DGROUP, SS: DGROUP, ES: DGROUP
PUBLIC _alloca
_alloca PROC NEAR
; Get argument.
pop edx ; edx -> return address
pop eax ; eax = amount to allocate
; Validate allocation amount.
add eax,3
and eax,not 3
cmp eax,0
jg aa_size_ok
mov eax,4
aa_size_ok:
; Allocate stack space.
mov ecx,esp ; ecx -> old stack pointer
sub esp,eax ; perform allocation
mov eax,esp ; eax -> new stack pointer
; Copy the three saved register variables from old stack top to new stack top.
; They may not be there. So we waste twelve bytes. Big fat hairy deal.
push DWORD PTR 8[ecx]
push DWORD PTR 4[ecx]
push DWORD PTR 0[ecx]
; Push something so the caller can pop it off.
push eax
; Return to caller.
jmp edx
_alloca ENDP
_TEXT ENDS
END

78
lib/malloc/xmalloc.c Normal file
View file

@ -0,0 +1,78 @@
/* xmalloc.c -- safe versions of malloc and realloc */
/* Copyright (C) 1991 Free Software Foundation, Inc.
This file is part of GNU Readline, a library for reading lines
of text with interactive input and history editing.
Readline is free software; you can redistribute it and/or modify it
under the terms of the GNU General Public License as published by the
Free Software Foundation; either version 1, or (at your option) any
later version.
Readline is distributed in the hope that it will be useful, but
WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
General Public License for more details.
You should have received a copy of the GNU General Public License
along with Readline; see the file COPYING. If not, write to the Free
Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA. */
#if defined (ALREADY_HAVE_XMALLOC)
#else
#include <stdio.h>
#if defined (HAVE_STDLIB_H)
# include <stdlib.h>
#else
# include "ansi_stdlib.h"
#endif /* HAVE_STDLIB_H */
static void memory_error_and_abort ();
/* **************************************************************** */
/* */
/* Memory Allocation and Deallocation. */
/* */
/* **************************************************************** */
/* Return a pointer to free()able block of memory large enough
to hold BYTES number of bytes. If the memory cannot be allocated,
print an error message and abort. */
char *
xmalloc (bytes)
int bytes;
{
char *temp = (char *)malloc (bytes);
if (!temp)
memory_error_and_abort ("xmalloc");
return (temp);
}
char *
xrealloc (pointer, bytes)
char *pointer;
int bytes;
{
char *temp;
if (!pointer)
temp = (char *)malloc (bytes);
else
temp = (char *)realloc (pointer, bytes);
if (!temp)
memory_error_and_abort ("xrealloc");
return (temp);
}
static void
memory_error_and_abort (fname)
char *fname;
{
fprintf (stderr, "%s: Out of virtual memory!\n", fname);
abort ();
}
#endif /* !ALREADY_HAVE_XMALLOC */

53
lib/malloclib/Makefile Normal file
View file

@ -0,0 +1,53 @@
# Copyright (C) 1991 Free Software Foundation, Inc.
# This file is part of the GNU C Library.
# The GNU C Library is free software; you can redistribute it and/or
# modify it under the terms of the GNU Library General Public License
# as published by the Free Software Foundation; either version 2 of
# the License, or (at your option) any later version.
# The GNU C Library is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
# Library General Public License for more details.
# You should have received a copy of the GNU Library General Public
# License along with the GNU C Library; see the file COPYING.LIB. If
# not, write to the Free Software Foundation, Inc., 675 Mass Ave,
# Cambridge, MA 02139, USA.
# Makefile for standalone distribution of malloc.
srcdir = .
VPATH = .:$(srcdir)
all: libmalloc.a
sources = calloc.c cfree.c free.c malloc.c mcheck.c morecore.c \
memalign.c mstats.c mtrace.c realloc.c valloc.c
objects = calloc.o cfree.o free.o malloc.o mcheck.o morecore.o \
memalign.o mstats.o mtrace.o realloc.o valloc.o
headers = malloc.h getpagesize.h
libmalloc.a: $(objects)
ar crv $@ $(objects)
ranlib $@
.c.o:
$(CC) $(CFLAGS) $(CPPFLAGS) -I. -c $< $(OUTPUT_OPTION)
.PHONY: clean realclean malloc-clean malloc-realclean
clean malloc-clean:
-rm -f libmalloc.a $(objects) core
realclean malloc-realclean: clean
-rm -f TAGS tags *~
calloc.o: malloc.h
free.o: malloc.h
malloc.o: malloc.h
mcheck.o: malloc.h
memalign.o: malloc.h
mstats.o: malloc.h
mtrace.o: malloc.h
realloc.o: malloc.h
valloc.o: malloc.h getpagesize.h

189
lib/malloclib/alloca.c Normal file
View file

@ -0,0 +1,189 @@
/* alloca -- (mostly) portable public-domain implementation -- D A Gwyn
last edit: 86/05/30 rms
include config.h, since on VMS it renames some symbols.
Use xmalloc instead of malloc.
This implementation of the PWB library alloca() function,
which is used to allocate space off the run-time stack so
that it is automatically reclaimed upon procedure exit,
was inspired by discussions with J. Q. Johnson of Cornell.
It should work under any C implementation that uses an
actual procedure stack (as opposed to a linked list of
frames). There are some preprocessor constants that can
be defined when compiling for your specific system, for
improved efficiency; however, the defaults should be okay.
The general concept of this implementation is to keep
track of all alloca()-allocated blocks, and reclaim any
that are found to be deeper in the stack than the current
invocation. This heuristic does not reclaim storage as
soon as it becomes invalid, but it will do so eventually.
As a special case, alloca(0) reclaims storage without
allocating any. It is a good idea to use alloca(0) in
your main control loop, etc. to force garbage collection.
*/
#ifndef lint
static char SCCSid[] = "@(#)alloca.c 1.1"; /* for the "what" utility */
#endif
#ifdef emacs
#include "config.h"
#ifdef static
/* actually, only want this if static is defined as ""
-- this is for usg, in which emacs must undefine static
in order to make unexec workable
*/
#ifndef STACK_DIRECTION
you
lose
-- must know STACK_DIRECTION at compile-time
#endif /* STACK_DIRECTION undefined */
#endif /* static */
#endif /* emacs */
#ifdef X3J11
typedef void *pointer; /* generic pointer type */
#else
typedef char *pointer; /* generic pointer type */
#endif /* X3J11 */
#define NULL 0 /* null pointer constant */
extern void free();
extern pointer xmalloc();
/*
Define STACK_DIRECTION if you know the direction of stack
growth for your system; otherwise it will be automatically
deduced at run-time.
STACK_DIRECTION > 0 => grows toward higher addresses
STACK_DIRECTION < 0 => grows toward lower addresses
STACK_DIRECTION = 0 => direction of growth unknown
*/
#ifndef STACK_DIRECTION
#define STACK_DIRECTION 0 /* direction unknown */
#endif
#if STACK_DIRECTION != 0
#define STACK_DIR STACK_DIRECTION /* known at compile-time */
#else /* STACK_DIRECTION == 0; need run-time code */
static int stack_dir; /* 1 or -1 once known */
#define STACK_DIR stack_dir
static void
find_stack_direction (/* void */)
{
static char *addr = NULL; /* address of first
`dummy', once known */
auto char dummy; /* to get stack address */
if (addr == NULL)
{ /* initial entry */
addr = &dummy;
find_stack_direction (); /* recurse once */
}
else /* second entry */
if (&dummy > addr)
stack_dir = 1; /* stack grew upward */
else
stack_dir = -1; /* stack grew downward */
}
#endif /* STACK_DIRECTION == 0 */
/*
An "alloca header" is used to:
(a) chain together all alloca()ed blocks;
(b) keep track of stack depth.
It is very important that sizeof(header) agree with malloc()
alignment chunk size. The following default should work okay.
*/
#ifndef ALIGN_SIZE
#define ALIGN_SIZE sizeof(double)
#endif
typedef union hdr
{
char align[ALIGN_SIZE]; /* to force sizeof(header) */
struct
{
union hdr *next; /* for chaining headers */
char *deep; /* for stack depth measure */
} h;
} header;
/*
alloca( size ) returns a pointer to at least `size' bytes of
storage which will be automatically reclaimed upon exit from
the procedure that called alloca(). Originally, this space
was supposed to be taken from the current stack frame of the
caller, but that method cannot be made to work for some
implementations of C, for example under Gould's UTX/32.
*/
static header *last_alloca_header = NULL; /* -> last alloca header */
pointer
alloca (size) /* returns pointer to storage */
unsigned size; /* # bytes to allocate */
{
auto char probe; /* probes stack depth: */
register char *depth = &probe;
#if STACK_DIRECTION == 0
if (STACK_DIR == 0) /* unknown growth direction */
find_stack_direction ();
#endif
/* Reclaim garbage, defined as all alloca()ed storage that
was allocated from deeper in the stack than currently. */
{
register header *hp; /* traverses linked list */
for (hp = last_alloca_header; hp != NULL;)
if (STACK_DIR > 0 && hp->h.deep > depth
|| STACK_DIR < 0 && hp->h.deep < depth)
{
register header *np = hp->h.next;
free ((pointer) hp); /* collect garbage */
hp = np; /* -> next header */
}
else
break; /* rest are not deeper */
last_alloca_header = hp; /* -> last valid storage */
}
if (size == 0)
return NULL; /* no allocation required */
/* Allocate combined header + user data storage. */
{
register pointer new = xmalloc (sizeof (header) + size);
/* address of header */
((header *)new)->h.next = last_alloca_header;
((header *)new)->h.deep = depth;
last_alloca_header = (header *)new;
/* User storage begins just after header. */
return (pointer)((char *)new + sizeof(header));
}
}

39
lib/malloclib/calloc.c Normal file
View file

@ -0,0 +1,39 @@
/* Copyright (C) 1991, 1992 Free Software Foundation, Inc.
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public License as
published by the Free Software Foundation; either version 2 of the
License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; see the file COPYING.LIB. If
not, write to the Free Software Foundation, Inc., 675 Mass Ave,
Cambridge, MA 02139, USA.
The author may be reached (Email) at the address mike@ai.mit.edu,
or (US mail) as Mike Haertel c/o Free Software Foundation. */
#ifndef _MALLOC_INTERNAL
#define _MALLOC_INTERNAL
#include <malloc.h>
#endif
/* Allocate an array of NMEMB elements each SIZE bytes long.
The entire array is initialized to zeros. */
__ptr_t
calloc (nmemb, size)
register size_t nmemb;
register size_t size;
{
register __ptr_t result = malloc (nmemb * size);
if (result != NULL)
(void) memset (result, 0, nmemb * size);
return result;
}

43
lib/malloclib/cfree.c Normal file
View file

@ -0,0 +1,43 @@
/* Copyright (C) 1991, 1993 Free Software Foundation, Inc.
This file is part of the GNU C Library.
The GNU C Library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public License as
published by the Free Software Foundation; either version 2 of the
License, or (at your option) any later version.
The GNU C Library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with the GNU C Library; see the file COPYING.LIB. If
not, write to the Free Software Foundation, Inc., 675 Mass Ave,
Cambridge, MA 02139, USA. */
#ifndef _MALLOC_INTERNAL
#define _MALLOC_INTERNAL
#include <malloc.h>
#endif
#undef cfree
#ifdef _LIBC
#include <ansidecl.h>
#include <gnu-stabs.h>
function_alias(cfree, free, void, (ptr),
DEFUN(cfree, (ptr), PTR ptr))
#else
void
cfree (ptr)
__ptr_t ptr;
{
free (ptr);
}
#endif

212
lib/malloclib/free.c Normal file
View file

@ -0,0 +1,212 @@
/* Free a block of memory allocated by `malloc'.
Copyright 1990, 1991, 1992 Free Software Foundation
Written May 1989 by Mike Haertel.
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public License as
published by the Free Software Foundation; either version 2 of the
License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; see the file COPYING.LIB. If
not, write to the Free Software Foundation, Inc., 675 Mass Ave,
Cambridge, MA 02139, USA.
The author may be reached (Email) at the address mike@ai.mit.edu,
or (US mail) as Mike Haertel c/o Free Software Foundation. */
#ifndef _MALLOC_INTERNAL
#define _MALLOC_INTERNAL
#include <malloc.h>
#endif
/* Debugging hook for free. */
void (*__free_hook) __P ((__ptr_t __ptr));
/* List of blocks allocated by memalign. */
struct alignlist *_aligned_blocks = NULL;
/* Return memory to the heap.
Like `free' but don't call a __free_hook if there is one. */
void
_free_internal (ptr)
__ptr_t ptr;
{
int type;
size_t block, blocks;
register size_t i;
struct list *prev, *next;
block = BLOCK (ptr);
type = _heapinfo[block].busy.type;
switch (type)
{
case 0:
/* Get as many statistics as early as we can. */
--_chunks_used;
_bytes_used -= _heapinfo[block].busy.info.size * BLOCKSIZE;
_bytes_free += _heapinfo[block].busy.info.size * BLOCKSIZE;
/* Find the free cluster previous to this one in the free list.
Start searching at the last block referenced; this may benefit
programs with locality of allocation. */
i = _heapindex;
if (i > block)
while (i > block)
i = _heapinfo[i].free.prev;
else
{
do
i = _heapinfo[i].free.next;
while (i > 0 && i < block);
i = _heapinfo[i].free.prev;
}
/* Determine how to link this block into the free list. */
if (block == i + _heapinfo[i].free.size)
{
/* Coalesce this block with its predecessor. */
_heapinfo[i].free.size += _heapinfo[block].busy.info.size;
block = i;
}
else
{
/* Really link this block back into the free list. */
_heapinfo[block].free.size = _heapinfo[block].busy.info.size;
_heapinfo[block].free.next = _heapinfo[i].free.next;
_heapinfo[block].free.prev = i;
_heapinfo[i].free.next = block;
_heapinfo[_heapinfo[block].free.next].free.prev = block;
++_chunks_free;
}
/* Now that the block is linked in, see if we can coalesce it
with its successor (by deleting its successor from the list
and adding in its size). */
if (block + _heapinfo[block].free.size == _heapinfo[block].free.next)
{
_heapinfo[block].free.size
+= _heapinfo[_heapinfo[block].free.next].free.size;
_heapinfo[block].free.next
= _heapinfo[_heapinfo[block].free.next].free.next;
_heapinfo[_heapinfo[block].free.next].free.prev = block;
--_chunks_free;
}
/* Now see if we can return stuff to the system. */
blocks = _heapinfo[block].free.size;
if (blocks >= FINAL_FREE_BLOCKS && block + blocks == _heaplimit
&& (*__morecore) (0) == ADDRESS (block + blocks))
{
register size_t bytes = blocks * BLOCKSIZE;
_heaplimit -= blocks;
(*__morecore) (-bytes);
_heapinfo[_heapinfo[block].free.prev].free.next
= _heapinfo[block].free.next;
_heapinfo[_heapinfo[block].free.next].free.prev
= _heapinfo[block].free.prev;
block = _heapinfo[block].free.prev;
--_chunks_free;
_bytes_free -= bytes;
}
/* Set the next search to begin at this block. */
_heapindex = block;
break;
default:
/* Do some of the statistics. */
--_chunks_used;
_bytes_used -= 1 << type;
++_chunks_free;
_bytes_free += 1 << type;
/* Get the address of the first free fragment in this block. */
prev = (struct list *) ((char *) ADDRESS (block) +
(_heapinfo[block].busy.info.frag.first << type));
if (_heapinfo[block].busy.info.frag.nfree == (BLOCKSIZE >> type) - 1
&& _fragblocks[type] > 1)
{
/* If all fragments of this block are free, remove them
from the fragment list and free the whole block. */
--_fragblocks[type];
next = prev;
for (i = 1; i < (size_t) (BLOCKSIZE >> type); ++i)
next = next->next;
prev->prev->next = next;
if (next != NULL)
next->prev = prev->prev;
_heapinfo[block].busy.type = 0;
_heapinfo[block].busy.info.size = 1;
/* Keep the statistics accurate. */
++_chunks_used;
_bytes_used += BLOCKSIZE;
_chunks_free -= BLOCKSIZE >> type;
_bytes_free -= BLOCKSIZE;
free (ADDRESS (block));
}
else if (_heapinfo[block].busy.info.frag.nfree != 0)
{
/* If some fragments of this block are free, link this
fragment into the fragment list after the first free
fragment of this block. */
next = (struct list *) ptr;
next->next = prev->next;
next->prev = prev;
prev->next = next;
if (next->next != NULL)
next->next->prev = next;
++_heapinfo[block].busy.info.frag.nfree;
}
else
{
/* No fragments of this block are free, so link this
fragment into the fragment list and announce that
it is the first free fragment of this block. */
prev = (struct list *) ptr;
_heapinfo[block].busy.info.frag.nfree = 1;
_heapinfo[block].busy.info.frag.first = (unsigned long int)
((unsigned long int) ((char *) ptr - (char *) NULL)
% BLOCKSIZE >> type);
prev->next = _fraghead[type].next;
prev->prev = &_fraghead[type];
prev->prev->next = prev;
if (prev->next != NULL)
prev->next->prev = prev;
}
break;
}
}
/* Return memory to the heap. */
void
free (ptr)
__ptr_t ptr;
{
register struct alignlist *l;
if (ptr == NULL)
return;
for (l = _aligned_blocks; l != NULL; l = l->next)
if (l->aligned == ptr)
{
l->aligned = NULL; /* Mark the slot in the list as free. */
ptr = l->exact;
break;
}
if (__free_hook != NULL)
(*__free_hook) (ptr);
else
_free_internal (ptr);
}

View file

@ -0,0 +1,56 @@
/* Emulation of getpagesize() for systems that need it.
Copyright (C) 1991 Free Software Foundation, Inc.
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */
#if !defined (USG)
extern size_t getpagesize __P ((void));
# if !defined (HAVE_GETPAGESIZE)
# define HAVE_GETPAGESIZE
# endif /* !HAVE_GETPAGESIZE */
#endif /* !USG */
#if !defined (HAVE_GETPAGESIZE) && defined (HAVE_UNISTD_H)
# include <unistd.h>
# if defined (_SC_PAGESIZE)
# define getpagesize() sysconf(_SC_PAGESIZE)
# endif /* _SC_PAGESIZE */
#endif
#if !defined (HAVE_GETPAGESIZE)
# include <sys/param.h>
# if defined (PAGESIZE)
# define getpagesize() PAGESIZE
# else /* !PAGESIZE */
# if defined (EXEC_PAGESIZE)
# define getpagesize() EXEC_PAGESIZE
# else /* !EXEC_PAGESIZE */
# if defined (NBPG)
# if !defined (CLSIZE)
# define CLSIZE 1
# endif /* !CLSIZE */
# define getpagesize() (NBPG * CLSIZE)
# else /* !NBPG */
# if defined (NBPC)
# define getpagesize() NBPC
# endif /* NBPC */
# endif /* !NBPG */
# endif /* !EXEC_PAGESIZE */
# endif /* !PAGESIZE */
#endif /* !getpagesize */
#if !defined (HAVE_GETPAGESIZE) && !defined (getpagesize)
# define getpagesize() 4096 /* Just punt and use reasonable value */
#endif /* !HAVE_GETPAGESIZE && !getpagesize */

View file

@ -0,0 +1,16 @@
.file "alloca.s"
.text
.align 4
.def alloca; .val alloca; .scl 2; .type 044; .endef
.globl alloca
alloca:
popl %edx
popl %eax
addl $3,%eax
andl $0xfffffffc,%eax
subl %eax,%esp
movl %esp,%eax
pushl %eax
pushl %edx
ret
.def alloca; .val .; .scl -1; .endef

324
lib/malloclib/malloc.c Normal file
View file

@ -0,0 +1,324 @@
/* Memory allocator `malloc'.
Copyright 1990, 1991, 1992, 1993 Free Software Foundation
Written May 1989 by Mike Haertel.
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public License as
published by the Free Software Foundation; either version 2 of the
License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; see the file COPYING.LIB. If
not, write to the Free Software Foundation, Inc., 675 Mass Ave,
Cambridge, MA 02139, USA.
The author may be reached (Email) at the address mike@ai.mit.edu,
or (US mail) as Mike Haertel c/o Free Software Foundation. */
#ifndef _MALLOC_INTERNAL
#define _MALLOC_INTERNAL
#include <malloc.h>
#endif
/* How to really get more memory. */
__ptr_t (*__morecore) __P ((ptrdiff_t __size)) = __default_morecore;
/* Debugging hook for `malloc'. */
__ptr_t (*__malloc_hook) __P ((size_t __size));
/* Pointer to the base of the first block. */
char *_heapbase;
/* Block information table. Allocated with align/__free (not malloc/free). */
malloc_info *_heapinfo;
/* Number of info entries. */
static size_t heapsize;
/* Search index in the info table. */
size_t _heapindex;
/* Limit of valid info table indices. */
size_t _heaplimit;
/* Count of large blocks allocated for each fragment size. */
int _fragblocks[BLOCKLOG];
/* Free lists for each fragment size. */
struct list _fraghead[BLOCKLOG];
/* Instrumentation. */
size_t _chunks_used;
size_t _bytes_used;
size_t _chunks_free;
size_t _bytes_free;
/* Are you experienced? */
int __malloc_initialized;
void (*__after_morecore_hook) __P ((void));
/* Aligned allocation. */
static __ptr_t align __P ((size_t));
static __ptr_t
align (size)
size_t size;
{
__ptr_t result;
unsigned long int adj;
result = (*__morecore) (size);
adj = (unsigned long int) ((unsigned long int) ((char *) result -
(char *) NULL)) % BLOCKSIZE;
if (adj != 0)
{
adj = BLOCKSIZE - adj;
(void) (*__morecore) (adj);
result = (char *) result + adj;
}
if (__after_morecore_hook)
(*__after_morecore_hook) ();
return result;
}
/* Set everything up and remember that we have. */
static int initialize __P ((void));
static int
initialize ()
{
heapsize = HEAP / BLOCKSIZE;
_heapinfo = (malloc_info *) align (heapsize * sizeof (malloc_info));
_bytes_used = heapsize * sizeof (malloc_info);
_chunks_used++;
if (_heapinfo == NULL)
return 0;
memset (_heapinfo, 0, heapsize * sizeof (malloc_info));
_heapinfo[0].free.size = 0;
_heapinfo[0].free.next = _heapinfo[0].free.prev = 0;
_heapindex = 0;
_heapbase = (char *) _heapinfo;
__malloc_initialized = 1;
return 1;
}
/* Get neatly aligned memory, initializing or
growing the heap info table as necessary. */
static __ptr_t morecore __P ((size_t));
static __ptr_t
morecore (size)
size_t size;
{
__ptr_t result;
malloc_info *newinfo, *oldinfo;
size_t newsize;
result = align (size);
if (result == NULL)
return NULL;
/* Check if we need to grow the info table. */
if ((size_t) BLOCK ((char *) result + size) > heapsize)
{
newsize = heapsize;
while ((size_t) BLOCK ((char *) result + size) > newsize)
newsize *= 2;
newinfo = (malloc_info *) align (newsize * sizeof (malloc_info));
if (newinfo == NULL)
{
(*__morecore) (-size);
return NULL;
}
_bytes_used += newsize * sizeof (malloc_info);
_chunks_used++;
memset (newinfo, 0, newsize * sizeof (malloc_info));
memcpy (newinfo, _heapinfo, heapsize * sizeof (malloc_info));
oldinfo = _heapinfo;
newinfo[BLOCK (oldinfo)].busy.type = 0;
newinfo[BLOCK (oldinfo)].busy.info.size
= BLOCKIFY (heapsize * sizeof (malloc_info));
_heapinfo = newinfo;
heapsize = newsize;
}
_heaplimit = BLOCK ((char *) result + size);
return result;
}
/* Allocate memory from the heap. */
__ptr_t
malloc (size)
size_t size;
{
__ptr_t result;
size_t block, blocks, lastblocks, start;
register size_t i;
struct list *next;
if (size == 0)
return NULL;
if (__malloc_hook != NULL)
return (*__malloc_hook) (size);
if (!__malloc_initialized)
if (!initialize ())
return NULL;
if (size < sizeof (struct list))
size = sizeof (struct list);
/* Determine the allocation policy based on the request size. */
if (size <= BLOCKSIZE / 2)
{
/* Small allocation to receive a fragment of a block.
Determine the logarithm to base two of the fragment size. */
register size_t log = 1;
--size;
while ((size /= 2) != 0)
++log;
/* Look in the fragment lists for a
free fragment of the desired size. */
next = _fraghead[log].next;
if (next != NULL)
{
/* There are free fragments of this size.
Pop a fragment out of the fragment list and return it.
Update the block's nfree and first counters. */
result = (__ptr_t) next;
next->prev->next = next->next;
if (next->next != NULL)
next->next->prev = next->prev;
block = BLOCK (result);
if (--_heapinfo[block].busy.info.frag.nfree != 0)
_heapinfo[block].busy.info.frag.first = (unsigned long int)
((unsigned long int) ((char *) next->next - (char *) NULL)
% BLOCKSIZE) >> log;
/* Update the statistics. */
++_chunks_used;
_bytes_used += 1 << log;
--_chunks_free;
_bytes_free -= 1 << log;
}
else
{
/* No free fragments of the desired size, so get a new block
and break it into fragments, returning the first. */
result = malloc (BLOCKSIZE);
if (result == NULL)
return NULL;
++_fragblocks[log];
/* Link all fragments but the first into the free list. */
for (i = 1; i < (size_t) (BLOCKSIZE >> log); ++i)
{
next = (struct list *) ((char *) result + (i << log));
next->next = _fraghead[log].next;
next->prev = &_fraghead[log];
next->prev->next = next;
if (next->next != NULL)
next->next->prev = next;
}
/* Initialize the nfree and first counters for this block. */
block = BLOCK (result);
_heapinfo[block].busy.type = log;
_heapinfo[block].busy.info.frag.nfree = i - 1;
_heapinfo[block].busy.info.frag.first = i - 1;
_chunks_free += (BLOCKSIZE >> log) - 1;
_bytes_free += BLOCKSIZE - (1 << log);
_bytes_used -= BLOCKSIZE - (1 << log);
}
}
else
{
/* Large allocation to receive one or more blocks.
Search the free list in a circle starting at the last place visited.
If we loop completely around without finding a large enough
space we will have to get more memory from the system. */
blocks = BLOCKIFY (size);
start = block = _heapindex;
while (_heapinfo[block].free.size < blocks)
{
block = _heapinfo[block].free.next;
if (block == start)
{
/* Need to get more from the system. Check to see if
the new core will be contiguous with the final free
block; if so we don't need to get as much. */
block = _heapinfo[0].free.prev;
lastblocks = _heapinfo[block].free.size;
if (_heaplimit != 0 && block + lastblocks == _heaplimit &&
(*__morecore) (0) == ADDRESS (block + lastblocks) &&
(morecore ((blocks - lastblocks) * BLOCKSIZE)) != NULL)
{
/* Note that morecore() can change the location of
the final block if it moves the info table and the
old one gets coalesced into the final block. */
block = _heapinfo[0].free.prev;
_heapinfo[block].free.size += blocks - lastblocks;
continue;
}
result = morecore (blocks * BLOCKSIZE);
if (result == NULL)
return NULL;
block = BLOCK (result);
_heapinfo[block].busy.type = 0;
_heapinfo[block].busy.info.size = blocks;
++_chunks_used;
_bytes_used += blocks * BLOCKSIZE;
return result;
}
}
/* At this point we have found a suitable free list entry.
Figure out how to remove what we need from the list. */
result = ADDRESS (block);
if (_heapinfo[block].free.size > blocks)
{
/* The block we found has a bit left over,
so relink the tail end back into the free list. */
_heapinfo[block + blocks].free.size
= _heapinfo[block].free.size - blocks;
_heapinfo[block + blocks].free.next
= _heapinfo[block].free.next;
_heapinfo[block + blocks].free.prev
= _heapinfo[block].free.prev;
_heapinfo[_heapinfo[block].free.prev].free.next
= _heapinfo[_heapinfo[block].free.next].free.prev
= _heapindex = block + blocks;
}
else
{
/* The block exactly matches our requirements,
so just remove it from the list. */
_heapinfo[_heapinfo[block].free.next].free.prev
= _heapinfo[block].free.prev;
_heapinfo[_heapinfo[block].free.prev].free.next
= _heapindex = _heapinfo[block].free.next;
--_chunks_free;
}
_heapinfo[block].busy.type = 0;
_heapinfo[block].busy.info.size = blocks;
++_chunks_used;
_bytes_used += blocks * BLOCKSIZE;
_bytes_free -= blocks * BLOCKSIZE;
}
return result;
}

268
lib/malloclib/malloc.h Normal file
View file

@ -0,0 +1,268 @@
/* Declarations for `malloc' and friends.
Copyright 1990, 1991, 1992, 1993 Free Software Foundation, Inc.
Written May 1989 by Mike Haertel.
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public License as
published by the Free Software Foundation; either version 2 of the
License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; see the file COPYING.LIB. If
not, write to the Free Software Foundation, Inc., 675 Mass Ave,
Cambridge, MA 02139, USA.
The author may be reached (Email) at the address mike@ai.mit.edu,
or (US mail) as Mike Haertel c/o Free Software Foundation. */
#ifndef _MALLOC_H
#define _MALLOC_H 1
#ifdef _MALLOC_INTERNAL
/* Harmless, gets __GNU_LIBRARY__ defined.
We must do this before #defining size_t and ptrdiff_t
because <stdio.h> tries to typedef them on some systems. */
#include <stdio.h>
#endif
#ifdef __cplusplus
extern "C"
{
#endif
#if defined (__cplusplus) || (defined (__STDC__) && __STDC__)
#undef __P
#define __P(args) args
#undef __ptr_t
#define __ptr_t void *
#else /* Not C++ or ANSI C. */
#undef __P
#define __P(args) ()
#undef const
#define const
#undef __ptr_t
#define __ptr_t char *
#endif /* C++ or ANSI C. */
#ifndef NULL
#define NULL 0
#endif
#ifdef __STDC__
#include <stddef.h>
#else
#undef size_t
#define size_t unsigned int
#undef ptrdiff_t
#define ptrdiff_t int
#endif
/* Allocate SIZE bytes of memory. */
extern __ptr_t malloc __P ((size_t __size));
/* Re-allocate the previously allocated block
in __ptr_t, making the new block SIZE bytes long. */
extern __ptr_t realloc __P ((__ptr_t __ptr, size_t __size));
/* Allocate NMEMB elements of SIZE bytes each, all initialized to 0. */
extern __ptr_t calloc __P ((size_t __nmemb, size_t __size));
/* Free a block allocated by `malloc', `realloc' or `calloc'. */
extern void free __P ((__ptr_t __ptr));
/* Allocate SIZE bytes allocated to ALIGNMENT bytes. */
extern __ptr_t memalign __P ((size_t __alignment, size_t __size));
/* Allocate SIZE bytes on a page boundary. */
extern __ptr_t valloc __P ((size_t __size));
#ifdef _MALLOC_INTERNAL
#ifdef HAVE_CONFIG_H
#include "config.h"
#endif
#if defined(__GNU_LIBRARY__) || defined(STDC_HEADERS) || defined(USG)
#include <string.h>
#else
#ifndef memset
#define memset(s, zero, n) bzero ((s), (n))
#endif
#ifndef memcpy
#define memcpy(d, s, n) bcopy ((s), (d), (n))
#endif
#ifndef memmove
#define memmove(d, s, n) bcopy ((s), (d), (n))
#endif
#endif
#if defined(__GNU_LIBRARY__) || defined(__STDC__)
#include <limits.h>
#else
#define CHAR_BIT 8
#endif
/* The allocator divides the heap into blocks of fixed size; large
requests receive one or more whole blocks, and small requests
receive a fragment of a block. Fragment sizes are powers of two,
and all fragments of a block are the same size. When all the
fragments in a block have been freed, the block itself is freed. */
#define INT_BIT (CHAR_BIT * sizeof(int))
#define BLOCKLOG (INT_BIT > 16 ? 12 : 9)
#define BLOCKSIZE (1 << BLOCKLOG)
#define BLOCKIFY(SIZE) (((SIZE) + BLOCKSIZE - 1) / BLOCKSIZE)
/* Determine the amount of memory spanned by the initial heap table
(not an absolute limit). */
#define HEAP (INT_BIT > 16 ? 4194304 : 65536)
/* Number of contiguous free blocks allowed to build up at the end of
memory before they will be returned to the system. */
#define FINAL_FREE_BLOCKS 8
/* Data structure giving per-block information. */
typedef union
{
/* Heap information for a busy block. */
struct
{
/* Zero for a large block, or positive giving the
logarithm to the base two of the fragment size. */
int type;
union
{
struct
{
size_t nfree; /* Free fragments in a fragmented block. */
size_t first; /* First free fragment of the block. */
} frag;
/* Size (in blocks) of a large cluster. */
size_t size;
} info;
} busy;
/* Heap information for a free block
(that may be the first of a free cluster). */
struct
{
size_t size; /* Size (in blocks) of a free cluster. */
size_t next; /* Index of next free cluster. */
size_t prev; /* Index of previous free cluster. */
} free;
} malloc_info;
/* Pointer to first block of the heap. */
extern char *_heapbase;
/* Table indexed by block number giving per-block information. */
extern malloc_info *_heapinfo;
/* Address to block number and vice versa. */
#define BLOCK(A) (((char *) (A) - _heapbase) / BLOCKSIZE + 1)
#define ADDRESS(B) ((__ptr_t) (((B) - 1) * BLOCKSIZE + _heapbase))
/* Current search index for the heap table. */
extern size_t _heapindex;
/* Limit of valid info table indices. */
extern size_t _heaplimit;
/* Doubly linked lists of free fragments. */
struct list
{
struct list *next;
struct list *prev;
};
/* Count of blocks for each fragment size. */
extern int _fragblocks[];
/* Free list headers for each fragment size. */
extern struct list _fraghead[];
/* List of blocks allocated with `memalign' (or `valloc'). */
struct alignlist
{
struct alignlist *next;
__ptr_t aligned; /* The address that memaligned returned. */
__ptr_t exact; /* The address that malloc returned. */
};
extern struct alignlist *_aligned_blocks;
/* Instrumentation. */
extern size_t _chunks_used;
extern size_t _bytes_used;
extern size_t _chunks_free;
extern size_t _bytes_free;
/* Internal version of `free' used in `morecore' (malloc.c). */
extern void _free_internal __P ((__ptr_t __ptr));
#endif /* _MALLOC_INTERNAL. */
/* Underlying allocation function; successive calls should
return contiguous pieces of memory. */
extern __ptr_t (*__morecore) __P ((ptrdiff_t __size));
/* Default value of `__morecore'. */
extern __ptr_t __default_morecore __P ((ptrdiff_t __size));
/* If not NULL, this function is called after each time
`__morecore' is called to increase the data size. */
extern void (*__after_morecore_hook) __P ((void));
/* Nonzero if `malloc' has been called and done its initialization. */
extern int __malloc_initialized;
/* Hooks for debugging versions. */
extern void (*__free_hook) __P ((__ptr_t __ptr));
extern __ptr_t (*__malloc_hook) __P ((size_t __size));
extern __ptr_t (*__realloc_hook) __P ((__ptr_t __ptr, size_t __size));
/* Activate a standard collection of debugging hooks. */
extern int mcheck __P ((void (*__bfunc) __P ((char *)),
void (*__afunc) __P ((void))));
/* Activate a standard collection of tracing hooks. */
extern void mtrace __P ((void));
/* Statistics available to the user. */
struct mstats
{
size_t bytes_total; /* Total size of the heap. */
size_t chunks_used; /* Chunks allocated by the user. */
size_t bytes_used; /* Byte total of user-allocated chunks. */
size_t chunks_free; /* Chunks in the free list. */
size_t bytes_free; /* Byte total of chunks in the free list. */
};
/* Pick up the current statistics. */
extern struct mstats mstats __P ((void));
/* Call WARNFUN with a warning message when memory usage is high. */
extern void memory_warnings __P ((__ptr_t __start,
void (*__warnfun) __P ((__const char *))));
/* Relocating allocator. */
/* Allocate SIZE bytes, and store the address in *HANDLEPTR. */
extern __ptr_t r_alloc __P ((__ptr_t *__handleptr, size_t __size));
/* Free the storage allocated in HANDLEPTR. */
extern void r_alloc_free __P ((__ptr_t *__handleptr));
/* Adjust the block at HANDLEPTR to be SIZE bytes long. */
extern __ptr_t r_re_alloc __P ((__ptr_t *__handleptr, size_t __size));
#ifdef __cplusplus
}
#endif
#endif /* malloc.h */

133
lib/malloclib/mcheck.c Normal file
View file

@ -0,0 +1,133 @@
/* Standard debugging hooks for `malloc'.
Copyright 1990, 1991, 1992, 1993 Free Software Foundation
Written May 1989 by Mike Haertel.
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public License as
published by the Free Software Foundation; either version 2 of the
License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; see the file COPYING.LIB. If
not, write to the Free Software Foundation, Inc., 675 Mass Ave,
Cambridge, MA 02139, USA.
The author may be reached (Email) at the address mike@ai.mit.edu,
or (US mail) as Mike Haertel c/o Free Software Foundation. */
#ifndef _MALLOC_INTERNAL
#define _MALLOC_INTERNAL
#include <malloc.h>
#endif
/* Old hook values. */
static void (*old_free_hook) __P ((__ptr_t ptr));
static __ptr_t (*old_malloc_hook) __P ((size_t size));
static __ptr_t (*old_realloc_hook) __P ((__ptr_t ptr, size_t size));
/* Function to call when something awful happens. */
static void (*abortfunc) __P ((void));
/* Arbitrary magical numbers. */
#define MAGICWORD 0xfedabeeb
#define MAGICBYTE ((char) 0xd7)
struct hdr
{
size_t size; /* Exact size requested by user. */
unsigned long int magic; /* Magic number to check header integrity. */
};
static void checkhdr __P ((const struct hdr *));
static void
checkhdr (hdr)
const struct hdr *hdr;
{
if (hdr->magic != MAGICWORD || ((char *) &hdr[1])[hdr->size] != MAGICBYTE)
(*abortfunc) ();
}
static void freehook __P ((__ptr_t));
static void
freehook (ptr)
__ptr_t ptr;
{
struct hdr *hdr = ((struct hdr *) ptr) - 1;
checkhdr (hdr);
hdr->magic = 0;
__free_hook = old_free_hook;
free (hdr);
__free_hook = freehook;
}
static __ptr_t mallochook __P ((size_t));
static __ptr_t
mallochook (size)
size_t size;
{
struct hdr *hdr;
__malloc_hook = old_malloc_hook;
hdr = (struct hdr *) malloc (sizeof (struct hdr) + size + 1);
__malloc_hook = mallochook;
if (hdr == NULL)
return NULL;
hdr->size = size;
hdr->magic = MAGICWORD;
((char *) &hdr[1])[size] = MAGICBYTE;
return (__ptr_t) (hdr + 1);
}
static __ptr_t reallochook __P ((__ptr_t, size_t));
static __ptr_t
reallochook (ptr, size)
__ptr_t ptr;
size_t size;
{
struct hdr *hdr = ((struct hdr *) ptr) - 1;
checkhdr (hdr);
__free_hook = old_free_hook;
__malloc_hook = old_malloc_hook;
__realloc_hook = old_realloc_hook;
hdr = (struct hdr *) realloc ((__ptr_t) hdr, sizeof (struct hdr) + size + 1);
__free_hook = freehook;
__malloc_hook = mallochook;
__realloc_hook = reallochook;
if (hdr == NULL)
return NULL;
hdr->size = size;
((char *) &hdr[1])[size] = MAGICBYTE;
return (__ptr_t) (hdr + 1);
}
int
mcheck (func)
void (*func) __P ((void));
{
extern void abort __P ((void));
static int mcheck_used = 0;
abortfunc = (func != NULL) ? func : abort;
/* These hooks may not be safely inserted if malloc is already in use. */
if (!__malloc_initialized && !mcheck_used)
{
old_free_hook = __free_hook;
__free_hook = freehook;
old_malloc_hook = __malloc_hook;
__malloc_hook = mallochook;
old_realloc_hook = __realloc_hook;
__realloc_hook = reallochook;
mcheck_used = 1;
}
return mcheck_used ? 0 : -1;
}

61
lib/malloclib/memalign.c Normal file
View file

@ -0,0 +1,61 @@
/* Copyright (C) 1991, 1992 Free Software Foundation, Inc.
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public License as
published by the Free Software Foundation; either version 2 of the
License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; see the file COPYING.LIB. If
not, write to the Free Software Foundation, Inc., 675 Mass Ave,
Cambridge, MA 02139, USA. */
#ifndef _MALLOC_INTERNAL
#define _MALLOC_INTERNAL
#include <malloc.h>
#endif
__ptr_t
memalign (alignment, size)
size_t alignment;
size_t size;
{
__ptr_t result;
unsigned long int adj;
size = ((size + alignment - 1) / alignment) * alignment;
result = malloc (size);
if (result == NULL)
return NULL;
adj = (unsigned long int) ((unsigned long int) ((char *) result -
(char *) NULL)) % alignment;
if (adj != 0)
{
struct alignlist *l;
for (l = _aligned_blocks; l != NULL; l = l->next)
if (l->aligned == NULL)
/* This slot is free. Use it. */
break;
if (l == NULL)
{
l = (struct alignlist *) malloc (sizeof (struct alignlist));
if (l == NULL)
{
free (result);
return NULL;
}
}
l->exact = result;
result = l->aligned = (char *) result + alignment - adj;
l->next = _aligned_blocks;
_aligned_blocks = l;
}
return result;
}

44
lib/malloclib/morecore.c Normal file
View file

@ -0,0 +1,44 @@
/* Copyright (C) 1991, 1992 Free Software Foundation, Inc.
This file is part of the GNU C Library.
The GNU C Library is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2, or (at your option)
any later version.
The GNU C Library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with the GNU C Library; see the file COPYING. If not, write to
the Free Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA. */
#ifndef _MALLOC_INTERNAL
#define _MALLOC_INTERNAL
#include <malloc.h>
#endif
#ifndef __GNU_LIBRARY__
#define __sbrk sbrk
#endif
extern __ptr_t __sbrk __P ((int increment));
#ifndef NULL
#define NULL 0
#endif
/* Allocate INCREMENT more bytes of data space,
and return the start of data space, or NULL on errors.
If INCREMENT is negative, shrink data space. */
__ptr_t
__default_morecore (increment)
ptrdiff_t increment;
{
__ptr_t result = __sbrk ((int) increment);
if (result == (__ptr_t) -1)
return NULL;
return result;
}

39
lib/malloclib/mstats.c Normal file
View file

@ -0,0 +1,39 @@
/* Access the statistics maintained by `malloc'.
Copyright 1990, 1991, 1992 Free Software Foundation
Written May 1989 by Mike Haertel.
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public License as
published by the Free Software Foundation; either version 2 of the
License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; see the file COPYING.LIB. If
not, write to the Free Software Foundation, Inc., 675 Mass Ave,
Cambridge, MA 02139, USA.
The author may be reached (Email) at the address mike@ai.mit.edu,
or (US mail) as Mike Haertel c/o Free Software Foundation. */
#ifndef _MALLOC_INTERNAL
#define _MALLOC_INTERNAL
#include <malloc.h>
#endif
struct mstats
mstats ()
{
struct mstats result;
result.bytes_total = (char *) (*__morecore) (0) - _heapbase;
result.chunks_used = _chunks_used;
result.bytes_used = _bytes_used;
result.chunks_free = _chunks_free;
result.bytes_free = _bytes_free;
return result;
}

36
lib/malloclib/mtrace.awk Normal file
View file

@ -0,0 +1,36 @@
#
# Awk program to analyze mtrace.c output.
#
$1 == "+" { if (allocated[$2] != "")
print "+", $2, "Alloc", NR, "duplicate:", allocated[$2];
else
allocated[$2] = $3;
}
$1 == "-" { if (allocated[$2] != "") {
allocated[$2] = "";
if (allocated[$2] != "")
print "DELETE FAILED", $2, allocated[$2];
} else
print "-", $2, "Free", NR, "was never alloc'd";
}
$1 == "<" { if (allocated[$2] != "")
allocated[$2] = "";
else
print "-", $2, "Realloc", NR, "was never alloc'd";
}
$1 == ">" { if (allocated[$2] != "")
print "+", $2, "Realloc", NR, "duplicate:", allocated[$2];
else
allocated[$2] = $3;
}
# Ignore "= Start"
$1 == "=" { }
# Ignore failed realloc attempts for now
$1 == "!" { }
END { for (x in allocated)
if (allocated[x] != "")
print "+", x, allocated[x];
}

150
lib/malloclib/mtrace.c Normal file
View file

@ -0,0 +1,150 @@
/* More debugging hooks for `malloc'.
Copyright (C) 1991, 1992, 1993 Free Software Foundation, Inc.
Written April 2, 1991 by John Gilmore of Cygnus Support.
Based on mcheck.c by Mike Haertel.
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public License as
published by the Free Software Foundation; either version 2 of the
License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; see the file COPYING.LIB. If
not, write to the Free Software Foundation, Inc., 675 Mass Ave,
Cambridge, MA 02139, USA.
The author may be reached (Email) at the address mike@ai.mit.edu,
or (US mail) as Mike Haertel c/o Free Software Foundation. */
#ifndef _MALLOC_INTERNAL
#define _MALLOC_INTERNAL
#include <malloc.h>
#endif
/* Don't #include <stdio.h> because <malloc.h> did it for us. */
#ifndef __GNU_LIBRARY__
extern char *getenv ();
#else
#include <stdlib.h>
#endif
static FILE *mallstream;
static char mallenv[]= "MALLOC_TRACE";
static char mallbuf[BUFSIZ]; /* Buffer for the output. */
/* Address to breakpoint on accesses to... */
__ptr_t mallwatch;
/* Old hook values. */
static void (*tr_old_free_hook) __P ((__ptr_t ptr));
static __ptr_t (*tr_old_malloc_hook) __P ((size_t size));
static __ptr_t (*tr_old_realloc_hook) __P ((__ptr_t ptr, size_t size));
/* This function is called when the block being alloc'd, realloc'd, or
freed has an address matching the variable "mallwatch". In a debugger,
set "mallwatch" to the address of interest, then put a breakpoint on
tr_break. */
void tr_break __P ((void));
void
tr_break ()
{
}
static void tr_freehook __P ((__ptr_t));
static void
tr_freehook (ptr)
__ptr_t ptr;
{
fprintf (mallstream, "- %p\n", ptr); /* Be sure to print it first. */
if (ptr == mallwatch)
tr_break ();
__free_hook = tr_old_free_hook;
free (ptr);
__free_hook = tr_freehook;
}
static __ptr_t tr_mallochook __P ((size_t));
static __ptr_t
tr_mallochook (size)
size_t size;
{
__ptr_t hdr;
__malloc_hook = tr_old_malloc_hook;
hdr = (__ptr_t) malloc (size);
__malloc_hook = tr_mallochook;
/* We could be printing a NULL here; that's OK. */
fprintf (mallstream, "+ %p %x\n", hdr, size);
if (hdr == mallwatch)
tr_break ();
return hdr;
}
static __ptr_t tr_reallochook __P ((__ptr_t, size_t));
static __ptr_t
tr_reallochook (ptr, size)
__ptr_t ptr;
size_t size;
{
__ptr_t hdr;
if (ptr == mallwatch)
tr_break ();
__free_hook = tr_old_free_hook;
__malloc_hook = tr_old_malloc_hook;
__realloc_hook = tr_old_realloc_hook;
hdr = (__ptr_t) realloc (ptr, size);
__free_hook = tr_freehook;
__malloc_hook = tr_mallochook;
__realloc_hook = tr_reallochook;
if (hdr == NULL)
/* Failed realloc. */
fprintf (mallstream, "! %p %x\n", ptr, size);
else
fprintf (mallstream, "< %p\n> %p %x\n", ptr, hdr, size);
if (hdr == mallwatch)
tr_break ();
return hdr;
}
/* We enable tracing if either the environment variable MALLOC_TRACE
is set, or if the variable mallwatch has been patched to an address
that the debugging user wants us to stop on. When patching mallwatch,
don't forget to set a breakpoint on tr_break! */
void
mtrace ()
{
char *mallfile;
mallfile = getenv (mallenv);
if (mallfile != NULL || mallwatch != NULL)
{
mallstream = fopen (mallfile != NULL ? mallfile : "/dev/null", "w");
if (mallstream != NULL)
{
/* Be sure it doesn't malloc its buffer! */
setbuf (mallstream, mallbuf);
fprintf (mallstream, "= Start\n");
tr_old_free_hook = __free_hook;
__free_hook = tr_freehook;
tr_old_malloc_hook = __malloc_hook;
__malloc_hook = tr_mallochook;
tr_old_realloc_hook = __realloc_hook;
__realloc_hook = tr_reallochook;
}
}
}

146
lib/malloclib/realloc.c Normal file
View file

@ -0,0 +1,146 @@
/* Change the size of a block allocated by `malloc'.
Copyright 1990, 1991, 1992, 1993 Free Software Foundation, Inc.
Written May 1989 by Mike Haertel.
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public License as
published by the Free Software Foundation; either version 2 of the
License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; see the file COPYING.LIB. If
not, write to the Free Software Foundation, Inc., 675 Mass Ave,
Cambridge, MA 02139, USA.
The author may be reached (Email) at the address mike@ai.mit.edu,
or (US mail) as Mike Haertel c/o Free Software Foundation. */
#ifndef _MALLOC_INTERNAL
#define _MALLOC_INTERNAL
#include <malloc.h>
#endif
#define min(A, B) ((A) < (B) ? (A) : (B))
/* Debugging hook for realloc. */
__ptr_t (*__realloc_hook) __P ((__ptr_t __ptr, size_t __size));
/* Resize the given region to the new size, returning a pointer
to the (possibly moved) region. This is optimized for speed;
some benchmarks seem to indicate that greater compactness is
achieved by unconditionally allocating and copying to a
new region. This module has incestuous knowledge of the
internals of both free and malloc. */
__ptr_t
realloc (ptr, size)
__ptr_t ptr;
size_t size;
{
__ptr_t result;
int type;
size_t block, blocks, oldlimit;
if (size == 0)
{
free (ptr);
return malloc (0);
}
else if (ptr == NULL)
return malloc (size);
if (__realloc_hook != NULL)
return (*__realloc_hook) (ptr, size);
block = BLOCK (ptr);
type = _heapinfo[block].busy.type;
switch (type)
{
case 0:
/* Maybe reallocate a large block to a small fragment. */
if (size <= BLOCKSIZE / 2)
{
result = malloc (size);
if (result != NULL)
{
memcpy (result, ptr, size);
free (ptr);
return result;
}
}
/* The new size is a large allocation as well;
see if we can hold it in place. */
blocks = BLOCKIFY (size);
if (blocks < _heapinfo[block].busy.info.size)
{
/* The new size is smaller; return
excess memory to the free list. */
_heapinfo[block + blocks].busy.type = 0;
_heapinfo[block + blocks].busy.info.size
= _heapinfo[block].busy.info.size - blocks;
_heapinfo[block].busy.info.size = blocks;
free (ADDRESS (block + blocks));
result = ptr;
}
else if (blocks == _heapinfo[block].busy.info.size)
/* No size change necessary. */
result = ptr;
else
{
/* Won't fit, so allocate a new region that will.
Free the old region first in case there is sufficient
adjacent free space to grow without moving. */
blocks = _heapinfo[block].busy.info.size;
/* Prevent free from actually returning memory to the system. */
oldlimit = _heaplimit;
_heaplimit = 0;
free (ptr);
_heaplimit = oldlimit;
result = malloc (size);
if (result == NULL)
{
/* Now we're really in trouble. We have to unfree
the thing we just freed. Unfortunately it might
have been coalesced with its neighbors. */
if (_heapindex == block)
(void) malloc (blocks * BLOCKSIZE);
else
{
__ptr_t previous = malloc ((block - _heapindex) * BLOCKSIZE);
(void) malloc (blocks * BLOCKSIZE);
free (previous);
}
return NULL;
}
if (ptr != result)
memmove (result, ptr, blocks * BLOCKSIZE);
}
break;
default:
/* Old size is a fragment; type is logarithm
to base two of the fragment size. */
if (size > (size_t) (1 << (type - 1)) && size <= (size_t) (1 << type))
/* The new size is the same kind of fragment. */
result = ptr;
else
{
/* The new size is different; allocate a new space,
and copy the lesser of the new size and the old. */
result = malloc (size);
if (result == NULL)
return NULL;
memcpy (result, ptr, min (size, (size_t) 1 << type));
free (ptr);
}
break;
}
return result;
}

48
lib/malloclib/valloc.c Normal file
View file

@ -0,0 +1,48 @@
/* Allocate memory on a page boundary.
Copyright (C) 1991, 1992, 1993 Free Software Foundation, Inc.
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public License as
published by the Free Software Foundation; either version 2 of the
License, or (at your option) any later version.
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; see the file COPYING.LIB. If
not, write to the Free Software Foundation, Inc., 675 Mass Ave,
Cambridge, MA 02139, USA.
The author may be reached (Email) at the address mike@ai.mit.edu,
or (US mail) as Mike Haertel c/o Free Software Foundation. */
#ifndef _MALLOC_INTERNAL
#define _MALLOC_INTERNAL
#include <malloc.h>
#endif
#if defined (emacs) || defined (HAVE_CONFIG_H)
#include "config.h"
#endif
#ifdef __GNU_LIBRARY__
extern size_t __getpagesize __P ((void));
#else
#include "getpagesize.h"
#define __getpagesize() getpagesize()
#endif
static size_t pagesize;
__ptr_t
valloc (size)
size_t size;
{
if (pagesize == 0)
pagesize = __getpagesize ();
return memalign (pagesize, size);
}

View file

@ -0,0 +1,63 @@
;; alloca386.s 1.2
;; GNU-compatible stack allocation function for Xenix/386.
;; Written by Chip Salzenberg at ComDev.
;; Last modified 90/01/11
;;> Is your alloca clearly better than the one in i386-alloca.s? I haven't
;;> looked at either.
;;
;;They're different because Xenix/386 has a different assembler. SCO
;;Xenix has the Microsoft C compiler and the Microsoft macro assembler,
;;called "masm". MASM's assembler syntax is quite different from AT&T's
;;in all sorts of ways. Xenix people can't use the AT&T version.
;;--
;;Chip Salzenberg at ComDev/TCT <chip@tct.uucp>, <uunet!ateng!tct!chip>
TITLE $alloca386
.386
DGROUP GROUP CONST, _BSS, _DATA
_DATA SEGMENT DWORD USE32 PUBLIC 'DATA'
_DATA ENDS
_BSS SEGMENT DWORD USE32 PUBLIC 'BSS'
_BSS ENDS
CONST SEGMENT DWORD USE32 PUBLIC 'CONST'
CONST ENDS
_TEXT SEGMENT DWORD USE32 PUBLIC 'CODE'
ASSUME CS: _TEXT, DS: DGROUP, SS: DGROUP, ES: DGROUP
PUBLIC _alloca
_alloca PROC NEAR
; Get argument.
pop edx ; edx -> return address
pop eax ; eax = amount to allocate
; Validate allocation amount.
add eax,3
and eax,not 3
cmp eax,0
jg aa_size_ok
mov eax,4
aa_size_ok:
; Allocate stack space.
mov ecx,esp ; ecx -> old stack pointer
sub esp,eax ; perform allocation
mov eax,esp ; eax -> new stack pointer
; Copy the three saved register variables from old stack top to new stack top.
; They may not be there. So we waste twelve bytes. Big fat hairy deal.
push DWORD PTR 8[ecx]
push DWORD PTR 4[ecx]
push DWORD PTR 0[ecx]
; Push something so the caller can pop it off.
push eax
; Return to caller.
jmp edx
_alloca ENDP
_TEXT ENDS
END

69
lib/malloclib/xmalloc.c Normal file
View file

@ -0,0 +1,69 @@
/* xmalloc.c -- safe versions of malloc and realloc */
/* Copyright (C) 1991 Free Software Foundation, Inc.
This file is part of GNU Readline, a library for reading lines
of text with interactive input and history editing.
Readline is free software; you can redistribute it and/or modify it
under the terms of the GNU General Public License as published by the
Free Software Foundation; either version 1, or (at your option) any
later version.
Readline is distributed in the hope that it will be useful, but
WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
General Public License for more details.
You should have received a copy of the GNU General Public License
along with Readline; see the file COPYING. If not, write to the Free
Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA. */
#include <stdio.h>
static void memory_error_and_abort ();
/* **************************************************************** */
/* */
/* Memory Allocation and Deallocation. */
/* */
/* **************************************************************** */
/* Return a pointer to free()able block of memory large enough
to hold BYTES number of bytes. If the memory cannot be allocated,
print an error message and abort. */
char *
xmalloc (bytes)
int bytes;
{
char *temp = (char *)malloc (bytes);
if (!temp)
memory_error_and_abort ("xmalloc");
return (temp);
}
char *
xrealloc (pointer, bytes)
char *pointer;
int bytes;
{
char *temp;
if (!pointer)
temp = (char *)malloc (bytes);
else
temp = (char *)realloc (pointer, bytes);
if (!temp)
memory_error_and_abort ("xrealloc");
return (temp);
}
static void
memory_error_and_abort (fname)
char *fname;
{
fprintf (stderr, "%s: Out of virtual memory!\n", fname);
abort ();
}

View file

@ -0,0 +1,41 @@
/* ansi_stdlib.h -- An ANSI Standard stdlib.h. */
/* A minimal stdlib.h containing extern declarations for those functions
that bash uses. */
/* Copyright (C) 1993 Free Software Foundation, Inc.
This file is part of GNU Bash, the Bourne Again SHell.
Bash is free software; you can redistribute it and/or modify it under
the terms of the GNU General Public License as published by the Free
Software Foundation; either version 2, or (at your option) any later
version.
Bash is distributed in the hope that it will be useful, but WITHOUT ANY
WARRANTY; without even the implied warranty of MERCHANTABILITY or
FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
for more details.
You should have received a copy of the GNU General Public License along
with Bash; see the file COPYING. If not, write to the Free Software
Foundation, 675 Mass Ave, Cambridge, MA 02139, USA. */
#if !defined (_STDLIB_H_)
#define _STDLIB_H_ 1
/* String conversion functions. */
extern int atoi ();
extern long int atol ();
/* Memory allocation functions. */
extern char *malloc ();
extern char *realloc ();
extern void free ();
/* Other miscellaneous functions. */
extern void abort ();
extern void exit ();
extern char *getenv ();
extern void qsort ();
#endif /* _STDLIB_H */

View file

@ -0,0 +1,36 @@
/* filecntl.h - Definitions to set file descriptors to close-on-exec. */
/* Copyright (C) 1993 Free Software Foundation, Inc.
This file is part of GNU Bash, the Bourne Again SHell.
Bash is free software; you can redistribute it and/or modify it under
the terms of the GNU General Public License as published by the Free
Software Foundation; either version 2, or (at your option) any later
version.
Bash is distributed in the hope that it will be useful, but WITHOUT ANY
WARRANTY; without even the implied warranty of MERCHANTABILITY or
FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
for more details.
You should have received a copy of the GNU General Public License along
with Bash; see the file COPYING. If not, write to the Free Software
Foundation, 675 Mass Ave, Cambridge, MA 02139, USA. */
#if !defined (_FILECNTL_H_)
#define _FILECNTL_H_
#include <fcntl.h>
/* Definitions to set file descriptors to close-on-exec, the Posix way. */
#if !defined (FD_CLOEXEC)
#define FD_CLOEXEC 1
#endif
#define FD_NCLOEXEC 0
#define SET_CLOSE_ON_EXEC(fd) (fcntl ((fd), F_SETFD, FD_CLOEXEC))
#define SET_OPEN_ON_EXEC(fd) (fcntl ((fd), F_SETFD, FD_NCLOEXEC))
#endif /* ! _FILECNTL_H_ */

View file

@ -0,0 +1,56 @@
/* memalloc.h -- consolidate code for including alloca.h or malloc.h and
defining alloca. */
/* Copyright (C) 1993 Free Software Foundation, Inc.
This file is part of GNU Bash, the Bourne Again SHell.
Bash is free software; you can redistribute it and/or modify it under
the terms of the GNU General Public License as published by the Free
Software Foundation; either version 2, or (at your option) any later
version.
Bash is distributed in the hope that it will be useful, but WITHOUT ANY
WARRANTY; without even the implied warranty of MERCHANTABILITY or
FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
for more details.
You should have received a copy of the GNU General Public License along
with Bash; see the file COPYING. If not, write to the Free Software
Foundation, 675 Mass Ave, Cambridge, MA 02139, USA. */
#if !defined (__MEMALLOC_H__)
# define __MEMALLOC_H__
#if defined (sparc) && defined (sun) && !defined (HAVE_ALLOCA_H)
# define HAVE_ALLOCA_H
#endif
#if defined (__GNUC__) && !defined (HAVE_ALLOCA)
# define HAVE_ALLOCA
#endif
#if defined (HAVE_ALLOCA_H) && !defined (HAVE_ALLOCA)
# define HAVE_ALLOCA
#endif /* HAVE_ALLOCA_H && !HAVE_ALLOCA */
#if !defined (BUILDING_MAKEFILE)
#if defined (__GNUC__)
# undef alloca
# define alloca __builtin_alloca
#else /* !__GNUC__ */
# if defined (HAVE_ALLOCA_H)
# if defined (IBMESA)
# include <malloc.h>
# else /* !IBMESA */
# include <alloca.h>
# endif /* !IBMESA */
# else
extern char *alloca ();
# endif /* !HAVE_ALLOCA_H */
#endif /* !__GNUC__ */
#endif /* !BUILDING_MAKEFILE */
#endif /* __MEMALLOC_H__ */

View file

@ -0,0 +1,149 @@
/* posixstat.h -- Posix stat(2) definitions for systems that
don't have them. */
/* Copyright (C) 1987,1991 Free Software Foundation, Inc.
This file is part of GNU Bash, the Bourne Again SHell.
Bash is free software; you can redistribute it and/or modify it
under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 1, or (at your option)
any later version.
Bash is distributed in the hope that it will be useful, but WITHOUT
ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public
License for more details.
You should have received a copy of the GNU General Public License
along with Bash; see the file COPYING. If not, write to the Free
Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA. */
/* This file should be included instead of <sys/stat.h>.
It relies on the local sys/stat.h to work though. */
#if !defined (_POSIXSTAT_H)
#define _POSIXSTAT_H
#include <sys/stat.h>
#if defined (isc386)
# if !defined (S_IFDIR)
# define S_IFDIR 0040000
# endif /* !S_IFDIR */
# if !defined (S_IFMT)
# define S_IFMT 0170000
# endif /* !S_IFMT */
#endif /* isc386 */
/* This text is taken directly from the Cadmus I was trying to
compile on:
the following MACROs are defined for X/OPEN compatibility
however, is the param correct ??
#define S_ISBLK(s) ((s.st_mode & S_IFMT) == S_IFBLK)
Well, the answer is no. Thus... */
#if defined (BrainDeath)
# undef S_ISBLK
# undef S_ISCHR
# undef S_ISDIR
# undef S_ISFIFO
# undef S_ISREG
#endif /* BrainDeath */
/* Posix 1003.1 5.6.1.1 <sys/stat.h> file types */
/* Some Posix-wannabe systems define _S_IF* macros instead of S_IF*, but
do not provide the S_IS* macros that Posix requires. */
#if defined (_S_IFMT) && !defined (S_IFMT)
#define S_IFMT _S_IFMT
#endif
#if defined (_S_IFIFO) && !defined (S_IFIFO)
#define S_IFIFO _S_IFIFO
#endif
#if defined (_S_IFCHR) && !defined (S_IFCHR)
#define S_IFCHR _S_IFCHR
#endif
#if defined (_S_IFDIR) && !defined (S_IFDIR)
#define S_IFDIR _S_IFDIR
#endif
#if defined (_S_IFBLK) && !defined (S_IFBLK)
#define S_IFBLK _S_IFBLK
#endif
#if defined (_S_IFREG) && !defined (S_IFREG)
#define S_IFREG _S_IFREG
#endif
#if defined (_S_IFLNK) && !defined (S_IFLNK)
#define S_IFLNK _S_IFLNK
#endif
#if defined (_S_IFSOCK) && !defined (S_IFSOCK)
#define S_IFSOCK _S_IFSOCK
#endif
/* Test for each symbol individually and define the ones necessary (some
systems claiming Posix compatibility define some but not all). */
#if defined (S_IFBLK) && !defined (S_ISBLK)
#define S_ISBLK(m) (((m)&S_IFMT) == S_IFBLK) /* block device */
#endif
#if defined (S_IFCHR) && !defined (S_ISCHR)
#define S_ISCHR(m) (((m)&S_IFMT) == S_IFCHR) /* character device */
#endif
#if defined (S_IFDIR) && !defined (S_ISDIR)
#define S_ISDIR(m) (((m)&S_IFMT) == S_IFDIR) /* directory */
#endif
#if defined (S_IFREG) && !defined (S_ISREG)
#define S_ISREG(m) (((m)&S_IFMT) == S_IFREG) /* file */
#endif
#if defined (S_IFIFO) && !defined (S_ISFIFO)
#define S_ISFIFO(m) (((m)&S_IFMT) == S_IFIFO) /* fifo - named pipe */
#endif
#if defined (S_IFLNK) && !defined (S_ISLNK)
#define S_ISLNK(m) (((m)&S_IFMT) == S_IFLNK) /* symbolic link */
#endif
#if defined (S_IFSOCK) && !defined (S_ISSOCK)
#define S_ISSOCK(m) (((m)&S_IFMT) == S_IFSOCK) /* socket */
#endif
/*
* POSIX 1003.1 5.6.1.2 <sys/stat.h> File Modes
*/
#if !defined (S_IRWXU)
# if !defined (S_IREAD)
# define S_IREAD 00400
# define S_IWRITE 00200
# define S_IEXEC 00100
# endif /* S_IREAD */
# if !defined (S_IRUSR)
# define S_IRUSR S_IREAD /* read, owner */
# define S_IWUSR S_IWRITE /* write, owner */
# define S_IXUSR S_IEXEC /* execute, owner */
# define S_IRGRP (S_IREAD >> 3) /* read, group */
# define S_IWGRP (S_IWRITE >> 3) /* write, group */
# define S_IXGRP (S_IEXEC >> 3) /* execute, group */
# define S_IROTH (S_IREAD >> 6) /* read, other */
# define S_IWOTH (S_IWRITE >> 6) /* write, other */
# define S_IXOTH (S_IEXEC >> 6) /* execute, other */
# endif /* !S_IRUSR */
# define S_IRWXU (S_IRUSR | S_IWUSR | S_IXUSR)
# define S_IRWXG (S_IRGRP | S_IWGRP | S_IXGRP)
# define S_IRWXO (S_IROTH | S_IWOTH | S_IXOTH)
#endif /* !S_IRWXU */
/* These are non-standard, but are used in builtins.c$symbolic_umask() */
#define S_IRUGO (S_IRUSR | S_IRGRP | S_IROTH)
#define S_IWUGO (S_IWUSR | S_IWGRP | S_IWOTH)
#define S_IXUGO (S_IXUSR | S_IXGRP | S_IXOTH)
#endif /* _POSIXSTAT_H */

78
lib/posixheaders/stdc.h Normal file
View file

@ -0,0 +1,78 @@
/* stdc.h -- macros to make source compile on both ANSI C and K&R C
compilers. */
/* Copyright (C) 1993 Free Software Foundation, Inc.
This file is part of GNU Bash, the Bourne Again SHell.
Bash is free software; you can redistribute it and/or modify it
under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 1, or (at your option)
any later version.
Bash is distributed in the hope that it will be useful, but WITHOUT
ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public
License for more details.
You should have received a copy of the GNU General Public License
along with Bash; see the file COPYING. If not, write to the Free
Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA. */
#if !defined (__STDC_H__)
#define __STDC_H__
/* Adapted from BSD /usr/include/sys/cdefs.h. */
/* A function can be defined using prototypes and compile on both ANSI C
and traditional C compilers with something like this:
extern char *func __P((char *, char *, int)); */
#if defined (__STDC__)
# if !defined (__P)
# define __P(protos) protos
# endif
# define __STRING(x) #x
# if !defined (__GNUC__)
# define inline
# endif
#else /* !__STDC__ */
# if !defined (__P)
# define __P(protos) ()
# endif
# define __STRING(x) "x"
#if defined (__GNUC__) /* gcc with -traditional */
# if !defined (const)
# define const __const
# endif
# if !defined (inline)
# define inline __inline
# endif
# if !defined (signed)
# define signed __signed
# endif
# if !defined (volatile)
# define volatile __volatile
# endif
#else /* !__GNUC__ */
# if !defined (const)
# define const
# endif
# if !defined (inline)
# define inline
# endif
# if !defined (signed)
# define signed
# endif
# if !defined (volatile)
# define volatile
# endif
#endif /* !__GNUC__ */
#endif /* !__STDC__ */
#endif /* !__STDC_H__ */

257
lib/readline/COPYING Normal file
View file

@ -0,0 +1,257 @@
GNU GENERAL PUBLIC LICENSE
Version 1, February 1989
Copyright (C) 1989 Free Software Foundation, Inc.
675 Mass Ave, Cambridge, MA 02139, USA
Everyone is permitted to copy and distribute verbatim copies
of this license document, but changing it is not allowed.
The Free Software Foundation has exempted Bash from the requirement of
Paragraph 2c of the General Public License. This is to say, there is
no requirement for Bash to print a notice when it is started
interactively in the usual way. We made this exception because users
and standards expect shells not to print such messages. This
exception applies to any program that serves as a shell and that is
based primarily on Bash as opposed to other GNU software.
Preamble
The license agreements of most software companies try to keep users
at the mercy of those companies. By contrast, our General Public
License is intended to guarantee your freedom to share and change free
software--to make sure the software is free for all its users. The
General Public License applies to the Free Software Foundation's
software and to any other program whose authors commit to using it.
You can use it for your programs, too.
When we speak of free software, we are referring to freedom, not
price. Specifically, the General Public License is designed to make
sure that you have the freedom to give away or sell copies of free
software, that you receive source code or can get it if you want it,
that you can change the software or use pieces of it in new free
programs; and that you know you can do these things.
To protect your rights, we need to make restrictions that forbid
anyone to deny you these rights or to ask you to surrender the rights.
These restrictions translate to certain responsibilities for you if you
distribute copies of the software, or if you modify it.
For example, if you distribute copies of a such a program, whether
gratis or for a fee, you must give the recipients all the rights that
you have. You must make sure that they, too, receive or can get the
source code. And you must tell them their rights.
We protect your rights with two steps: (1) copyright the software, and
(2) offer you this license which gives you legal permission to copy,
distribute and/or modify the software.
Also, for each author's protection and ours, we want to make certain
that everyone understands that there is no warranty for this free
software. If the software is modified by someone else and passed on, we
want its recipients to know that what they have is not the original, so
that any problems introduced by others will not reflect on the original
authors' reputations.
The precise terms and conditions for copying, distribution and
modification follow.
GNU GENERAL PUBLIC LICENSE
TERMS AND CONDITIONS FOR COPYING, DISTRIBUTION AND MODIFICATION
0. This License Agreement applies to any program or other work which
contains a notice placed by the copyright holder saying it may be
distributed under the terms of this General Public License. The
"Program", below, refers to any such program or work, and a "work based
on the Program" means either the Program or any work containing the
Program or a portion of it, either verbatim or with modifications. Each
licensee is addressed as "you".
1. You may copy and distribute verbatim copies of the Program's source
code as you receive it, in any medium, provided that you conspicuously and
appropriately publish on each copy an appropriate copyright notice and
disclaimer of warranty; keep intact all the notices that refer to this
General Public License and to the absence of any warranty; and give any
other recipients of the Program a copy of this General Public License
along with the Program. You may charge a fee for the physical act of
transferring a copy.
2. You may modify your copy or copies of the Program or any portion of
it, and copy and distribute such modifications under the terms of Paragraph
1 above, provided that you also do the following:
a) cause the modified files to carry prominent notices stating that
you changed the files and the date of any change; and
b) cause the whole of any work that you distribute or publish, that
in whole or in part contains the Program or any part thereof, either
with or without modifications, to be licensed at no charge to all
third parties under the terms of this General Public License (except
that you may choose to grant warranty protection to some or all
third parties, at your option).
c) If the modified program normally reads commands interactively when
run, you must cause it, when started running for such interactive use
in the simplest and most usual way, to print or display an
announcement including an appropriate copyright notice and a notice
that there is no warranty (or else, saying that you provide a
warranty) and that users may redistribute the program under these
conditions, and telling the user how to view a copy of this General
Public License.
d) You may charge a fee for the physical act of transferring a
copy, and you may at your option offer warranty protection in
exchange for a fee.
Mere aggregation of another independent work with the Program (or its
derivative) on a volume of a storage or distribution medium does not bring
the other work under the scope of these terms.
3. You may copy and distribute the Program (or a portion or derivative of
it, under Paragraph 2) in object code or executable form under the terms of
Paragraphs 1 and 2 above provided that you also do one of the following:
a) accompany it with the complete corresponding machine-readable
source code, which must be distributed under the terms of
Paragraphs 1 and 2 above; or,
b) accompany it with a written offer, valid for at least three
years, to give any third party free (except for a nominal charge
for the cost of distribution) a complete machine-readable copy of the
corresponding source code, to be distributed under the terms of
Paragraphs 1 and 2 above; or,
c) accompany it with the information you received as to where the
corresponding source code may be obtained. (This alternative is
allowed only for noncommercial distribution and only if you
received the program in object code or executable form alone.)
Source code for a work means the preferred form of the work for making
modifications to it. For an executable file, complete source code means
all the source code for all modules it contains; but, as a special
exception, it need not include source code for modules which are standard
libraries that accompany the operating system on which the executable
file runs, or for standard header files or definitions files that
accompany that operating system.
4. You may not copy, modify, sublicense, distribute or transfer the
Program except as expressly provided under this General Public License.
Any attempt otherwise to copy, modify, sublicense, distribute or transfer
the Program is void, and will automatically terminate your rights to use
the Program under this License. However, parties who have received
copies, or rights to use copies, from you under this General Public
License will not have their licenses terminated so long as such parties
remain in full compliance.
5. By copying, distributing or modifying the Program (or any work based
on the Program) you indicate your acceptance of this license to do so,
and all its terms and conditions.
6. Each time you redistribute the Program (or any work based on the
Program), the recipient automatically receives a license from the original
licensor to copy, distribute or modify the Program subject to these
terms and conditions. You may not impose any further restrictions on the
recipients' exercise of the rights granted herein.
7. The Free Software Foundation may publish revised and/or new versions
of the General Public License from time to time. Such new versions will
be similar in spirit to the present version, but may differ in detail to
address new problems or concerns.
Each version is given a distinguishing version number. If the Program
specifies a version number of the license which applies to it and "any
later version", you have the option of following the terms and conditions
either of that version or of any later version published by the Free
Software Foundation. If the Program does not specify a version number of
the license, you may choose any version ever published by the Free Software
Foundation.
8. If you wish to incorporate parts of the Program into other free
programs whose distribution conditions are different, write to the author
to ask for permission. For software which is copyrighted by the Free
Software Foundation, write to the Free Software Foundation; we sometimes
make exceptions for this. Our decision will be guided by the two goals
of preserving the free status of all derivatives of our free software and
of promoting the sharing and reuse of software generally.
NO WARRANTY
9. BECAUSE THE PROGRAM IS LICENSED FREE OF CHARGE, THERE IS NO WARRANTY
FOR THE PROGRAM, TO THE EXTENT PERMITTED BY APPLICABLE LAW. EXCEPT WHEN
OTHERWISE STATED IN WRITING THE COPYRIGHT HOLDERS AND/OR OTHER PARTIES
PROVIDE THE PROGRAM "AS IS" WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESSED
OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. THE ENTIRE RISK AS
TO THE QUALITY AND PERFORMANCE OF THE PROGRAM IS WITH YOU. SHOULD THE
PROGRAM PROVE DEFECTIVE, YOU ASSUME THE COST OF ALL NECESSARY SERVICING,
REPAIR OR CORRECTION.
10. IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED TO IN WRITING
WILL ANY COPYRIGHT HOLDER, OR ANY OTHER PARTY WHO MAY MODIFY AND/OR
REDISTRIBUTE THE PROGRAM AS PERMITTED ABOVE, BE LIABLE TO YOU FOR DAMAGES,
INCLUDING ANY GENERAL, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES ARISING
OUT OF THE USE OR INABILITY TO USE THE PROGRAM (INCLUDING BUT NOT LIMITED
TO LOSS OF DATA OR DATA BEING RENDERED INACCURATE OR LOSSES SUSTAINED BY
YOU OR THIRD PARTIES OR A FAILURE OF THE PROGRAM TO OPERATE WITH ANY OTHER
PROGRAMS), EVEN IF SUCH HOLDER OR OTHER PARTY HAS BEEN ADVISED OF THE
POSSIBILITY OF SUCH DAMAGES.
END OF TERMS AND CONDITIONS
Appendix: How to Apply These Terms to Your New Programs
If you develop a new program, and you want it to be of the greatest
possible use to humanity, the best way to achieve this is to make it
free software which everyone can redistribute and change under these
terms.
To do so, attach the following notices to the program. It is safest to
attach them to the start of each source file to most effectively convey
the exclusion of warranty; and each file should have at least the
"copyright" line and a pointer to where the full notice is found.
<one line to give the program's name and a brief idea of what it does.>
Copyright (C) 19yy <name of author>
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 1, or (at your option)
any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
Also add information on how to contact you by electronic and paper mail.
If the program is interactive, make it output a short notice like this
when it starts in an interactive mode:
Gnomovision version 69, Copyright (C) 19xx name of author
Gnomovision comes with ABSOLUTELY NO WARRANTY; for details type `show w'.
This is free software, and you are welcome to redistribute it
under certain conditions; type `show c' for details.
The hypothetical commands `show w' and `show c' should show the
appropriate parts of the General Public License. Of course, the
commands you use may be called something other than `show w' and `show
c'; they could even be mouse-clicks or menu items--whatever suits your
program.
You should also get your employer (if you work as a programmer) or your
school, if any, to sign a "copyright disclaimer" for the program, if
necessary. Here a sample; alter the names:
Yoyodyne, Inc., hereby disclaims all copyright interest in the
program `Gnomovision' (a program to direct compilers to make passes
at assemblers) written by James Hacker.
<signature of Ty Coon>, 1 April 1989
Ty Coon, President of Vice
That's all there is to it!

403
lib/readline/ChangeLog Normal file
View file

@ -0,0 +1,403 @@
Tue Mar 23 14:36:51 1993 Brian Fox (bfox@eos.crseo.ucsb.edu)
* readline.c (rl_copy): Changed name to rl_copy_text.
Mon Mar 22 19:16:05 1993 Brian Fox (bfox@eos.crseo.ucsb.edu)
* dispose_cmd.c, several other files. Declare dispose_xxx () as
"void".
* builtins/hashcom.h: Make declarations of hashed_filenames be
"extern" to keep the SGI compiler happy.
* readline.c (rl_initialize_everything): Assign values to
out_stream and in_stream immediately, since
output_character_function () can be called before
readline_internal () is called.
Tue Dec 8 09:30:56 1992 Brian Fox (bfox@cubit)
* readline.c (rl_init_terminal) Set PC from BC, not from *buffer.
Mon Nov 30 09:35:47 1992 Brian Fox (bfox@cubit)
* readline.c (invoking_keyseqs_in_map, rl_parse_and_bind) Allow
backslash to quote characters, such as backslash, double quote,
and space. Backslash quotes all character indiscriminately.
* funmap.c (vi_keymap) Fix type in "vi-replace" declaration.
Fri Nov 20 10:55:05 1992 Brian Fox (bfox@cubit)
* readline.c (init_terminal_io, rl_prep_terminal): FINALLY!
Declare and use termcap variable `ospeed' when setting up terminal
parameters.
Thu Oct 8 08:53:07 1992 Brian J. Fox (bfox@helios)
* Makefile, this directory: Include (as links to the canonical
sources), tilde.c, tilde.h, posixstat.h and xmalloc.c.
Tue Sep 29 13:07:21 1992 Brian J. Fox (bfox@helios)
* readline.c (init_terminal_io) Don't set arrow keys if the key
sequences that represent them are already set.
* readline.c (rl_function_of_keyseq) New function returns the first
function (or macro) found while searching a key sequence.
Mon Sep 28 00:34:04 1992 Brian J. Fox (bfox@helios)
* readline.c (LibraryVersion) New static char * contains current
version number. Version is at 2.0.
* readline.c (rl_complete_internal): Incorporated clean changes
from gilmore (gnu@cygnus.com) to support quoted substrings within
completion functions.
* readline.c (many locations) Added support for the _GO32_,
whatever that is. Patches supplied by Cygnus, typed in by hand,
with cleanups.
Sun Aug 16 12:46:24 1992 Brian Fox (bfox@cubit)
* readline.c (init_terminal_io): Find out the values of the keypad
arrows and bind them to appropriate RL functions if present.
Mon Aug 10 18:13:24 1992 Brian Fox (bfox@cubit)
* history.c (stifle_history): A negative argument to stifle
becomes zero.
Tue Jul 28 09:28:41 1992 Brian Fox (bfox@cubit)
* readline.c (rl_variable_bind): New local structure describes
booleans by name and address; code in rl_variable_bind () looks at
structure to set simple variables.
* parens.c (rl_insert_close): New variable rl_blink_matching_paren
is non-zero if we want to blink the matching open when a close is
inserted. If FD_SET is defined, rl_blink_matching_paren defaults
to 1, else 0. If FD_SET is not defined, and
rl_blink_matching_paren is non-zero, the close character(s) are/is
simply inserted.
Wed Jul 22 20:03:59 1992 Brian Fox (bfox@cubit)
* history.c, readline.c, vi_mode.c: Cause the functions strchr ()
and strrchr () to be used instead of index () and rindex ()
throughout the source.
Mon Jul 13 11:34:07 1992 Brian Fox (bfox@cubit)
* readline.c: (rl_variable_bind) New variable "meta-flag" if "on"
means force the use of the 8th bit as Meta bit. Internal variable
is called meta_flag.
Thu Jul 9 10:37:56 1992 Brian Fox (bfox@cubit)
* history.c (get_history_event) Change INDEX to LOCAL_INDEX. If
compiling for the shell, allow shell metacharacters to separate
history tokens as they would for shell tokens.
Sat Jul 4 19:29:12 1992 Brian Fox (bfox@cubit)
* vi_keymap.c: According to Posix, TAB self-inserts instead of
doing completion.
* vi_mode.c: (rl_vi_yank_arg) Enter VI insert mode after yanking
an arg from the previous line.
* search.c: New file takes over vi style searching and implements
non-incremental searching the history.
Makefile: Add search.c and search.o.
funmap.c: Add names for non-incremental-forward-search-history and
non-incremental-reverse-search-history.
readline.h: Add extern definitions for non-incremental searching.
vi_mode.c: Remove old search code; add calls to code in search.c.
Fri Jul 3 10:36:33 1992 Brian Fox (bfox@cubit)
* readline.c (rl_delete_horizontal_space); New function deletes
all whitespace surrounding point.
funmap.c: Add "delete-horizontal-space".
emacs_keymap.c: Put rl_delete_horizontal_space () on M-\.
* readline.c (rl_set_signals, rl_clear_signals); New function
rl_set_sighandler () is either defined in a Posix way (if
HAVE_POSIX_SIGNALS is defined) or in a BSD way. Function is
called from rl_set_signals () and rl_clear_signals ().
Fri May 8 12:50:15 1992 Brian Fox (bfox@cubit)
* readline.c: (readline_default_bindings) Do comparisons with
_POSIX_VDISABLE casted to `unsigned char'. Change tty characters
to be unsigned char.
Thu Apr 30 12:36:35 1992 Brian Fox (bfox@cubit)
* readline.c: (rl_getc) Handle "read would block" error on
non-blocking IO streams.
* readline.c: (rl_signal_handler): Unblock only the signal that we
have caught, not all signals.
Sun Feb 23 03:33:09 1992 Brian Fox (bfox at gnuwest.fsf.org)
* readline.c: Many functions. Use only the macros META_CHAR and
UNMETA to deal with meta characters. Prior to this, we used
numeric values and tests.
* readline.c (rl_complete_internal) Report exactly the number of
possible completions, not the number + 1.
* vi_mode.c (rl_do_move) Do not change the cursor position when
using `cw' or `cW'.
* vi_mode.c (rl_vi_complete) Enter insert mode after completing
with `*' or `\'.
Fri Feb 21 05:58:18 1992 Brian Fox (bfox at gnuwest.fsf.org)
* readline.c (rl_dispatch) Increment rl_key_sequence_length for
meta characters that map onto ESC map.
Mon Feb 10 01:41:35 1992 Brian Fox (bfox at gnuwest.fsf.org)
* history.c (history_do_write) Build a buffer of all of the lines
to write and write them in one fell swoop (lower overhead than
calling write () for each line). Suggested by Peter Ho.
* readline.c: Include hbullx20 as well as hpux for determining
USGr3ness.
* readline.c (rl_unix_word_rubout) As per the "Now REMEMBER"
comment, pass arguments to rl_kill_text () in the correct order to
preserve prepending and appending of killed text.
* readline.c (rl_search_history) malloc (), realloc (), and free
() SEARCH_STRING so that there are no static limits on searching.
* vi_mode.c (rl_vi_subst) Don't forget to end the undo group.
Fri Jan 31 14:51:02 1992 Brian Fox (bfox at gnuwest.fsf.org)
* readline.c (rl_signal_handler): Zero the current history entry's
pointer after freeing the undo_list when SIGINT received.
Reformat a couple of functions.
Sat Jan 25 13:47:35 1992 Brian Fox (bfox at bears)
* readline.c (parser_if): free () TNAME after use.
Tue Jan 21 01:01:35 1992 Brian Fox (bfox at gnuwest.fsf.org)
* readline.c (rl_redisplay) and (rl_character_len): Display
Control characters as "^c" and Meta characters as "\234", instead
of "C-C" and "M-C".
Sun Dec 29 10:59:00 1991 Brian Fox (bfox at gnuwest.fsf.org)
* readline.c (init_terminal_io) Default to environment variables
LINES and COLUMNS before termcap entry values. If all else fails,
then assume 80x24 terminal.
Sat Dec 28 16:33:11 1991 Brian Fox (bfox at gnuwest.fsf.org)
* readline.c: If this machine is USG and it is hpux, then define
USGr3.
* history.c: Cosmetic fixes.
Thu Nov 21 00:10:12 1991 Brian Fox (bfox at gnuwest.fsf.org)
* vi_mode.c: (rl_do_move) Place cursor at end of line, never at
next to last character.
Thu Nov 14 05:08:01 1991 Brian Fox (bfox at gnuwest.fsf.org)
* history.c (get_history_event) Non-anchored searches can have a
return index of greater than zero from get_history_event ().
Fri Nov 1 07:02:13 1991 Brian Fox (bfox at gnuwest.fsf.org)
* readline.c (rl_translate_keyseq) Make C-? translate to RUBOUT
unconditionally.
Mon Oct 28 11:34:52 1991 Brian Fox (bfox at gnuwest.fsf.org)
* readline.c; Use Posix directory routines and macros.
* funmap.c; Add entry for call-last-kbd-macro.
* readline.c (rl_prep_term); Use system EOF character on POSIX
systems also.
Thu Oct 3 16:19:53 1991 Brian Fox (bfox at gnuwest.fsf.org)
* readline.c; Make a distinction between having a TERMIOS tty
driver, and having POSIX signal handling. You might one without
the other. New defines used HAVE_POSIX_SIGNALS, and
TERMIOS_TTY_DRIVER.
Tue Jul 30 22:37:26 1991 Brian Fox (bfox at gnuwest.fsf.org)
* readline.c: rl_getc () If a call to read () returns without an
error, but with zero characters, the file is empty, so return EOF.
Thu Jul 11 20:58:38 1991 Brian Fox (bfox at gnuwest.fsf.org)
* readline.c: (rl_get_next_history, rl_get_previous_history)
Reallocate the buffer space if the line being moved to is longer
the the current space allocated. Amazing that no one has found
this bug until now.
Sun Jul 7 02:37:05 1991 Brian Fox (bfox at gnuwest.fsf.org)
* readline.c:(rl_parse_and_bind) Allow leading whitespace.
Make sure TERMIO and TERMIOS systems treat CR and NL
disctinctly.
Tue Jun 25 04:09:27 1991 Brian Fox (bfox at gnuwest.fsf.org)
* readline.c: Rework parsing conditionals to pay attention to the
prior states of the conditional stack. This makes $if statements
work correctly.
Mon Jun 24 20:45:59 1991 Brian Fox (bfox at gnuwest.fsf.org)
* readline.c: support for displaying key binding information
includes the functions rl_list_funmap_names (),
invoking_keyseqs_in_map (), rl_invoking_keyseqs (),
rl_dump_functions (), and rl_function_dumper ().
funmap.c: support for same includes rl_funmap_names ().
readline.c, funmap.c: no longer define STATIC_MALLOC. However,
update both version of xrealloc () to handle a null pointer.
Thu Apr 25 12:03:49 1991 Brian Fox (bfox at gnuwest.fsf.org)
* vi_mode.c (rl_vi_fword, fWord, etc. All functions use
the macro `isident()'. Fixed movement bug which prevents
continious movement through the text.
Fri Jul 27 16:47:01 1990 Brian Fox (bfox at gnuwest.fsf.org)
* readline.c (parser_if) Allow "$if term=foo" construct.
Wed May 23 16:10:33 1990 Brian Fox (bfox at gnuwest.fsf.org)
* readline.c (rl_dispatch) Correctly remember the last command
executed. Fixed typo in username_completion_function ().
Mon Apr 9 19:55:48 1990 Brian Fox (bfox at gnuwest.fsf.org)
* readline.c: username_completion_function (); For text passed in
with a leading `~', remember that this could be a filename (after
it is completed).
Thu Apr 5 13:44:24 1990 Brian Fox (bfox at gnuwest.fsf.org)
* readline.c: rl_search_history (): Correctly handle case of an
unfound search string, but a graceful exit (as with ESC).
* readline.c: rl_restart_output (); The Apollo passes the address
of the file descriptor to TIOCSTART, not the descriptor itself.
Tue Mar 20 05:38:55 1990 Brian Fox (bfox at gnuwest.fsf.org)
* readline.c: rl_complete (); second call in a row causes possible
completions to be listed.
* readline.c: rl_redisplay (), added prompt_this_line variable
which is the first character character following \n in prompt.
Sun Mar 11 04:32:03 1990 Brian Fox (bfox at gnuwest.fsf.org)
* Signals are now supposedly handled inside of SYSV compilation.
Wed Jan 17 19:24:09 1990 Brian Fox (bfox at sbphy.ucsb.edu)
* history.c: history_expand (); fixed overwriting memory error,
added needed argument to call to get_history_event ().
Thu Jan 11 10:54:04 1990 Brian Fox (bfox at sbphy.ucsb.edu)
* readline.c: added mark_modified_lines to control the
display of an asterisk on modified history lines. Also
added a user variable called mark-modified-lines to the
`set' command.
Thu Jan 4 10:38:05 1990 Brian Fox (bfox at sbphy.ucsb.edu)
* readline.c: start_insert (). Only use IC if we don't have an im
capability.
Fri Sep 8 09:00:45 1989 Brian Fox (bfox at aurel)
* readline.c: rl_prep_terminal (). Only turn on 8th bit
as meta-bit iff the terminal is not using parity.
Sun Sep 3 08:57:40 1989 Brian Fox (bfox at aurel)
* readline.c: start_insert (). Uses multiple
insertion call in cases where that makes sense.
rl_insert (). Read type-ahead buffer for additional
keys that are bound to rl_insert, and insert them
all at once. Make insertion of single keys given
with an argument much more efficient.
Tue Aug 8 18:13:57 1989 Brian Fox (bfox at aurel)
* readline.c: Changed handling of EOF. readline () returns
(char *)EOF or consed string. The EOF character is read from the
tty, or if the tty doesn't have one, defaults to C-d.
* readline.c: Added support for event driven programs.
rl_event_hook is the address of a function you want called
while Readline is waiting for input.
* readline.c: Cleanup time. Functions without type declarations
do not use return with a value.
* history.c: history_expand () has new variable which is the
characters to ignore immediately following history_expansion_char.
Sun Jul 16 08:14:00 1989 Brian Fox (bfox at aurel)
* rl_prep_terminal ()
BSD version turns off C-s, C-q, C-y, C-v.
* readline.c -- rl_prep_terminal ()
SYSV version hacks readline_echoing_p.
BSD version turns on passing of the 8th bit for the duration
of reading the line.
Tue Jul 11 06:25:01 1989 Brian Fox (bfox at aurel)
* readline.c: new variable rl_tilde_expander.
If non-null, this contains the address of a function to call if
the standard meaning for expanding a tilde fails. The function is
called with the text sans tilde (as in "foo"), and returns a
malloc()'ed string which is the expansion, or a NULL pointer if
there is no expansion.
* readline.h - new file chardefs.h
Separates things that only readline.c needs from the standard
header file publishing interesting things about readline.
* readline.c:
readline_default_bindings () now looks at terminal chararacters
and binds those as well.
Wed Jun 28 20:20:51 1989 Brian Fox (bfox at aurel)
* Made readline and history into independent libraries.

134
lib/readline/Makefile Normal file
View file

@ -0,0 +1,134 @@
## -*- text -*- ####################################################
# #
# Makefile for the GNU Readline and History Libraries. #
# #
####################################################################
srcdir = .
VPATH = .:$(srcdir)
INSTALL = install -c
INSTALL_PROGRAM = ${INSTALL}
INSTALL_DATA = ${INSTALL} -m 644
RANLIB = ranlib
AR = ar
RM = rm
CP = cp
MV = mv
# See the file STANDALONE for the -D defines that readline understands
DEFS =
# For libraries which include headers from other libraries.
LOCAL_INCLUDES = -I. -I..
CPPFLAGS = $(DEFS) $(LOCAL_INCLUDES)
# Here is a rule for making .o files from .c files that doesn't force
# the type of the machine (like -sun3) into the flags.
.c.o:
$(CC) -c $(CPPFLAGS) $(CFLAGS) $<
# The name of the main library target.
LIBRARY_NAME = libreadline.a
# The C code source files for this library.
CSOURCES = $(srcdir)readline.c $(srcdir)funmap.c $(srcdir)keymaps.c \
$(srcdir)vi_mode.c $(srcdir)parens.c $(srcdir)rltty.c \
$(srcdir)complete.c $(srcdir)bind.c $(srcdir)isearch.c \
$(srcdir)display.c $(srcdir)signals.c $(srcdir)emacs_keymap.c \
$(srcdir)vi_keymap.c $(srcdir)history.c $(srcdir)tilde.c \
$(srcdir)xmalloc.c
# The header files for this library.
HSOURCES = readline.h rldefs.h chardefs.h keymaps.h history.h \
posixstat.h tilde.h rlconf.h
OBJECTS = readline.o vi_mode.o funmap.o keymaps.o parens.o search.o \
rltty.o complete.o bind.o isearch.o display.o signals.o \
history.o tilde.o xmalloc.o
# The texinfo files which document this library.
DOCSOURCE = doc/rlman.texinfo doc/rltech.texinfo doc/rluser.texinfo
DOCOBJECT = doc/readline.dvi
DOCSUPPORT = doc/Makefile
DOCUMENTATION = $(DOCSOURCE) $(DOCOBJECT) $(DOCSUPPORT)
SUPPORT = Makefile ChangeLog $(DOCSUPPORT) examples/[-a-z.]*
SOURCES = $(CSOURCES) $(HSOURCES) $(DOCSOURCE)
THINGS_TO_TAR = $(SOURCES) $(SUPPORT)
##########################################################################
all: libreadline.a libhistory.a
libreadline.a: $(OBJECTS)
$(RM) -f $@
$(AR) cq $@ $(OBJECTS)
-[ -n "$(RANLIB)" ] && $(RANLIB) $@
libhistory.a: history.o
$(RM) -f $@
$(AR) cq $@ history.o
-[ -n "$(RANLIB)" ] && $(RANLIB) $@
documentation: force
[ ! -d doc ] && mkdir doc
(if [ -d doc ]; then cd doc; $(MAKE) $(MFLAGS); fi)
force:
# The rule for 'includes' is written funny so that the if statement
# always returns TRUE unless there really was an error installing the
# include files.
install: installdirs libreadline.a
${INSTALL_DATA} readline.h keymaps.h chardefs.h history.h \
$(incdir)/readline
-${MV} $(libdir)/libreadline.a $(libdir)/libreadline.old
${INSTALL_DATA} libreadline.a $(bindir)/libreadline.a
-[ -n "$(RANLIB)" ] && $(RANLIB) -t $(bindir)/libreadline.a
installdirs:
[ ! -d $(incdir)/readline ] && { \
mkdir $(incdir)/readline && chmod chmod 755 $(incdir)/readline; }
uninstall:
cd $(incdir)/readline && ${RM} -f ${INSTALLED_HEADERS}
cd $(libdir) && ${RM} -f libreadline.a libreadline.old
tags: force
etags $(CSOURCES) $(HSOURCES)
TAGS: force
ctags -x $(CSOURCES) $(HSOURCES) > $@
readline: readline.h rldefs.h chardefs.h
readline: $(OBJECTS)
$(CC) $(CFLAGS) $(CPPFLAGS) $(READLINE_DEFINES) \
$(LOCAL_INCLUDES) -DTEST -o readline readline.c vi_mode.o funmap.o \
keymaps.o -ltermcap
clean:
$(RM) -f $(OBJECTS) libreadline.a libhistory.a
(if [ -d doc ]; then cd doc; $(MAKE) $(MFLAGS) $@; fi)
maintainer-clean realclean distclean mostlyclean: clean
(if [ -d doc ]; then cd doc; $(MAKE) $(MFLAGS) $@; fi)
# Dependencies
readline.o: readline.c readline.h rldefs.h rlconf.h chardefs.h
readline.o: keymaps.h history.h
vi_mode.o: rldefs.h rlconf.h readline.h history.h
funmap.o: funmap.c readline.h rlconf.h
keymaps.o: keymaps.c emacs_keymap.c vi_keymap.c keymaps.h chardefs.h rlconf.h
history.o: history.h memalloc.h
isearch.o: memalloc.h readline.h history.h
search.o: memalloc.h readline.h history.h
display.o: readline.h history.h rldefs.h rlconf.h
complete.o: readline.h rldefs.h rlconf.h
rltty.o: rldefs.h rlconf.h readline.h
bind.o: rldefs.h rlconf.h readline.h history.h
signals.o: rldefs.h rlconf.h readline.h history.h
parens.o: readline.h

6
lib/readline/README Normal file
View file

@ -0,0 +1,6 @@
This is the distribution of the Gnu Readline library. See the file
STANDALONE for a description of the #defines that can be passed via
the makefile to build readline on different systems.
The file rlconf.h contains defines that enable and disable certain
readline features.

31
lib/readline/STANDALONE Normal file
View file

@ -0,0 +1,31 @@
This is a description of C preprocessor defines that readline accepts.
Most are passed in from the parent `make'; e.g. from the bash source
directory.
NO_SYS_FILE <sys/file.h> is not present
HAVE_UNISTD_H <unistd.h> exists
HAVE_STDLIB_H <stdlib.h> exists
HAVE_VARARGS_H <varargs.h> exists and is usable
HAVE_STRING_H <string.h> exists
HAVE_ALLOCA_H <alloca.h> exists and is needed for alloca()
HAVE_ALLOCA alloca(3) or a define for it exists
PRAGMA_ALLOCA use of alloca() requires a #pragma, as in AIX 3.x
VOID_SIGHANDLER signal handlers are void functions
HAVE_DIRENT_H <dirent.h> exists and is usable
HAVE_SYS_PTEM_H <sys/ptem.h> exists
HAVE_SYS_PTE_H <sys/pte.h> exists
HAVE_SYS_STREAM_H <sys/stream.h> exists
System-specific options:
GWINSZ_IN_SYS_IOCTL need to include <sys/ioctl.h> for TIOCGWINSZ
HAVE_GETPW_DECLS the getpw* functions are declared in <pwd.h> and cannot
be redeclared without compiler errors
HAVE_STRCASECMP the strcasecmp and strncasecmp functions are available
USG Running a variant of System V
USGr3 Running System V.3
XENIX_22 Xenix 2.2
Linux Linux
CRAY running a recent version of Cray UNICOS
SunOS4 Running SunOS 4.x

View file

@ -0,0 +1,41 @@
/* ansi_stdlib.h -- An ANSI Standard stdlib.h. */
/* A minimal stdlib.h containing extern declarations for those functions
that bash uses. */
/* Copyright (C) 1993 Free Software Foundation, Inc.
This file is part of GNU Bash, the Bourne Again SHell.
Bash is free software; you can redistribute it and/or modify it under
the terms of the GNU General Public License as published by the Free
Software Foundation; either version 2, or (at your option) any later
version.
Bash is distributed in the hope that it will be useful, but WITHOUT ANY
WARRANTY; without even the implied warranty of MERCHANTABILITY or
FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
for more details.
You should have received a copy of the GNU General Public License along
with Bash; see the file COPYING. If not, write to the Free Software
Foundation, 675 Mass Ave, Cambridge, MA 02139, USA. */
#if !defined (_STDLIB_H_)
#define _STDLIB_H_ 1
/* String conversion functions. */
extern int atoi ();
extern long int atol ();
/* Memory allocation functions. */
extern char *malloc ();
extern char *realloc ();
extern void free ();
/* Other miscellaneous functions. */
extern void abort ();
extern void exit ();
extern char *getenv ();
extern void qsort ();
#endif /* _STDLIB_H */

1487
lib/readline/bind.c Normal file

File diff suppressed because it is too large Load diff

122
lib/readline/chardefs.h Normal file
View file

@ -0,0 +1,122 @@
/* chardefs.h -- Character definitions for readline. */
/* Copyright (C) 1994 Free Software Foundation, Inc.
This file is part of the GNU Readline Library, a library for
reading lines of text with interactive input and history editing.
The GNU Readline Library is free software; you can redistribute it
and/or modify it under the terms of the GNU General Public License
as published by the Free Software Foundation; either version 1, or
(at your option) any later version.
The GNU Readline Library is distributed in the hope that it will be
useful, but WITHOUT ANY WARRANTY; without even the implied warranty
of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
The GNU General Public License is often shipped with GNU software, and
is generally kept in a file called COPYING or LICENSE. If you do not
have a copy of the license, write to the Free Software Foundation,
675 Mass Ave, Cambridge, MA 02139, USA. */
#ifndef _CHARDEFS_H
#define _CHARDEFS_H
#include <ctype.h>
#if defined (HAVE_STRING_H)
# include <string.h>
#else
# include <strings.h>
#endif /* HAVE_STRING_H */
#ifndef whitespace
#define whitespace(c) (((c) == ' ') || ((c) == '\t'))
#endif
#ifdef CTRL
#undef CTRL
#endif
/* Some character stuff. */
#define control_character_threshold 0x020 /* Smaller than this is control. */
#define control_character_mask 0x1f /* 0x20 - 1 */
#define meta_character_threshold 0x07f /* Larger than this is Meta. */
#define control_character_bit 0x40 /* 0x000000, must be off. */
#define meta_character_bit 0x080 /* x0000000, must be on. */
#define largest_char 255 /* Largest character value. */
#define CTRL_CHAR(c) ((c) < control_character_threshold)
#define META_CHAR(c) ((c) > meta_character_threshold && (c) <= largest_char)
#define CTRL(c) ((c) & control_character_mask)
#define META(c) ((c) | meta_character_bit)
#define UNMETA(c) ((c) & (~meta_character_bit))
#define UNCTRL(c) to_upper(((c)|control_character_bit))
/* Old versions
#define lowercase_p(c) (((c) > ('a' - 1) && (c) < ('z' + 1)))
#define uppercase_p(c) (((c) > ('A' - 1) && (c) < ('Z' + 1)))
#define digit_p(c) ((c) >= '0' && (c) <= '9')
*/
#define lowercase_p(c) (islower(c))
#define uppercase_p(c) (isupper(c))
#define digit_p(x) (isdigit (x))
#define pure_alphabetic(c) (lowercase_p(c) || uppercase_p(c))
/* Old versions
# define to_upper(c) (lowercase_p(c) ? ((c) - 32) : (c))
# define to_lower(c) (uppercase_p(c) ? ((c) + 32) : (c))
*/
#ifndef to_upper
# define to_upper(c) (islower(c) ? toupper(c) : (c))
# define to_lower(c) (isupper(c) ? tolower(c) : (c))
#endif
#ifndef digit_value
#define digit_value(x) ((x) - '0')
#endif
#ifndef NEWLINE
#define NEWLINE '\n'
#endif
#ifndef RETURN
#define RETURN CTRL('M')
#endif
#ifndef RUBOUT
#define RUBOUT 0x7f
#endif
#ifndef TAB
#define TAB '\t'
#endif
#ifdef ABORT_CHAR
#undef ABORT_CHAR
#endif
#define ABORT_CHAR CTRL('G')
#ifdef PAGE
#undef PAGE
#endif
#define PAGE CTRL('L')
#ifdef SPACE
#undef SPACE
#endif
#define SPACE ' ' /* XXX - was 0x20 */
#ifdef ESC
#undef ESC
#endif
#define ESC CTRL('[')
#endif /* _CHARDEFS_H */

1459
lib/readline/complete.c Normal file

File diff suppressed because it is too large Load diff

1276
lib/readline/display.c Normal file

File diff suppressed because it is too large Load diff

55
lib/readline/doc/Makefile Normal file
View file

@ -0,0 +1,55 @@
# This makefile for History library documentation is in -*- text -*- mode.
# Emacs likes it that way.
DOC_SUPPORT = ../../doc-support/
TEXINDEX = $(DOC_SUPPORT)/texindex
TEX = tex
RLSRC = rlman.texinfo rluser.texinfo rltech.texinfo
HISTSRC = hist.texinfo hsuser.texinfo hstech.texinfo
DVIOBJ = readline.dvi history.dvi
INFOOBJ = readline.info history.info
PSOBJ = readline.ps history.ps
all: info dvi
readline.dvi: $(RLSRC)
$(TEX) rlman.texinfo
$(TEXINDEX) rlman.??
$(TEX) rlman.texinfo
mv rlman.dvi readline.dvi
readline.info: $(RLSRC)
makeinfo rlman.texinfo
history.dvi: ${HISTSRC}
$(TEX) hist.texinfo
$(TEXINDEX) hist.??
$(TEX) hist.texinfo
mv hist.dvi history.dvi
history.info: ${HISTSRC}
makeinfo hist.texinfo
readline.ps: readline.dvi
dvips -D 300 -o $@ readline.dvi
history.ps: history.dvi
dvips -D 300 -o $@ history.dvi
info: $(INFOOBJ)
dvi: $(DVIOBJ)
ps: $(PSOBJ)
$(TEXINDEX):
(cd $(DOC_SUPPORT); $(MAKE) $(MFLAGS) CFLAGS='$(CFLAGS)' texindex)
distclean mostlyclean clean:
rm -f *.aux *.cp *.fn *.ky *.log *.pg *.toc *.tp *.vr *.cps *.pgs \
*.fns *.kys *.tps *.vrs *.o core
maintainer-clean realclean: clean
rm -f *.dvi *.info *.info-* *.ps

View file

@ -0,0 +1,113 @@
\input texinfo @c -*-texinfo-*-
@c %**start of header (This is for running Texinfo on a region.)
@setfilename history.info
@settitle GNU History Library
@c %**end of header (This is for running Texinfo on a region.)
@setchapternewpage odd
@ignore
last change: Wed Jul 20 09:57:17 EDT 1994
@end ignore
@set EDITION 2.0
@set VERSION 2.0
@set UPDATED 20 July 1994
@set UPDATE-MONTH July 1994
@ifinfo
This document describes the GNU History library, a programming tool that
provides a consistent user interface for recalling lines of previously
typed input.
Copyright (C) 1988, 1991 Free Software Foundation, Inc.
Permission is granted to make and distribute verbatim copies of
this manual provided the copyright notice and this permission notice
pare preserved on all copies.
@ignore
Permission is granted to process this file through TeX and print the
results, provided the printed document carries copying permission
notice identical to this one except for the removal of this paragraph
(this paragraph not being relevant to the printed manual).
@end ignore
Permission is granted to copy and distribute modified versions of this
manual under the conditions for verbatim copying, provided that the entire
resulting derived work is distributed under the terms of a permission
notice identical to this one.
Permission is granted to copy and distribute translations of this manual
into another language, under the above conditions for modified versions,
except that this permission notice may be stated in a translation approved
by the Foundation.
@end ifinfo
@titlepage
@sp 10
@title GNU History Library
@subtitle Edition @value{EDITION}, for @code{History Library} Version @value{VERSION}.
@subtitle @value{UPDATE-MONTH}
@author Brian Fox, Free Software Foundation
@author Chet Ramey, Case Western Reserve University
@page
This document describes the GNU History library, a programming tool that
provides a consistent user interface for recalling lines of previously
typed input.
Published by the Free Software Foundation @*
675 Massachusetts Avenue, @*
Cambridge, MA 02139 USA
Permission is granted to make and distribute verbatim copies of
this manual provided the copyright notice and this permission notice
are preserved on all copies.
Permission is granted to copy and distribute modified versions of this
manual under the conditions for verbatim copying, provided that the entire
resulting derived work is distributed under the terms of a permission
notice identical to this one.
Permission is granted to copy and distribute translations of this manual
into another language, under the above conditions for modified versions,
except that this permission notice may be stated in a translation approved
by the Foundation.
@vskip 0pt plus 1filll
Copyright @copyright{} 1989, 1991 Free Software Foundation, Inc.
@end titlepage
@ifinfo
@node Top
@top GNU History Library
This document describes the GNU History library, a programming tool that
provides a consistent user interface for recalling lines of previously
typed input.
@menu
* Using History Interactively:: GNU History User's Manual.
* Programming with GNU History:: GNU History Programmer's Manual.
* Concept Index:: Index of concepts described in this manual.
* Function and Variable Index:: Index of externally visible functions
and variables.
@end menu
@end ifinfo
@syncodeindex fn vr
@include hsuser.texinfo
@include hstech.texinfo
@node Concept Index
@appendix Concept Index
@printindex cp
@node Function and Variable Index
@appendix Function and Variable Index
@printindex vr
@contents
@bye

Binary file not shown.

View file

@ -0,0 +1,744 @@
This is Info file history.info, produced by Makeinfo-1.55 from the
input file hist.texinfo.
This document describes the GNU History library, a programming tool
that provides a consistent user interface for recalling lines of
previously typed input.
Copyright (C) 1988, 1991 Free Software Foundation, Inc.
Permission is granted to make and distribute verbatim copies of this
manual provided the copyright notice and this permission notice pare
preserved on all copies.
Permission is granted to copy and distribute modified versions of
this manual under the conditions for verbatim copying, provided that
the entire resulting derived work is distributed under the terms of a
permission notice identical to this one.
Permission is granted to copy and distribute translations of this
manual into another language, under the above conditions for modified
versions, except that this permission notice may be stated in a
translation approved by the Foundation.

File: history.info, Node: Top, Next: Using History Interactively, Prev: (DIR), Up: (DIR)
GNU History Library
*******************
This document describes the GNU History library, a programming tool
that provides a consistent user interface for recalling lines of
previously typed input.
* Menu:
* Using History Interactively:: GNU History User's Manual.
* Programming with GNU History:: GNU History Programmer's Manual.
* Concept Index:: Index of concepts described in this manual.
* Function and Variable Index:: Index of externally visible functions
and variables.

File: history.info, Node: Using History Interactively, Next: Programming with GNU History, Prev: Top, Up: Top
Using History Interactively
***************************
This chapter describes how to use the GNU History Library
interactively, from a user's standpoint. It should be considered a
user's guide. For information on using the GNU History Library in your
own programs, *note Programming with GNU History::..
* Menu:
* History Interaction:: What it feels like using History as a user.

File: history.info, Node: History Interaction, Up: Using History Interactively
History Interaction
===================
The History library provides a history expansion feature that is
similar to the history expansion provided by `csh'. The following text
describes the syntax used to manipulate the history information.
History expansion takes place in two parts. The first is to
determine which line from the previous history should be used during
substitution. The second is to select portions of that line for
inclusion into the current one. The line selected from the previous
history is called the "event", and the portions of that line that are
acted upon are called "words". The line is broken into words in the
same fashion that Bash does, so that several English (or Unix) words
surrounded by quotes are considered as one word.
* Menu:
* Event Designators:: How to specify which history line to use.
* Word Designators:: Specifying which words are of interest.
* Modifiers:: Modifying the results of substitution.

File: history.info, Node: Event Designators, Next: Word Designators, Up: History Interaction
Event Designators
-----------------
An event designator is a reference to a command line entry in the
history list.
`!'
Start a history substitution, except when followed by a space, tab,
the end of the line, = or (.
`!!'
Refer to the previous command. This is a synonym for `!-1'.
`!n'
Refer to command line N.
`!-n'
Refer to the command N lines back.
`!string'
Refer to the most recent command starting with STRING.
`!?string'[`?']
Refer to the most recent command containing STRING.
`!#'
The entire command line typed so far.
`^string1^string2^'
Quick Substitution. Repeat the last command, replacing STRING1
with STRING2. Equivalent to `!!:s/string1/string2/'.

File: history.info, Node: Word Designators, Next: Modifiers, Prev: Event Designators, Up: History Interaction
Word Designators
----------------
A : separates the event specification from the word designator. It
can be omitted if the word designator begins with a ^, $, * or %.
Words are numbered from the beginning of the line, with the first word
being denoted by a 0 (zero).
`0 (zero)'
The `0'th word. For many applications, this is the command word.
`n'
The Nth word.
`^'
The first argument; that is, word 1.
`$'
The last argument.
`%'
The word matched by the most recent `?string?' search.
`x-y'
A range of words; `-Y' abbreviates `0-Y'.
`*'
All of the words, except the `0'th. This is a synonym for `1-$'.
It is not an error to use * if there is just one word in the event;
the empty string is returned in that case.
`x*'
Abbreviates `x-$'
`x-'
Abbreviates `x-$' like `x*', but omits the last word.

File: history.info, Node: Modifiers, Prev: Word Designators, Up: History Interaction
Modifiers
---------
After the optional word designator, you can add a sequence of one or
more of the following modifiers, each preceded by a :.
`h'
Remove a trailing pathname component, leaving only the head.
`r'
Remove a trailing suffix of the form `.'SUFFIX, leaving the
basename.
`e'
Remove all but the trailing suffix.
`t'
Remove all leading pathname components, leaving the tail.
`p'
Print the new command but do not execute it.
`s/old/new/'
Substitute NEW for the first occurrence of OLD in the event line.
Any delimiter may be used in place of /. The delimiter may be
quoted in OLD and NEW with a single backslash. If & appears in
NEW, it is replaced by OLD. A single backslash will quote the &.
The final delimiter is optional if it is the last character on the
input line.
`&'
Repeat the previous substitution.
`g'
Cause changes to be applied over the entire event line. Used in
conjunction with `s', as in `gs/old/new/', or with `&'.

File: history.info, Node: Programming with GNU History, Next: Concept Index, Prev: Using History Interactively, Up: Top
Programming with GNU History
****************************
This chapter describes how to interface programs that you write with
the GNU History Library. It should be considered a technical guide.
For information on the interactive use of GNU History, *note Using
History Interactively::..
* Menu:
* Introduction to History:: What is the GNU History library for?
* History Storage:: How information is stored.
* History Functions:: Functions that you can use.
* History Variables:: Variables that control behaviour.
* History Programming Example:: Example of using the GNU History Library.

File: history.info, Node: Introduction to History, Next: History Storage, Up: Programming with GNU History
Introduction to History
=======================
Many programs read input from the user a line at a time. The GNU
History library is able to keep track of those lines, associate
arbitrary data with each line, and utilize information from previous
lines in composing new ones.
The programmer using the History library has available functions for
remembering lines on a history list, associating arbitrary data with a
line, removing lines from the list, searching through the list for a
line containing an arbitrary text string, and referencing any line in
the list directly. In addition, a history "expansion" function is
available which provides for a consistent user interface across
different programs.
The user using programs written with the History library has the
benefit of a consistent user interface with a set of well-known
commands for manipulating the text of previous lines and using that text
in new commands. The basic history manipulation commands are similar to
the history substitution provided by `csh'.
If the programmer desires, he can use the Readline library, which
includes some history manipulation by default, and has the added
advantage of command line editing.

File: history.info, Node: History Storage, Next: History Functions, Prev: Introduction to History, Up: Programming with GNU History
History Storage
===============
The history list is an array of history entries. A history entry is
declared as follows:
typedef struct _hist_entry {
char *line;
char *data;
} HIST_ENTRY;
The history list itself might therefore be declared as
HIST_ENTRY **the_history_list;
The state of the History library is encapsulated into a single
structure:
/* A structure used to pass the current state of the history stuff around. */
typedef struct _hist_state {
HIST_ENTRY **entries; /* Pointer to the entries themselves. */
int offset; /* The location pointer within this array. */
int length; /* Number of elements within this array. */
int size; /* Number of slots allocated to this array. */
int flags;
} HISTORY_STATE;
If the flags member includes `HS_STIFLED', the history has been
stifled.

File: history.info, Node: History Functions, Next: History Variables, Prev: History Storage, Up: Programming with GNU History
History Functions
=================
This section describes the calling sequence for the various functions
present in GNU History.
* Menu:
* Initializing History and State Management:: Functions to call when you
want to use history in a
program.
* History List Management:: Functions used to manage the list
of history entries.
* Information About the History List:: Functions returning information about
the history list.
* Moving Around the History List:: Functions used to change the position
in the history list.
* Searching the History List:: Functions to search the history list
for entries containing a string.
* Managing the History File:: Functions that read and write a file
containing the history list.
* History Expansion:: Functions to perform csh-like history
expansion.

File: history.info, Node: Initializing History and State Management, Next: History List Management, Up: History Functions
Initializing History and State Management
-----------------------------------------
This section describes functions used to initialize and manage the
state of the History library when you want to use the history functions
in your program.
- Function: void using_history ()
Begin a session in which the history functions might be used. This
initializes the interactive variables.
- Function: HISTORY_STATE * history_get_history_state ()
Return a structure describing the current state of the input
history.
- Function: void history_set_history_state (HISTORY_STATE *state)
Set the state of the history list according to STATE.

File: history.info, Node: History List Management, Next: Information About the History List, Prev: Initializing History and State Management, Up: History Functions
History List Management
-----------------------
These functions manage individual entries on the history list, or set
parameters managing the list itself.
- Function: void add_history (char *string)
Place STRING at the end of the history list. The associated data
field (if any) is set to `NULL'.
- Function: HIST_ENTRY * remove_history (int which)
Remove history entry at offset WHICH from the history. The
removed element is returned so you can free the line, data, and
containing structure.
- Function: HIST_ENTRY * replace_history_entry (int which, char *line,
char *data)
Make the history entry at offset WHICH have LINE and DATA. This
returns the old entry so you can dispose of the data. In the case
of an invalid WHICH, a `NULL' pointer is returned.
- Function: void stifle_history (int max)
Stifle the history list, remembering only the last MAX entries.
- Function: int unstifle_history ()
Stop stifling the history. This returns the previous amount the
history was stifled. The value is positive if the history was
stifled, negative if it wasn't.
- Function: int history_is_stifled ()
Returns non-zero if the history is stifled, zero if it is not.

File: history.info, Node: Information About the History List, Next: Moving Around the History List, Prev: History List Management, Up: History Functions
Information About the History List
----------------------------------
These functions return information about the entire history list or
individual list entries.
- Function: HIST_ENTRY ** history_list ()
Return a `NULL' terminated array of `HIST_ENTRY' which is the
current input history. Element 0 of this list is the beginning of
time. If there is no history, return `NULL'.
- Function: int where_history ()
Returns the offset of the current history element.
- Function: HIST_ENTRY * current_history ()
Return the history entry at the current position, as determined by
`where_history ()'. If there is no entry there, return a `NULL'
pointer.
- Function: HIST_ENTRY * history_get (int offset)
Return the history entry at position OFFSET, starting from
`history_base'. If there is no entry there, or if OFFSET is
greater than the history length, return a `NULL' pointer.
- Function: int history_total_bytes ()
Return the number of bytes that the primary history entries are
using. This function returns the sum of the lengths of all the
lines in the history.

File: history.info, Node: Moving Around the History List, Next: Searching the History List, Prev: Information About the History List, Up: History Functions
Moving Around the History List
------------------------------
These functions allow the current index into the history list to be
set or changed.
- Function: int history_set_pos (int pos)
Set the position in the history list to POS, an absolute index
into the list.
- Function: HIST_ENTRY * previous_history ()
Back up the current history offset to the previous history entry,
and return a pointer to that entry. If there is no previous
entry, return a `NULL' pointer.
- Function: HIST_ENTRY * next_history ()
Move the current history offset forward to the next history entry,
and return the a pointer to that entry. If there is no next
entry, return a `NULL' pointer.

File: history.info, Node: Searching the History List, Next: Managing the History File, Prev: Moving Around the History List, Up: History Functions
Searching the History List
--------------------------
These functions allow searching of the history list for entries
containing a specific string. Searching may be performed both forward
and backward from the current history position. The search may be
"anchored", meaning that the string must match at the beginning of the
history entry.
- Function: int history_search (char *string, int direction)
Search the history for STRING, starting at the current history
offset. If DIRECTION < 0, then the search is through previous
entries, else through subsequent. If STRING is found, then the
current history index is set to that history entry, and the value
returned is the offset in the line of the entry where STRING was
found. Otherwise, nothing is changed, and a -1 is returned.
- Function: int history_search_prefix (char *string, int direction)
Search the history for STRING, starting at the current history
offset. The search is anchored: matching lines must begin with
STRING. If DIRECTION < 0, then the search is through previous
entries, else through subsequent. If STRING is found, then the
current history index is set to that entry, and the return value
is 0. Otherwise, nothing is changed, and a -1 is returned.
- Function: int history_search_pos (char *string, int direction, int
pos)
Search for STRING in the history list, starting at POS, an
absolute index into the list. If DIRECTION is negative, the search
proceeds backward from POS, otherwise forward. Returns the
absolute index of the history element where STRING was found, or
-1 otherwise.

File: history.info, Node: Managing the History File, Next: History Expansion, Prev: Searching the History List, Up: History Functions
Managing the History File
-------------------------
The History library can read the history from and write it to a file.
This section documents the functions for managing a history file.
- Function: int read_history (char *filename)
Add the contents of FILENAME to the history list, a line at a
time. If FILENAME is `NULL', then read from `~/.history'.
Returns 0 if successful, or errno if not.
- Function: int read_history_range (char *filename, int from, int to)
Read a range of lines from FILENAME, adding them to the history
list. Start reading at line FROM and end at TO. If FROM is zero,
start at the beginning. If TO is less than FROM, then read until
the end of the file. If FILENAME is `NULL', then read from
`~/.history'. Returns 0 if successful, or `errno' if not.
- Function: int write_history (char *filename)
Write the current history to FILENAME, overwriting FILENAME if
necessary. If FILENAME is `NULL', then write the history list to
`~/.history'. Values returned are as in `read_history ()'.
- Function: int append_history (int nelements, char *filename)
Append the last NELEMENTS of the history list to FILENAME.
- Function: int history_truncate_file (char *filename, int nlines)
Truncate the history file FILENAME, leaving only the last NLINES
lines.

File: history.info, Node: History Expansion, Prev: Managing the History File, Up: History Functions
History Expansion
-----------------
These functions implement `csh'-like history expansion.
- Function: int history_expand (char *string, char **output)
Expand STRING, placing the result into OUTPUT, a pointer to a
string (*note History Interaction::.). Returns:
`0'
If no expansions took place (or, if the only change in the
text was the de-slashifying of the history expansion
character);
`1'
if expansions did take place;
`-1'
if there was an error in expansion;
`2'
if the returned line should only be displayed, but not
executed, as with the `:p' modifier (*note Modifiers::.).
If an error ocurred in expansion, then OUTPUT contains a
descriptive error message.
- Function: char * history_arg_extract (int first, int last, char
*string)
Extract a string segment consisting of the FIRST through LAST
arguments present in STRING. Arguments are broken up as in Bash.
- Function: char * get_history_event (char *string, int *cindex, int
qchar)
Returns the text of the history event beginning at STRING +
*CINDEX. *CINDEX is modified to point to after the event
specifier. At function entry, CINDEX points to the index into
STRING where the history event specification begins. QCHAR is a
character that is allowed to end the event specification in
addition to the "normal" terminating characters.
- Function: char ** history_tokenize (char *string)
Return an array of tokens parsed out of STRING, much as the shell
might. The tokens are split on white space and on the characters
`()<>;&|$', and shell quoting conventions are obeyed.

File: history.info, Node: History Variables, Next: History Programming Example, Prev: History Functions, Up: Programming with GNU History
History Variables
=================
This section describes the externally visible variables exported by
the GNU History Library.
- Variable: int history_base
The logical offset of the first entry in the history list.
- Variable: int history_length
The number of entries currently stored in the history list.
- Variable: int max_input_history
The maximum number of history entries. This must be changed using
`stifle_history ()'.
- Variable: char history_expansion_char
The character that starts a history event. The default is `!'.
- Variable: char history_subst_char
The character that invokes word substitution if found at the start
of a line. The default is `^'.
- Variable: char history_comment_char
During tokenization, if this character is seen as the first
character of a word, then it and all subsequent characters up to a
newline are ignored, suppressing history expansion for the
remainder of the line. This is disabled by default.
- Variable: char * history_no_expand_chars
The list of characters which inhibit history expansion if found
immediately following HISTORY_EXPANSION_CHAR. The default is
whitespace and `='.

File: history.info, Node: History Programming Example, Prev: History Variables, Up: Programming with GNU History
History Programming Example
===========================
The following program demonstrates simple use of the GNU History
Library.
main ()
{
char line[1024], *t;
int len, done = 0;
line[0] = 0;
using_history ();
while (!done)
{
printf ("history$ ");
fflush (stdout);
t = fgets (line, sizeof (line) - 1, stdin);
if (t && *t)
{
len = strlen (t);
if (t[len - 1] == '\n')
t[len - 1] = '\0';
}
if (!t)
strcpy (line, "quit");
if (line[0])
{
char *expansion;
int result;
result = history_expand (line, &expansion);
if (result)
fprintf (stderr, "%s\n", expansion);
if (result < 0 || result == 2)
{
free (expansion);
continue;
}
add_history (expansion);
strncpy (line, expansion, sizeof (line) - 1);
free (expansion);
}
if (strcmp (line, "quit") == 0)
done = 1;
else if (strcmp (line, "save") == 0)
write_history ("history_file");
else if (strcmp (line, "read") == 0)
read_history ("history_file");
else if (strcmp (line, "list") == 0)
{
register HIST_ENTRY **the_list;
register int i;
the_list = history_list ();
if (the_list)
for (i = 0; the_list[i]; i++)
printf ("%d: %s\n", i + history_base, the_list[i]->line);
}
else if (strncmp (line, "delete", 6) == 0)
{
int which;
if ((sscanf (line + 6, "%d", &which)) == 1)
{
HIST_ENTRY *entry = remove_history (which);
if (!entry)
fprintf (stderr, "No such entry %d\n", which);
else
{
free (entry->line);
free (entry);
}
}
else
{
fprintf (stderr, "non-numeric arg given to `delete'\n");
}
}
}
}

File: history.info, Node: Concept Index, Next: Function and Variable Index, Prev: Programming with GNU History, Up: Top
Concept Index
*************
* Menu:
* anchored search: Searching the History List.
* event designators: Event Designators.
* expansion: History Interaction.
* history events: Event Designators.
* History Searching: Searching the History List.

File: history.info, Node: Function and Variable Index, Prev: Concept Index, Up: Top
Function and Variable Index
***************************
* Menu:
* add_history: History List Management.
* append_history: Managing the History File.
* current_history: Information About the History List.
* get_history_event: History Expansion.
* history_arg_extract: History Expansion.
* history_base: History Variables.
* history_comment_char: History Variables.
* history_expand: History Expansion.
* history_expansion_char: History Variables.
* history_get: Information About the History List.
* history_get_history_state: Initializing History and State Management.
* history_is_stifled: History List Management.
* history_length: History Variables.
* history_list: Information About the History List.
* history_no_expand_chars: History Variables.
* history_search: Searching the History List.
* history_search_pos: Searching the History List.
* history_search_prefix: Searching the History List.
* history_set_history_state: Initializing History and State Management.
* history_set_pos: Moving Around the History List.
* history_subst_char: History Variables.
* history_tokenize: History Expansion.
* history_total_bytes: Information About the History List.
* history_truncate_file: Managing the History File.
* max_input_history: History Variables.
* next_history: Moving Around the History List.
* previous_history: Moving Around the History List.
* read_history: Managing the History File.
* read_history_range: Managing the History File.
* remove_history: History List Management.
* replace_history_entry: History List Management.
* stifle_history: History List Management.
* unstifle_history: History List Management.
* using_history: Initializing History and State Management.
* where_history: Information About the History List.
* write_history: Managing the History File.

Tag Table:
Node: Top975
Node: Using History Interactively1569
Node: History Interaction2077
Node: Event Designators3122
Node: Word Designators3952
Node: Modifiers4936
Node: Programming with GNU History6065
Node: Introduction to History6791
Node: History Storage8112
Node: History Functions9205
Node: Initializing History and State Management10176
Node: History List Management10968
Node: Information About the History List12396
Node: Moving Around the History List13702
Node: Searching the History List14587
Node: Managing the History File16419
Node: History Expansion17925
Node: History Variables19769
Node: History Programming Example21138
Node: Concept Index23742
Node: Function and Variable Index24223

End Tag Table

2037
lib/readline/doc/history.ps Normal file

File diff suppressed because it is too large Load diff

View file

@ -0,0 +1,489 @@
@ignore
This file documents the user interface to the GNU History library.
Copyright (C) 1988, 1991 Free Software Foundation, Inc.
Authored by Brian Fox and Chet Ramey.
Permission is granted to make and distribute verbatim copies of this manual
provided the copyright notice and this permission notice are preserved on
all copies.
Permission is granted to process this file through Tex and print the
results, provided the printed document carries copying permission notice
identical to this one except for the removal of this paragraph (this
paragraph not being relevant to the printed manual).
Permission is granted to copy and distribute modified versions of this
manual under the conditions for verbatim copying, provided also that the
GNU Copyright statement is available to the distributee, and provided that
the entire resulting derived work is distributed under the terms of a
permission notice identical to this one.
Permission is granted to copy and distribute translations of this manual
into another language, under the above conditions for modified versions.
@end ignore
@node Programming with GNU History
@chapter Programming with GNU History
This chapter describes how to interface programs that you write
with the GNU History Library.
It should be considered a technical guide.
For information on the interactive use of GNU History, @pxref{Using
History Interactively}.
@menu
* Introduction to History:: What is the GNU History library for?
* History Storage:: How information is stored.
* History Functions:: Functions that you can use.
* History Variables:: Variables that control behaviour.
* History Programming Example:: Example of using the GNU History Library.
@end menu
@node Introduction to History
@section Introduction to History
Many programs read input from the user a line at a time. The GNU History
library is able to keep track of those lines, associate arbitrary data with
each line, and utilize information from previous lines in composing new
ones.
The programmer using the History library has available functions
for remembering lines on a history list, associating arbitrary data
with a line, removing lines from the list, searching through the list
for a line containing an arbitrary text string, and referencing any line
in the list directly. In addition, a history @dfn{expansion} function
is available which provides for a consistent user interface across
different programs.
The user using programs written with the History library has the
benefit of a consistent user interface with a set of well-known
commands for manipulating the text of previous lines and using that text
in new commands. The basic history manipulation commands are similar to
the history substitution provided by @code{csh}.
If the programmer desires, he can use the Readline library, which
includes some history manipulation by default, and has the added
advantage of command line editing.
@node History Storage
@section History Storage
The history list is an array of history entries. A history entry is
declared as follows:
@example
typedef struct _hist_entry @{
char *line;
char *data;
@} HIST_ENTRY;
@end example
The history list itself might therefore be declared as
@example
HIST_ENTRY **the_history_list;
@end example
The state of the History library is encapsulated into a single structure:
@example
/* A structure used to pass the current state of the history stuff around. */
typedef struct _hist_state @{
HIST_ENTRY **entries; /* Pointer to the entries themselves. */
int offset; /* The location pointer within this array. */
int length; /* Number of elements within this array. */
int size; /* Number of slots allocated to this array. */
int flags;
@} HISTORY_STATE;
@end example
If the flags member includes @code{HS_STIFLED}, the history has been
stifled.
@node History Functions
@section History Functions
This section describes the calling sequence for the various functions
present in GNU History.
@menu
* Initializing History and State Management:: Functions to call when you
want to use history in a
program.
* History List Management:: Functions used to manage the list
of history entries.
* Information About the History List:: Functions returning information about
the history list.
* Moving Around the History List:: Functions used to change the position
in the history list.
* Searching the History List:: Functions to search the history list
for entries containing a string.
* Managing the History File:: Functions that read and write a file
containing the history list.
* History Expansion:: Functions to perform csh-like history
expansion.
@end menu
@node Initializing History and State Management
@subsection Initializing History and State Management
This section describes functions used to initialize and manage
the state of the History library when you want to use the history
functions in your program.
@deftypefun void using_history ()
Begin a session in which the history functions might be used. This
initializes the interactive variables.
@end deftypefun
@deftypefun {HISTORY_STATE *} history_get_history_state ()
Return a structure describing the current state of the input history.
@end deftypefun
@deftypefun void history_set_history_state (HISTORY_STATE *state)
Set the state of the history list according to @var{state}.
@end deftypefun
@node History List Management
@subsection History List Management
These functions manage individual entries on the history list, or set
parameters managing the list itself.
@deftypefun void add_history (char *string)
Place @var{string} at the end of the history list. The associated data
field (if any) is set to @code{NULL}.
@end deftypefun
@deftypefun {HIST_ENTRY *} remove_history (int which)
Remove history entry at offset @var{which} from the history. The
removed element is returned so you can free the line, data,
and containing structure.
@end deftypefun
@deftypefun {HIST_ENTRY *} replace_history_entry (int which, char *line, char *data)
Make the history entry at offset @var{which} have @var{line} and @var{data}.
This returns the old entry so you can dispose of the data. In the case
of an invalid @var{which}, a @code{NULL} pointer is returned.
@end deftypefun
@deftypefun void stifle_history (int max)
Stifle the history list, remembering only the last @var{max} entries.
@end deftypefun
@deftypefun int unstifle_history ()
Stop stifling the history. This returns the previous amount the
history was stifled. The value is positive if the history was
stifled, negative if it wasn't.
@end deftypefun
@deftypefun int history_is_stifled ()
Returns non-zero if the history is stifled, zero if it is not.
@end deftypefun
@node Information About the History List
@subsection Information About the History List
These functions return information about the entire history list or
individual list entries.
@deftypefun {HIST_ENTRY **} history_list ()
Return a @code{NULL} terminated array of @code{HIST_ENTRY} which is the
current input history. Element 0 of this list is the beginning of time.
If there is no history, return @code{NULL}.
@end deftypefun
@deftypefun int where_history ()
Returns the offset of the current history element.
@end deftypefun
@deftypefun {HIST_ENTRY *} current_history ()
Return the history entry at the current position, as determined by
@code{where_history ()}. If there is no entry there, return a @code{NULL}
pointer.
@end deftypefun
@deftypefun {HIST_ENTRY *} history_get (int offset)
Return the history entry at position @var{offset}, starting from
@code{history_base}. If there is no entry there, or if @var{offset}
is greater than the history length, return a @code{NULL} pointer.
@end deftypefun
@deftypefun int history_total_bytes ()
Return the number of bytes that the primary history entries are using.
This function returns the sum of the lengths of all the lines in the
history.
@end deftypefun
@node Moving Around the History List
@subsection Moving Around the History List
These functions allow the current index into the history list to be
set or changed.
@deftypefun int history_set_pos (int pos)
Set the position in the history list to @var{pos}, an absolute index
into the list.
@end deftypefun
@deftypefun {HIST_ENTRY *} previous_history ()
Back up the current history offset to the previous history entry, and
return a pointer to that entry. If there is no previous entry, return
a @code{NULL} pointer.
@end deftypefun
@deftypefun {HIST_ENTRY *} next_history ()
Move the current history offset forward to the next history entry, and
return the a pointer to that entry. If there is no next entry, return
a @code{NULL} pointer.
@end deftypefun
@node Searching the History List
@subsection Searching the History List
@cindex History Searching
These functions allow searching of the history list for entries containing
a specific string. Searching may be performed both forward and backward
from the current history position. The search may be @dfn{anchored},
meaning that the string must match at the beginning of the history entry.
@cindex anchored search
@deftypefun int history_search (char *string, int direction)
Search the history for @var{string}, starting at the current history
offset. If @var{direction} < 0, then the search is through previous entries,
else through subsequent. If @var{string} is found, then
the current history index is set to that history entry, and the value
returned is the offset in the line of the entry where
@var{string} was found. Otherwise, nothing is changed, and a -1 is
returned.
@end deftypefun
@deftypefun int history_search_prefix (char *string, int direction)
Search the history for @var{string}, starting at the current history
offset. The search is anchored: matching lines must begin with
@var{string}. If @var{direction} < 0, then the search is through previous
entries, else through subsequent. If @var{string} is found, then the
current history index is set to that entry, and the return value is 0.
Otherwise, nothing is changed, and a -1 is returned.
@end deftypefun
@deftypefun int history_search_pos (char *string, int direction, int pos)
Search for @var{string} in the history list, starting at @var{pos}, an
absolute index into the list. If @var{direction} is negative, the search
proceeds backward from @var{pos}, otherwise forward. Returns the absolute
index of the history element where @var{string} was found, or -1 otherwise.
@end deftypefun
@node Managing the History File
@subsection Managing the History File
The History library can read the history from and write it to a file.
This section documents the functions for managing a history file.
@deftypefun int read_history (char *filename)
Add the contents of @var{filename} to the history list, a line at a
time. If @var{filename} is @code{NULL}, then read from
@file{~/.history}. Returns 0 if successful, or errno if not.
@end deftypefun
@deftypefun int read_history_range (char *filename, int from, int to)
Read a range of lines from @var{filename}, adding them to the history list.
Start reading at line @var{from} and end at @var{to}. If
@var{from} is zero, start at the beginning. If @var{to} is less than
@var{from}, then read until the end of the file. If @var{filename} is
@code{NULL}, then read from @file{~/.history}. Returns 0 if successful,
or @code{errno} if not.
@end deftypefun
@deftypefun int write_history (char *filename)
Write the current history to @var{filename}, overwriting @var{filename}
if necessary. If @var{filename} is
@code{NULL}, then write the history list to @file{~/.history}. Values
returned are as in @code{read_history ()}.
@end deftypefun
@deftypefun int append_history (int nelements, char *filename)
Append the last @var{nelements} of the history list to @var{filename}.
@end deftypefun
@deftypefun int history_truncate_file (char *filename, int nlines)
Truncate the history file @var{filename}, leaving only the last
@var{nlines} lines.
@end deftypefun
@node History Expansion
@subsection History Expansion
These functions implement @code{csh}-like history expansion.
@deftypefun int history_expand (char *string, char **output)
Expand @var{string}, placing the result into @var{output}, a pointer
to a string (@pxref{History Interaction}). Returns:
@table @code
@item 0
If no expansions took place (or, if the only change in
the text was the de-slashifying of the history expansion
character);
@item 1
if expansions did take place;
@item -1
if there was an error in expansion;
@item 2
if the returned line should only be displayed, but not executed,
as with the @code{:p} modifier (@pxref{Modifiers}).
@end table
If an error ocurred in expansion, then @var{output} contains a descriptive
error message.
@end deftypefun
@deftypefun {char *} history_arg_extract (int first, int last, char *string)
Extract a string segment consisting of the @var{first} through @var{last}
arguments present in @var{string}. Arguments are broken up as in Bash.
@end deftypefun
@deftypefun {char *} get_history_event (char *string, int *cindex, int qchar)
Returns the text of the history event beginning at @var{string} +
@var{*cindex}. @var{*cindex} is modified to point to after the event
specifier. At function entry, @var{cindex} points to the index into
@var{string} where the history event specification begins. @var{qchar}
is a character that is allowed to end the event specification in addition
to the ``normal'' terminating characters.
@end deftypefun
@deftypefun {char **} history_tokenize (char *string)
Return an array of tokens parsed out of @var{string}, much as the
shell might. The tokens are split on white space and on the
characters @code{()<>;&|$}, and shell quoting conventions are
obeyed.
@end deftypefun
@node History Variables
@section History Variables
This section describes the externally visible variables exported by
the GNU History Library.
@deftypevar int history_base
The logical offset of the first entry in the history list.
@end deftypevar
@deftypevar int history_length
The number of entries currently stored in the history list.
@end deftypevar
@deftypevar int max_input_history
The maximum number of history entries. This must be changed using
@code{stifle_history ()}.
@end deftypevar
@deftypevar char history_expansion_char
The character that starts a history event. The default is @samp{!}.
@end deftypevar
@deftypevar char history_subst_char
The character that invokes word substitution if found at the start of
a line. The default is @samp{^}.
@end deftypevar
@deftypevar char history_comment_char
During tokenization, if this character is seen as the first character
of a word, then it and all subsequent characters up to a newline are
ignored, suppressing history expansion for the remainder of the line.
This is disabled by default.
@end deftypevar
@deftypevar {char *} history_no_expand_chars
The list of characters which inhibit history expansion if found immediately
following @var{history_expansion_char}. The default is whitespace and
@samp{=}.
@end deftypevar
@node History Programming Example
@section History Programming Example
The following program demonstrates simple use of the GNU History Library.
@smallexample
main ()
@{
char line[1024], *t;
int len, done = 0;
line[0] = 0;
using_history ();
while (!done)
@{
printf ("history$ ");
fflush (stdout);
t = fgets (line, sizeof (line) - 1, stdin);
if (t && *t)
@{
len = strlen (t);
if (t[len - 1] == '\n')
t[len - 1] = '\0';
@}
if (!t)
strcpy (line, "quit");
if (line[0])
@{
char *expansion;
int result;
result = history_expand (line, &expansion);
if (result)
fprintf (stderr, "%s\n", expansion);
if (result < 0 || result == 2)
@{
free (expansion);
continue;
@}
add_history (expansion);
strncpy (line, expansion, sizeof (line) - 1);
free (expansion);
@}
if (strcmp (line, "quit") == 0)
done = 1;
else if (strcmp (line, "save") == 0)
write_history ("history_file");
else if (strcmp (line, "read") == 0)
read_history ("history_file");
else if (strcmp (line, "list") == 0)
@{
register HIST_ENTRY **the_list;
register int i;
the_list = history_list ();
if (the_list)
for (i = 0; the_list[i]; i++)
printf ("%d: %s\n", i + history_base, the_list[i]->line);
@}
else if (strncmp (line, "delete", 6) == 0)
@{
int which;
if ((sscanf (line + 6, "%d", &which)) == 1)
@{
HIST_ENTRY *entry = remove_history (which);
if (!entry)
fprintf (stderr, "No such entry %d\n", which);
else
@{
free (entry->line);
free (entry);
@}
@}
else
@{
fprintf (stderr, "non-numeric arg given to `delete'\n");
@}
@}
@}
@}
@end smallexample

View file

@ -0,0 +1,198 @@
@ignore
This file documents the user interface to the GNU History library.
Copyright (C) 1988, 1991 Free Software Foundation, Inc.
Authored by Brian Fox and Chet Ramey.
Permission is granted to make and distribute verbatim copies of this manual
provided the copyright notice and this permission notice are preserved on
all copies.
Permission is granted to process this file through Tex and print the
results, provided the printed document carries copying permission notice
identical to this one except for the removal of this paragraph (this
paragraph not being relevant to the printed manual).
Permission is granted to copy and distribute modified versions of this
manual under the conditions for verbatim copying, provided also that the
GNU Copyright statement is available to the distributee, and provided that
the entire resulting derived work is distributed under the terms of a
permission notice identical to this one.
Permission is granted to copy and distribute translations of this manual
into another language, under the above conditions for modified versions.
@end ignore
@node Using History Interactively
@chapter Using History Interactively
@ifset BashFeatures
This chapter describes how to use the GNU History Library interactively,
from a user's standpoint. It should be considered a user's guide. For
information on using the GNU History Library in your own programs,
see the GNU Readline Library Manual.
@end ifset
@ifclear BashFeatures
This chapter describes how to use the GNU History Library interactively,
from a user's standpoint. It should be considered a user's guide. For
information on using the GNU History Library in your own programs,
@pxref{Programming with GNU History}.
@end ifclear
@menu
* History Interaction:: What it feels like using History as a user.
@end menu
@node History Interaction
@section History Interaction
@cindex expansion
The History library provides a history expansion feature that is similar
to the history expansion provided by @code{csh}. The following text
describes the syntax used to manipulate the history information.
History expansion takes place in two parts. The first is to determine
which line from the previous history should be used during substitution.
The second is to select portions of that line for inclusion into the
current one. The line selected from the previous history is called the
@dfn{event}, and the portions of that line that are acted upon are
called @dfn{words}. The line is broken into words in the same fashion
that Bash does, so that several English (or Unix) words
surrounded by quotes are considered as one word.
@menu
* Event Designators:: How to specify which history line to use.
* Word Designators:: Specifying which words are of interest.
* Modifiers:: Modifying the results of substitution.
@end menu
@node Event Designators
@subsection Event Designators
@cindex event designators
An event designator is a reference to a command line entry in the
history list.
@cindex history events
@table @asis
@item @code{!}
Start a history substitution, except when followed by a space, tab,
the end of the line, @key{=} or @key{(}.
@item @code{!!}
Refer to the previous command. This is a synonym for @code{!-1}.
@item @code{!n}
Refer to command line @var{n}.
@item @code{!-n}
Refer to the command @var{n} lines back.
@item @code{!string}
Refer to the most recent command starting with @var{string}.
@item @code{!?string}[@code{?}]
Refer to the most recent command containing @var{string}.
@item @code{!#}
The entire command line typed so far.
@item @code{^string1^string2^}
Quick Substitution. Repeat the last command, replacing @var{string1}
with @var{string2}. Equivalent to
@code{!!:s/string1/string2/}.
@end table
@node Word Designators
@subsection Word Designators
A @key{:} separates the event specification from the word designator. It
can be omitted if the word designator begins with a @key{^}, @key{$},
@key{*} or @key{%}. Words are numbered from the beginning of the line,
with the first word being denoted by a 0 (zero).
@table @code
@item 0 (zero)
The @code{0}th word. For many applications, this is the command word.
@item n
The @var{n}th word.
@item ^
The first argument; that is, word 1.
@item $
The last argument.
@item %
The word matched by the most recent @code{?string?} search.
@item x-y
A range of words; @code{-@var{y}} abbreviates @code{0-@var{y}}.
@item *
All of the words, except the @code{0}th. This is a synonym for @code{1-$}.
It is not an error to use @key{*} if there is just one word in the event;
the empty string is returned in that case.
@item x*
Abbreviates @code{x-$}
@item x-
Abbreviates @code{x-$} like @code{x*}, but omits the last word.
@end table
@node Modifiers
@subsection Modifiers
After the optional word designator, you can add a sequence of one or more
of the following modifiers, each preceded by a @key{:}.
@table @code
@item h
Remove a trailing pathname component, leaving only the head.
@item r
Remove a trailing suffix of the form @samp{.}@var{suffix}, leaving the basename.
@item e
Remove all but the trailing suffix.
@item t
Remove all leading pathname components, leaving the tail.
@item p
Print the new command but do not execute it.
@ifset BashFeatures
@item q
Quote the substituted words, escaping further substitutions.
@item x
Quote the substituted words as with @code{q},
but break into words at spaces, tabs, and newlines.
@end ifset
@item s/old/new/
Substitute @var{new} for the first occurrence of @var{old} in the
event line. Any delimiter may be used in place of @key{/}.
The delimiter may be quoted in @var{old} and @var{new}
with a single backslash. If @key{&} appears in @var{new},
it is replaced by @var{old}. A single backslash will quote
the @key{&}. The final delimiter is optional if it is the last
character on the input line.
@item &
Repeat the previous substitution.
@item g
Cause changes to be applied over the entire event line. Used in
conjunction with @code{s}, as in @code{gs/old/new/}, or with
@code{&}.
@end table

Binary file not shown.

View file

@ -0,0 +1,744 @@
This is Info file history.info, produced by Makeinfo-1.55 from the
input file hist.texinfo.
This document describes the GNU History library, a programming tool
that provides a consistent user interface for recalling lines of
previously typed input.
Copyright (C) 1988, 1991 Free Software Foundation, Inc.
Permission is granted to make and distribute verbatim copies of this
manual provided the copyright notice and this permission notice pare
preserved on all copies.
Permission is granted to copy and distribute modified versions of
this manual under the conditions for verbatim copying, provided that
the entire resulting derived work is distributed under the terms of a
permission notice identical to this one.
Permission is granted to copy and distribute translations of this
manual into another language, under the above conditions for modified
versions, except that this permission notice may be stated in a
translation approved by the Foundation.

File: history.info, Node: Top, Next: Using History Interactively, Prev: (DIR), Up: (DIR)
GNU History Library
*******************
This document describes the GNU History library, a programming tool
that provides a consistent user interface for recalling lines of
previously typed input.
* Menu:
* Using History Interactively:: GNU History User's Manual.
* Programming with GNU History:: GNU History Programmer's Manual.
* Concept Index:: Index of concepts described in this manual.
* Function and Variable Index:: Index of externally visible functions
and variables.

File: history.info, Node: Using History Interactively, Next: Programming with GNU History, Prev: Top, Up: Top
Using History Interactively
***************************
This chapter describes how to use the GNU History Library
interactively, from a user's standpoint. It should be considered a
user's guide. For information on using the GNU History Library in your
own programs, *note Programming with GNU History::..
* Menu:
* History Interaction:: What it feels like using History as a user.

File: history.info, Node: History Interaction, Up: Using History Interactively
History Interaction
===================
The History library provides a history expansion feature that is
similar to the history expansion provided by `csh'. The following text
describes the syntax used to manipulate the history information.
History expansion takes place in two parts. The first is to
determine which line from the previous history should be used during
substitution. The second is to select portions of that line for
inclusion into the current one. The line selected from the previous
history is called the "event", and the portions of that line that are
acted upon are called "words". The line is broken into words in the
same fashion that Bash does, so that several English (or Unix) words
surrounded by quotes are considered as one word.
* Menu:
* Event Designators:: How to specify which history line to use.
* Word Designators:: Specifying which words are of interest.
* Modifiers:: Modifying the results of substitution.

File: history.info, Node: Event Designators, Next: Word Designators, Up: History Interaction
Event Designators
-----------------
An event designator is a reference to a command line entry in the
history list.
`!'
Start a history substitution, except when followed by a space, tab,
the end of the line, = or (.
`!!'
Refer to the previous command. This is a synonym for `!-1'.
`!n'
Refer to command line N.
`!-n'
Refer to the command N lines back.
`!string'
Refer to the most recent command starting with STRING.
`!?string'[`?']
Refer to the most recent command containing STRING.
`!#'
The entire command line typed so far.
`^string1^string2^'
Quick Substitution. Repeat the last command, replacing STRING1
with STRING2. Equivalent to `!!:s/string1/string2/'.

File: history.info, Node: Word Designators, Next: Modifiers, Prev: Event Designators, Up: History Interaction
Word Designators
----------------
A : separates the event specification from the word designator. It
can be omitted if the word designator begins with a ^, $, * or %.
Words are numbered from the beginning of the line, with the first word
being denoted by a 0 (zero).
`0 (zero)'
The `0'th word. For many applications, this is the command word.
`n'
The Nth word.
`^'
The first argument; that is, word 1.
`$'
The last argument.
`%'
The word matched by the most recent `?string?' search.
`x-y'
A range of words; `-Y' abbreviates `0-Y'.
`*'
All of the words, except the `0'th. This is a synonym for `1-$'.
It is not an error to use * if there is just one word in the event;
the empty string is returned in that case.
`x*'
Abbreviates `x-$'
`x-'
Abbreviates `x-$' like `x*', but omits the last word.

File: history.info, Node: Modifiers, Prev: Word Designators, Up: History Interaction
Modifiers
---------
After the optional word designator, you can add a sequence of one or
more of the following modifiers, each preceded by a :.
`h'
Remove a trailing pathname component, leaving only the head.
`r'
Remove a trailing suffix of the form `.'SUFFIX, leaving the
basename.
`e'
Remove all but the trailing suffix.
`t'
Remove all leading pathname components, leaving the tail.
`p'
Print the new command but do not execute it.
`s/old/new/'
Substitute NEW for the first occurrence of OLD in the event line.
Any delimiter may be used in place of /. The delimiter may be
quoted in OLD and NEW with a single backslash. If & appears in
NEW, it is replaced by OLD. A single backslash will quote the &.
The final delimiter is optional if it is the last character on the
input line.
`&'
Repeat the previous substitution.
`g'
Cause changes to be applied over the entire event line. Used in
conjunction with `s', as in `gs/old/new/', or with `&'.

File: history.info, Node: Programming with GNU History, Next: Concept Index, Prev: Using History Interactively, Up: Top
Programming with GNU History
****************************
This chapter describes how to interface programs that you write with
the GNU History Library. It should be considered a technical guide.
For information on the interactive use of GNU History, *note Using
History Interactively::..
* Menu:
* Introduction to History:: What is the GNU History library for?
* History Storage:: How information is stored.
* History Functions:: Functions that you can use.
* History Variables:: Variables that control behaviour.
* History Programming Example:: Example of using the GNU History Library.

File: history.info, Node: Introduction to History, Next: History Storage, Up: Programming with GNU History
Introduction to History
=======================
Many programs read input from the user a line at a time. The GNU
History library is able to keep track of those lines, associate
arbitrary data with each line, and utilize information from previous
lines in composing new ones.
The programmer using the History library has available functions for
remembering lines on a history list, associating arbitrary data with a
line, removing lines from the list, searching through the list for a
line containing an arbitrary text string, and referencing any line in
the list directly. In addition, a history "expansion" function is
available which provides for a consistent user interface across
different programs.
The user using programs written with the History library has the
benefit of a consistent user interface with a set of well-known
commands for manipulating the text of previous lines and using that text
in new commands. The basic history manipulation commands are similar to
the history substitution provided by `csh'.
If the programmer desires, he can use the Readline library, which
includes some history manipulation by default, and has the added
advantage of command line editing.

File: history.info, Node: History Storage, Next: History Functions, Prev: Introduction to History, Up: Programming with GNU History
History Storage
===============
The history list is an array of history entries. A history entry is
declared as follows:
typedef struct _hist_entry {
char *line;
char *data;
} HIST_ENTRY;
The history list itself might therefore be declared as
HIST_ENTRY **the_history_list;
The state of the History library is encapsulated into a single
structure:
/* A structure used to pass the current state of the history stuff around. */
typedef struct _hist_state {
HIST_ENTRY **entries; /* Pointer to the entries themselves. */
int offset; /* The location pointer within this array. */
int length; /* Number of elements within this array. */
int size; /* Number of slots allocated to this array. */
int flags;
} HISTORY_STATE;
If the flags member includes `HS_STIFLED', the history has been
stifled.

File: history.info, Node: History Functions, Next: History Variables, Prev: History Storage, Up: Programming with GNU History
History Functions
=================
This section describes the calling sequence for the various functions
present in GNU History.
* Menu:
* Initializing History and State Management:: Functions to call when you
want to use history in a
program.
* History List Management:: Functions used to manage the list
of history entries.
* Information About the History List:: Functions returning information about
the history list.
* Moving Around the History List:: Functions used to change the position
in the history list.
* Searching the History List:: Functions to search the history list
for entries containing a string.
* Managing the History File:: Functions that read and write a file
containing the history list.
* History Expansion:: Functions to perform csh-like history
expansion.

File: history.info, Node: Initializing History and State Management, Next: History List Management, Up: History Functions
Initializing History and State Management
-----------------------------------------
This section describes functions used to initialize and manage the
state of the History library when you want to use the history functions
in your program.
- Function: void using_history ()
Begin a session in which the history functions might be used. This
initializes the interactive variables.
- Function: HISTORY_STATE * history_get_history_state ()
Return a structure describing the current state of the input
history.
- Function: void history_set_history_state (HISTORY_STATE *state)
Set the state of the history list according to STATE.

File: history.info, Node: History List Management, Next: Information About the History List, Prev: Initializing History and State Management, Up: History Functions
History List Management
-----------------------
These functions manage individual entries on the history list, or set
parameters managing the list itself.
- Function: void add_history (char *string)
Place STRING at the end of the history list. The associated data
field (if any) is set to `NULL'.
- Function: HIST_ENTRY * remove_history (int which)
Remove history entry at offset WHICH from the history. The
removed element is returned so you can free the line, data, and
containing structure.
- Function: HIST_ENTRY * replace_history_entry (int which, char *line,
char *data)
Make the history entry at offset WHICH have LINE and DATA. This
returns the old entry so you can dispose of the data. In the case
of an invalid WHICH, a `NULL' pointer is returned.
- Function: void stifle_history (int max)
Stifle the history list, remembering only the last MAX entries.
- Function: int unstifle_history ()
Stop stifling the history. This returns the previous amount the
history was stifled. The value is positive if the history was
stifled, negative if it wasn't.
- Function: int history_is_stifled ()
Returns non-zero if the history is stifled, zero if it is not.

File: history.info, Node: Information About the History List, Next: Moving Around the History List, Prev: History List Management, Up: History Functions
Information About the History List
----------------------------------
These functions return information about the entire history list or
individual list entries.
- Function: HIST_ENTRY ** history_list ()
Return a `NULL' terminated array of `HIST_ENTRY' which is the
current input history. Element 0 of this list is the beginning of
time. If there is no history, return `NULL'.
- Function: int where_history ()
Returns the offset of the current history element.
- Function: HIST_ENTRY * current_history ()
Return the history entry at the current position, as determined by
`where_history ()'. If there is no entry there, return a `NULL'
pointer.
- Function: HIST_ENTRY * history_get (int offset)
Return the history entry at position OFFSET, starting from
`history_base'. If there is no entry there, or if OFFSET is
greater than the history length, return a `NULL' pointer.
- Function: int history_total_bytes ()
Return the number of bytes that the primary history entries are
using. This function returns the sum of the lengths of all the
lines in the history.

File: history.info, Node: Moving Around the History List, Next: Searching the History List, Prev: Information About the History List, Up: History Functions
Moving Around the History List
------------------------------
These functions allow the current index into the history list to be
set or changed.
- Function: int history_set_pos (int pos)
Set the position in the history list to POS, an absolute index
into the list.
- Function: HIST_ENTRY * previous_history ()
Back up the current history offset to the previous history entry,
and return a pointer to that entry. If there is no previous
entry, return a `NULL' pointer.
- Function: HIST_ENTRY * next_history ()
Move the current history offset forward to the next history entry,
and return the a pointer to that entry. If there is no next
entry, return a `NULL' pointer.

File: history.info, Node: Searching the History List, Next: Managing the History File, Prev: Moving Around the History List, Up: History Functions
Searching the History List
--------------------------
These functions allow searching of the history list for entries
containing a specific string. Searching may be performed both forward
and backward from the current history position. The search may be
"anchored", meaning that the string must match at the beginning of the
history entry.
- Function: int history_search (char *string, int direction)
Search the history for STRING, starting at the current history
offset. If DIRECTION < 0, then the search is through previous
entries, else through subsequent. If STRING is found, then the
current history index is set to that history entry, and the value
returned is the offset in the line of the entry where STRING was
found. Otherwise, nothing is changed, and a -1 is returned.
- Function: int history_search_prefix (char *string, int direction)
Search the history for STRING, starting at the current history
offset. The search is anchored: matching lines must begin with
STRING. If DIRECTION < 0, then the search is through previous
entries, else through subsequent. If STRING is found, then the
current history index is set to that entry, and the return value
is 0. Otherwise, nothing is changed, and a -1 is returned.
- Function: int history_search_pos (char *string, int direction, int
pos)
Search for STRING in the history list, starting at POS, an
absolute index into the list. If DIRECTION is negative, the search
proceeds backward from POS, otherwise forward. Returns the
absolute index of the history element where STRING was found, or
-1 otherwise.

File: history.info, Node: Managing the History File, Next: History Expansion, Prev: Searching the History List, Up: History Functions
Managing the History File
-------------------------
The History library can read the history from and write it to a file.
This section documents the functions for managing a history file.
- Function: int read_history (char *filename)
Add the contents of FILENAME to the history list, a line at a
time. If FILENAME is `NULL', then read from `~/.history'.
Returns 0 if successful, or errno if not.
- Function: int read_history_range (char *filename, int from, int to)
Read a range of lines from FILENAME, adding them to the history
list. Start reading at line FROM and end at TO. If FROM is zero,
start at the beginning. If TO is less than FROM, then read until
the end of the file. If FILENAME is `NULL', then read from
`~/.history'. Returns 0 if successful, or `errno' if not.
- Function: int write_history (char *filename)
Write the current history to FILENAME, overwriting FILENAME if
necessary. If FILENAME is `NULL', then write the history list to
`~/.history'. Values returned are as in `read_history ()'.
- Function: int append_history (int nelements, char *filename)
Append the last NELEMENTS of the history list to FILENAME.
- Function: int history_truncate_file (char *filename, int nlines)
Truncate the history file FILENAME, leaving only the last NLINES
lines.

File: history.info, Node: History Expansion, Prev: Managing the History File, Up: History Functions
History Expansion
-----------------
These functions implement `csh'-like history expansion.
- Function: int history_expand (char *string, char **output)
Expand STRING, placing the result into OUTPUT, a pointer to a
string (*note History Interaction::.). Returns:
`0'
If no expansions took place (or, if the only change in the
text was the de-slashifying of the history expansion
character);
`1'
if expansions did take place;
`-1'
if there was an error in expansion;
`2'
if the returned line should only be displayed, but not
executed, as with the `:p' modifier (*note Modifiers::.).
If an error ocurred in expansion, then OUTPUT contains a
descriptive error message.
- Function: char * history_arg_extract (int first, int last, char
*string)
Extract a string segment consisting of the FIRST through LAST
arguments present in STRING. Arguments are broken up as in Bash.
- Function: char * get_history_event (char *string, int *cindex, int
qchar)
Returns the text of the history event beginning at STRING +
*CINDEX. *CINDEX is modified to point to after the event
specifier. At function entry, CINDEX points to the index into
STRING where the history event specification begins. QCHAR is a
character that is allowed to end the event specification in
addition to the "normal" terminating characters.
- Function: char ** history_tokenize (char *string)
Return an array of tokens parsed out of STRING, much as the shell
might. The tokens are split on white space and on the characters
`()<>;&|$', and shell quoting conventions are obeyed.

File: history.info, Node: History Variables, Next: History Programming Example, Prev: History Functions, Up: Programming with GNU History
History Variables
=================
This section describes the externally visible variables exported by
the GNU History Library.
- Variable: int history_base
The logical offset of the first entry in the history list.
- Variable: int history_length
The number of entries currently stored in the history list.
- Variable: int max_input_history
The maximum number of history entries. This must be changed using
`stifle_history ()'.
- Variable: char history_expansion_char
The character that starts a history event. The default is `!'.
- Variable: char history_subst_char
The character that invokes word substitution if found at the start
of a line. The default is `^'.
- Variable: char history_comment_char
During tokenization, if this character is seen as the first
character of a word, then it and all subsequent characters up to a
newline are ignored, suppressing history expansion for the
remainder of the line. This is disabled by default.
- Variable: char * history_no_expand_chars
The list of characters which inhibit history expansion if found
immediately following HISTORY_EXPANSION_CHAR. The default is
whitespace and `='.

File: history.info, Node: History Programming Example, Prev: History Variables, Up: Programming with GNU History
History Programming Example
===========================
The following program demonstrates simple use of the GNU History
Library.
main ()
{
char line[1024], *t;
int len, done = 0;
line[0] = 0;
using_history ();
while (!done)
{
printf ("history$ ");
fflush (stdout);
t = fgets (line, sizeof (line) - 1, stdin);
if (t && *t)
{
len = strlen (t);
if (t[len - 1] == '\n')
t[len - 1] = '\0';
}
if (!t)
strcpy (line, "quit");
if (line[0])
{
char *expansion;
int result;
result = history_expand (line, &expansion);
if (result)
fprintf (stderr, "%s\n", expansion);
if (result < 0 || result == 2)
{
free (expansion);
continue;
}
add_history (expansion);
strncpy (line, expansion, sizeof (line) - 1);
free (expansion);
}
if (strcmp (line, "quit") == 0)
done = 1;
else if (strcmp (line, "save") == 0)
write_history ("history_file");
else if (strcmp (line, "read") == 0)
read_history ("history_file");
else if (strcmp (line, "list") == 0)
{
register HIST_ENTRY **the_list;
register int i;
the_list = history_list ();
if (the_list)
for (i = 0; the_list[i]; i++)
printf ("%d: %s\n", i + history_base, the_list[i]->line);
}
else if (strncmp (line, "delete", 6) == 0)
{
int which;
if ((sscanf (line + 6, "%d", &which)) == 1)
{
HIST_ENTRY *entry = remove_history (which);
if (!entry)
fprintf (stderr, "No such entry %d\n", which);
else
{
free (entry->line);
free (entry);
}
}
else
{
fprintf (stderr, "non-numeric arg given to `delete'\n");
}
}
}
}

File: history.info, Node: Concept Index, Next: Function and Variable Index, Prev: Programming with GNU History, Up: Top
Concept Index
*************
* Menu:
* anchored search: Searching the History List.
* event designators: Event Designators.
* expansion: History Interaction.
* history events: Event Designators.
* History Searching: Searching the History List.

File: history.info, Node: Function and Variable Index, Prev: Concept Index, Up: Top
Function and Variable Index
***************************
* Menu:
* add_history: History List Management.
* append_history: Managing the History File.
* current_history: Information About the History List.
* get_history_event: History Expansion.
* history_arg_extract: History Expansion.
* history_base: History Variables.
* history_comment_char: History Variables.
* history_expand: History Expansion.
* history_expansion_char: History Variables.
* history_get: Information About the History List.
* history_get_history_state: Initializing History and State Management.
* history_is_stifled: History List Management.
* history_length: History Variables.
* history_list: Information About the History List.
* history_no_expand_chars: History Variables.
* history_search: Searching the History List.
* history_search_pos: Searching the History List.
* history_search_prefix: Searching the History List.
* history_set_history_state: Initializing History and State Management.
* history_set_pos: Moving Around the History List.
* history_subst_char: History Variables.
* history_tokenize: History Expansion.
* history_total_bytes: Information About the History List.
* history_truncate_file: Managing the History File.
* max_input_history: History Variables.
* next_history: Moving Around the History List.
* previous_history: Moving Around the History List.
* read_history: Managing the History File.
* read_history_range: Managing the History File.
* remove_history: History List Management.
* replace_history_entry: History List Management.
* stifle_history: History List Management.
* unstifle_history: History List Management.
* using_history: Initializing History and State Management.
* where_history: Information About the History List.
* write_history: Managing the History File.

Tag Table:
Node: Top975
Node: Using History Interactively1569
Node: History Interaction2077
Node: Event Designators3122
Node: Word Designators3952
Node: Modifiers4936
Node: Programming with GNU History6065
Node: Introduction to History6791
Node: History Storage8112
Node: History Functions9205
Node: Initializing History and State Management10176
Node: History List Management10968
Node: Information About the History List12396
Node: Moving Around the History List13702
Node: Searching the History List14587
Node: Managing the History File16419
Node: History Expansion17925
Node: History Variables19769
Node: History Programming Example21138
Node: Concept Index23742
Node: Function and Variable Index24223

End Tag Table

2037
lib/readline/doc/readline.ps Normal file

File diff suppressed because it is too large Load diff

View file

@ -0,0 +1,111 @@
\input texinfo @c -*-texinfo-*-
@comment %**start of header (This is for running Texinfo on a region.)
@setfilename readline.info
@settitle GNU Readline Library
@comment %**end of header (This is for running Texinfo on a region.)
@synindex vr fn
@setchapternewpage odd
@ignore
last change: Thu Jul 21 16:02:40 EDT 1994
@end ignore
@set EDITION 2.0
@set VERSION 2.0
@set UPDATED 21 July 1994
@set UPDATE-MONTH July 1994
@ifinfo
This document describes the GNU Readline Library, a utility which aids
in the consistency of user interface across discrete programs that need
to provide a command line interface.
Copyright (C) 1988, 1991 Free Software Foundation, Inc.
Permission is granted to make and distribute verbatim copies of
this manual provided the copyright notice and this permission notice
pare preserved on all copies.
@ignore
Permission is granted to process this file through TeX and print the
results, provided the printed document carries copying permission
notice identical to this one except for the removal of this paragraph
(this paragraph not being relevant to the printed manual).
@end ignore
Permission is granted to copy and distribute modified versions of this
manual under the conditions for verbatim copying, provided that the entire
resulting derived work is distributed under the terms of a permission
notice identical to this one.
Permission is granted to copy and distribute translations of this manual
into another language, under the above conditions for modified versions,
except that this permission notice may be stated in a translation approved
by the Foundation.
@end ifinfo
@titlepage
@sp 10
@title GNU Readline Library
@subtitle Edition @value{EDITION}, for @code{Readline Library} Version @value{VERSION}.
@subtitle @value{UPDATE-MONTH}
@author Brian Fox, Free Software Foundation
@author Chet Ramey, Case Western Reserve University
@page
This document describes the GNU Readline Library, a utility which aids
in the consistency of user interface across discrete programs that need
to provide a command line interface.
Published by the Free Software Foundation @*
675 Massachusetts Avenue, @*
Cambridge, MA 02139 USA
Permission is granted to make and distribute verbatim copies of
this manual provided the copyright notice and this permission notice
are preserved on all copies.
Permission is granted to copy and distribute modified versions of this
manual under the conditions for verbatim copying, provided that the entire
resulting derived work is distributed under the terms of a permission
notice identical to this one.
Permission is granted to copy and distribute translations of this manual
into another language, under the above conditions for modified versions,
except that this permission notice may be stated in a translation approved
by the Foundation.
@vskip 0pt plus 1filll
Copyright @copyright{} 1989, 1991 Free Software Foundation, Inc.
@end titlepage
@ifinfo
@node Top
@top GNU Readline Library
This document describes the GNU Readline Library, a utility which aids
in the consistency of user interface across discrete programs that need
to provide a command line interface.
@menu
* Command Line Editing:: GNU Readline User's Manual.
* Programming with GNU Readline:: GNU Readline Programmer's Manual.
* Concept Index:: Index of concepts described in this manual.
* Function and Variable Index:: Index of externally visible functions
and variables.
@end menu
@end ifinfo
@include rluser.texinfo
@include rltech.texinfo
@node Concept Index
@unnumbered Concept Index
@printindex cp
@node Function and Variable Index
@unnumbered Function and Variable Index
@printindex fn
@contents
@bye

File diff suppressed because it is too large Load diff

View file

@ -0,0 +1,875 @@
@comment %**start of header (This is for running Texinfo on a region.)
@setfilename rluser.info
@comment %**end of header (This is for running Texinfo on a region.)
@setchapternewpage odd
@ignore
This file documents the end user interface to the GNU command line
editing features. It is to be an appendix to manuals for programs which
use these features. There is a document entitled "readline.texinfo"
which contains both end-user and programmer documentation for the GNU
Readline Library.
Copyright (C) 1988 Free Software Foundation, Inc.
Authored by Brian Fox and Chet Ramey.
Permission is granted to process this file through Tex and print the
results, provided the printed document carries copying permission notice
identical to this one except for the removal of this paragraph (this
paragraph not being relevant to the printed manual).
Permission is granted to make and distribute verbatim copies of this manual
provided the copyright notice and this permission notice are preserved on
all copies.
Permission is granted to copy and distribute modified versions of this
manual under the conditions for verbatim copying, provided also that the
GNU Copyright statement is available to the distributee, and provided that
the entire resulting derived work is distributed under the terms of a
permission notice identical to this one.
Permission is granted to copy and distribute translations of this manual
into another language, under the above conditions for modified versions.
@end ignore
@comment If you are including this manual as an appendix, then set the
@comment variable readline-appendix.
@node Command Line Editing
@chapter Command Line Editing
This chapter describes the basic features of the GNU
command line editing interface.
@menu
* Introduction and Notation:: Notation used in this text.
* Readline Interaction:: The minimum set of commands for editing a line.
* Readline Init File:: Customizing Readline from a user's view.
* Bindable Readline Commands:: A description of most of the Readline commands
available for binding
* Readline vi Mode:: A short description of how to make Readline
behave like the vi editor.
@end menu
@node Introduction and Notation
@section Introduction to Line Editing
The following paragraphs describe the notation used to represent
keystrokes.
The text @key{C-k} is read as `Control-K' and describes the character
produced when the Control key is depressed and the @key{k} key is struck.
The text @key{M-k} is read as `Meta-K' and describes the character
produced when the meta key (if you have one) is depressed, and the @key{k}
key is struck. If you do not have a meta key, the identical keystroke
can be generated by typing @key{ESC} @i{first}, and then typing @key{k}.
Either process is known as @dfn{metafying} the @key{k} key.
The text @key{M-C-k} is read as `Meta-Control-k' and describes the
character produced by @dfn{metafying} @key{C-k}.
In addition, several keys have their own names. Specifically,
@key{DEL}, @key{ESC}, @key{LFD}, @key{SPC}, @key{RET}, and @key{TAB} all
stand for themselves when seen in this text, or in an init file
(@pxref{Readline Init File}, for more info).
@node Readline Interaction
@section Readline Interaction
@cindex interaction, readline
Often during an interactive session you type in a long line of text,
only to notice that the first word on the line is misspelled. The
Readline library gives you a set of commands for manipulating the text
as you type it in, allowing you to just fix your typo, and not forcing
you to retype the majority of the line. Using these editing commands,
you move the cursor to the place that needs correction, and delete or
insert the text of the corrections. Then, when you are satisfied with
the line, you simply press @key{RETURN}. You do not have to be at the
end of the line to press @key{RETURN}; the entire line is accepted
regardless of the location of the cursor within the line.
@menu
* Readline Bare Essentials:: The least you need to know about Readline.
* Readline Movement Commands:: Moving about the input line.
* Readline Killing Commands:: How to delete text, and how to get it back!
* Readline Arguments:: Giving numeric arguments to commands.
@end menu
@node Readline Bare Essentials
@subsection Readline Bare Essentials
In order to enter characters into the line, simply type them. The typed
character appears where the cursor was, and then the cursor moves one
space to the right. If you mistype a character, you can use your
erase character to back up and delete the mistyped character.
Sometimes you may miss typing a character that you wanted to type, and
not notice your error until you have typed several other characters. In
that case, you can type @key{C-b} to move the cursor to the left, and then
correct your mistake. Afterwards, you can move the cursor to the right
with @key{C-f}.
When you add text in the middle of a line, you will notice that characters
to the right of the cursor are `pushed over' to make room for the text
that you have inserted. Likewise, when you delete text behind the cursor,
characters to the right of the cursor are `pulled back' to fill in the
blank space created by the removal of the text. A list of the basic bare
essentials for editing the text of an input line follows.
@table @asis
@item @key{C-b}
Move back one character.
@item @key{C-f}
Move forward one character.
@item @key{DEL}
Delete the character to the left of the cursor.
@item @key{C-d}
Delete the character underneath the cursor.
@item @w{Printing characters}
Insert the character into the line at the cursor.
@item @key{C-_}
Undo the last thing that you did. You can undo all the way back to an
empty line.
@end table
@node Readline Movement Commands
@subsection Readline Movement Commands
The above table describes the most basic possible keystrokes that you need
in order to do editing of the input line. For your convenience, many
other commands have been added in addition to @key{C-b}, @key{C-f},
@key{C-d}, and @key{DEL}. Here are some commands for moving more rapidly
about the line.
@table @key
@item C-a
Move to the start of the line.
@item C-e
Move to the end of the line.
@item M-f
Move forward a word.
@item M-b
Move backward a word.
@item C-l
Clear the screen, reprinting the current line at the top.
@end table
Notice how @key{C-f} moves forward a character, while @key{M-f} moves
forward a word. It is a loose convention that control keystrokes
operate on characters while meta keystrokes operate on words.
@node Readline Killing Commands
@subsection Readline Killing Commands
@cindex Killing text
@cindex Yanking text
@dfn{Killing} text means to delete the text from the line, but to save
it away for later use, usually by @dfn{yanking} (re-inserting)
it back into the line.
If the description for a command says that it `kills' text, then you can
be sure that you can get the text back in a different (or the same)
place later.
When you use a kill command, the text is saved in a @dfn{kill-ring}.
Any number of consecutive kills save all of the killed text together, so
that when you yank it back, you get it all. The kill
ring is not line specific; the text that you killed on a previously
typed line is available to be yanked back later, when you are typing
another line.
@cindex Kill ring
Here is the list of commands for killing text.
@table @key
@item C-k
Kill the text from the current cursor position to the end of the line.
@item M-d
Kill from the cursor to the end of the current word, or if between
words, to the end of the next word.
@item M-DEL
Kill from the cursor the start of the previous word, or if between
words, to the start of the previous word.
@item C-w
Kill from the cursor to the previous whitespace. This is different than
@key{M-DEL} because the word boundaries differ.
@end table
And, here is how to @dfn{yank} the text back into the line. Yanking
means to copy the most-recently-killed text from the kill buffer.
@table @key
@item C-y
Yank the most recently killed text back into the buffer at the cursor.
@item M-y
Rotate the kill-ring, and yank the new top. You can only do this if
the prior command is @key{C-y} or @key{M-y}.
@end table
@node Readline Arguments
@subsection Readline Arguments
You can pass numeric arguments to Readline commands. Sometimes the
argument acts as a repeat count, other times it is the @i{sign} of the
argument that is significant. If you pass a negative argument to a
command which normally acts in a forward direction, that command will
act in a backward direction. For example, to kill text back to the
start of the line, you might type @key{M--} @key{C-k}.
The general way to pass numeric arguments to a command is to type meta
digits before the command. If the first `digit' you type is a minus
sign (@key{-}), then the sign of the argument will be negative. Once
you have typed one meta digit to get the argument started, you can type
the remainder of the digits, and then the command. For example, to give
the @key{C-d} command an argument of 10, you could type @key{M-1 0 C-d}.
@node Readline Init File
@section Readline Init File
Although the Readline library comes with a set of Emacs-like
keybindings installed by default,
it is possible that you would like to use a different set
of keybindings. You can customize programs that use Readline by putting
commands in an @dfn{init} file in your home directory. The name of this
@ifset BashFeatures
file is taken from the value of the shell variable @code{INPUTRC}. If
@end ifset
@ifclear BashFeatures
file is taken from the value of the environment variable @code{INPUTRC}. If
@end ifclear
that variable is unset, the default is @file{~/.inputrc}.
When a program which uses the Readline library starts up, the
init file is read, and the key bindings are set.
In addition, the @code{C-x C-r} command re-reads this init file, thus
incorporating any changes that you might have made to it.
@menu
* Readline Init Syntax:: Syntax for the commands in the inputrc file.
* Conditional Init Constructs:: Conditional key bindings in the inputrc file.
@end menu
@node Readline Init Syntax
@subsection Readline Init Syntax
There are only a few basic constructs allowed in the
Readline init file. Blank lines are ignored.
Lines beginning with a @key{#} are comments.
Lines beginning with a @key{$} indicate conditional
constructs (@pxref{Conditional Init Constructs}). Other lines
denote variable settings and key bindings.
@table @asis
@item Variable Settings
You can change the state of a few variables in Readline by
using the @code{set} command within the init file. Here is how you
would specify that you wish to use @code{vi} line editing commands:
@example
set editing-mode vi
@end example
Right now, there are only a few variables which can be set;
so few, in fact, that we just list them here:
@table @code
@item editing-mode
@vindex editing-mode
The @code{editing-mode} variable controls which editing mode you are
using. By default, Readline starts up in Emacs editing mode, where
the keystrokes are most similar to Emacs. This variable can be
set to either @code{emacs} or @code{vi}.
@item horizontal-scroll-mode
@vindex horizontal-scroll-mode
This variable can be set to either @code{On} or @code{Off}. Setting it
to @code{On} means that the text of the lines that you edit will scroll
horizontally on a single screen line when they are longer than the width
of the screen, instead of wrapping onto a new screen line. By default,
this variable is set to @code{Off}.
@item mark-modified-lines
@vindex mark-modified-lines
This variable, when set to @code{On}, says to display an asterisk
(@samp{*}) at the start of history lines which have been modified.
This variable is @code{off} by default.
@item bell-style
@vindex bell-style
Controls what happens when Readline wants to ring the terminal bell.
If set to @code{none}, Readline never rings the bell. If set to
@code{visible}, Readline uses a visible bell if one is available.
If set to @code{audible} (the default), Readline attempts to ring
the terminal's bell.
@item comment-begin
@vindex comment-begin
The string to insert at the beginning of the line when the
@code{vi-comment} command is executed. The default value
is @code{"#"}.
@item meta-flag
@vindex meta-flag
If set to @code{on}, Readline will enable eight-bit input (it
will not strip the eighth bit from the characters it reads),
regardless of what the terminal claims it can support. The
default value is @code{off}.
@item convert-meta
@vindex convert-meta
If set to @code{on}, Readline will convert characters with the
eigth bit set to an ASCII key sequence by stripping the eigth
bit and prepending an @key{ESC} character, converting them to a
meta-prefixed key sequence. The default value is @code{on}.
@item output-meta
@vindex output-meta
If set to @code{on}, Readline will display characters with the
eighth bit set directly rather than as a meta-prefixed escape
sequence. The default is @code{off}.
@item completion-query-items
@vindex completion-query-items
The number of possible completions that determines when the user is
asked whether he wants to see the list of possibilities. If the
number of possible completions is greater than this value,
Readline will ask the user whether or not he wishes to view
them; otherwise, they are simply listed. The default limit is
@code{100}.
@item keymap
@vindex keymap
Sets Readline's idea of the current keymap for key binding commands.
Acceptable @code{keymap} names are
@code{emacs},
@code{emacs-standard},
@code{emacs-meta},
@code{emacs-ctlx},
@code{vi},
@code{vi-move},
@code{vi-command}, and
@code{vi-insert}.
@code{vi} is equivalent to @code{vi-command}; @code{emacs} is
equivalent to @code{emacs-standard}. The default value is @code{emacs}.
The value of the @code{editing-mode} variable also affects the
default keymap.
@item show-all-if-ambiguous
@vindex show-all-if-ambiguous
This alters the default behavior of the completion functions. If
set to @code{on},
words which have more than one possible completion cause the
matches to be listed immediately instead of ringing the bell.
The default value is @code{off}.
@item expand-tilde
@vindex expand-tilde
If set to @code{on}, tilde expansion is performed when Readline
attempts word completion. The default is @code{off}.
@end table
@item Key Bindings
The syntax for controlling key bindings in the init file is
simple. First you have to know the name of the command that you
want to change. The following pages contain tables of the command name,
the default keybinding, and a short description of what the command
does.
Once you know the name of the command, simply place the name of the key
you wish to bind the command to, a colon, and then the name of the
command on a line in the init file. The name of the key
can be expressed in different ways, depending on which is most
comfortable for you.
@table @asis
@item @w{@var{keyname}: @var{function-name} or @var{macro}}
@var{keyname} is the name of a key spelled out in English. For example:
@example
Control-u: universal-argument
Meta-Rubout: backward-kill-word
Control-o: ">&output"
@end example
In the above example, @samp{C-u} is bound to the function
@code{universal-argument}, and @samp{C-o} is bound to run the macro
expressed on the right hand side (that is, to insert the text
@samp{>&output} into the line).
@item @w{"@var{keyseq}": @var{function-name} or @var{macro}}
@var{keyseq} differs from @var{keyname} above in that strings
denoting an entire key sequence can be specified, by placing
the key sequence in double quotes. Some GNU Emacs style key
escapes can be used, as in the following example, but the
special character names are not recognized.
@example
"\C-u": universal-argument
"\C-x\C-r": re-read-init-file
"\e[11~": "Function Key 1"
@end example
In the above example, @samp{C-u} is bound to the function
@code{universal-argument} (just as it was in the first example),
@samp{C-x C-r} is bound to the function @code{re-read-init-file}, and
@samp{ESC [ 1 1 ~} is bound to insert the text @samp{Function Key 1}.
The following escape sequences are available when specifying key
sequences:
@table @code
@item @kbd{\C-}
control prefix
@item @kbd{\M-}
meta prefix
@item @kbd{\e}
an escape character
@item @kbd{\\}
backslash
@item @kbd{\"}
@key{"}
@item @kbd{\'}
@key{'}
@end table
When entering the text of a macro, single or double quotes should
be used to indicate a macro definition. Unquoted text
is assumed to be a function name. Backslash
will quote any character in the macro text, including @key{"}
and @key{'}.
For example, the following binding will make @kbd{C-x \}
insert a single @key{\} into the line:
@example
"\C-x\\": "\\"
@end example
@end table
@end table
@node Conditional Init Constructs
@subsection Conditional Init Constructs
Readline implements a facility similar in spirit to the conditional
compilation features of the C preprocessor which allows key
bindings and variable settings to be performed as the result
of tests. There are three parser directives used.
@ftable @code
@item $if
The @code{$if} construct allows bindings to be made based on the
editing mode, the terminal being used, or the application using
Readline. The text of the test extends to the end of the line;
no characters are required to isolate it.
@table @code
@item mode
The @code{mode=} form of the @code{$if} directive is used to test
whether Readline is in @code{emacs} or @code{vi} mode.
This may be used in conjunction
with the @samp{set keymap} command, for instance, to set bindings in
the @code{emacs-standard} and @code{emacs-ctlx} keymaps only if
Readline is starting out in @code{emacs} mode.
@item term
The @code{term=} form may be used to include terminal-specific
key bindings, perhaps to bind the key sequences output by the
terminal's function keys. The word on the right side of the
@samp{=} is tested against the full name of the terminal and the
portion of the terminal name before the first @samp{-}. This
allows @var{sun} to match both @var{sun} and @var{sun-cmd},
for instance.
@item application
The @var{application} construct is used to include
application-specific settings. Each program using the Readline
library sets the @var{application name}, and you can test for it.
This could be used to bind key sequences to functions useful for
a specific program. For instance, the following command adds a
key sequence that quotes the current or previous word in Bash:
@example
$if bash
# Quote the current or previous word
"\C-xq": "\eb\"\ef\""
$endif
@end example
@end table
@item $endif
This command, as you saw in the previous example, terminates an
@code{$if} command.
@item $else
Commands in this branch of the @code{$if} directive are executed if
the test fails.
@end ftable
@node Bindable Readline Commands
@section Bindable Readline Commands
@menu
* Commands For Moving:: Moving about the line.
* Commands For History:: Getting at previous lines.
* Commands For Text:: Commands for changing text.
* Commands For Killing:: Commands for killing and yanking.
* Numeric Arguments:: Specifying numeric arguments, repeat counts.
* Commands For Completion:: Getting Readline to do the typing for you.
* Keyboard Macros:: Saving and re-executing typed characters
* Miscellaneous Commands:: Other miscellaneous commands.
@end menu
@node Commands For Moving
@subsection Commands For Moving
@ftable @code
@item beginning-of-line (C-a)
Move to the start of the current line.
@item end-of-line (C-e)
Move to the end of the line.
@item forward-char (C-f)
Move forward a character.
@item backward-char (C-b)
Move back a character.
@item forward-word (M-f)
Move forward to the end of the next word. Words are composed of
letters and digits.
@item backward-word (M-b)
Move back to the start of this, or the previous, word. Words are
composed of letters and digits.
@item clear-screen (C-l)
Clear the screen and redraw the current line,
leaving the current line at the top of the screen.
@item redraw-current-line ()
Refresh the current line. By default, this is unbound.
@end ftable
@node Commands For History
@subsection Commands For Manipulating The History
@ftable @code
@item accept-line (Newline, Return)
@ifset BashFeatures
Accept the line regardless of where the cursor is. If this line is
non-empty, add it to the history list according to the setting of
the @code{HISTCONTROL} variable. If this line was a history
line, then restore the history line to its original state.
@end ifset
@ifclear BashFeatures
Accept the line regardless of where the cursor is. If this line is
non-empty, add it to the history list. If this line was a history
line, then restore the history line to its original state.
@end ifclear
@item previous-history (C-p)
Move `up' through the history list.
@item next-history (C-n)
Move `down' through the history list.
@item beginning-of-history (M-<)
Move to the first line in the history.
@item end-of-history (M->)
Move to the end of the input history, i.e., the line you are entering.
@item reverse-search-history (C-r)
Search backward starting at the current line and moving `up' through
the history as necessary. This is an incremental search.
@item forward-search-history (C-s)
Search forward starting at the current line and moving `down' through
the the history as necessary. This is an incremental search.
@item non-incremental-reverse-search-history (M-p)
Search backward starting at the current line and moving `up'
through the history as necessary using a non-incremental search
for a string supplied by the user.
@item non-incremental-forward-search-history (M-n)
Search forward starting at the current line and moving `down'
through the the history as necessary using a non-incremental search
for a string supplied by the user.
@item history-search-forward ()
Search forward through the history for the string of characters
between the start of the current line and the current point. This
is a non-incremental search. By default, this command is unbound.
@item history-search-backward ()
Search backward through the history for the string of characters
between the start of the current line and the current point. This
is a non-incremental search. By default, this command is unbound.
@item yank-nth-arg (M-C-y)
Insert the first argument to the previous command (usually
the second word on the previous line). With an argument @var{n},
insert the @var{n}th word from the previous command (the words
in the previous command begin with word 0). A negative argument
inserts the @var{n}th word from the end of the previous command.
@item yank-last-arg (M-., M-_)
Insert last argument to the previous command (the last word on the
previous line). With an
argument, behave exactly like @code{yank-nth-arg}.
@end ftable
@node Commands For Text
@subsection Commands For Changing Text
@ftable @code
@item delete-char (C-d)
Delete the character under the cursor. If the cursor is at the
beginning of the line, there are no characters in the line, and
the last character typed was not C-d, then return EOF.
@item backward-delete-char (Rubout)
Delete the character behind the cursor. A numeric arg says to kill
the characters instead of deleting them.
@item quoted-insert (C-q, C-v)
Add the next character that you type to the line verbatim. This is
how to insert key sequences like @key{C-q}, for example.
@item tab-insert (M-TAB)
Insert a tab character.
@item self-insert (a, b, A, 1, !, ...)
Insert yourself.
@item transpose-chars (C-t)
Drag the character before the cursor forward over
the character at the cursor, moving the
cursor forward as well. If the insertion point
is at the end of the line, then this
transposes the last two characters of the line.
Negative argumentss don't work.
@item transpose-words (M-t)
Drag the word behind the cursor past the word in front of the cursor
moving the cursor over that word as well.
@item upcase-word (M-u)
Uppercase the current (or following) word. With a negative argument,
do the previous word, but do not move the cursor.
@item downcase-word (M-l)
Lowercase the current (or following) word. With a negative argument,
do the previous word, but do not move the cursor.
@item capitalize-word (M-c)
Capitalize the current (or following) word. With a negative argument,
do the previous word, but do not move the cursor.
@end ftable
@node Commands For Killing
@subsection Killing And Yanking
@ftable @code
@item kill-line (C-k)
Kill the text from the current cursor position to the end of the line.
@item backward-kill-line (C-x Rubout)
Kill backward to the beginning of the line.
@item unix-line-discard (C-u)
Kill backward from the cursor to the beginning of the current line.
Save the killed text on the kill-ring.
@item kill-whole-line ()
Kill all characters on the current line, no matter where the
cursor is. By default, this is unbound.
@item kill-word (M-d)
Kill from the cursor to the end of the current word, or if between
words, to the end of the next word. Word boundaries are the same
as @code{forward-word}.
@item backward-kill-word (M-DEL)
Kill the word behind the cursor. Word boundaries are the same
as @code{backward-word}.
@item unix-word-rubout (C-w)
Kill the word behind the cursor, using white space as a word
boundary. The killed text is saved on the kill-ring.
@item delete-horizontal-space ()
Delete all spaces and tabs around point. By default, this is unbound.
@item yank (C-y)
Yank the top of the kill ring into the buffer at the current
cursor position.
@item yank-pop (M-y)
Rotate the kill-ring, and yank the new top. You can only do this if
the prior command is yank or yank-pop.
@end ftable
@node Numeric Arguments
@subsection Specifying Numeric Arguments
@ftable @code
@item digit-argument (M-0, M-1, ... M--)
Add this digit to the argument already accumulating, or start a new
argument. M-- starts a negative argument.
@item universal-argument ()
Each time this is executed, the argument count is multiplied by four.
The argument count is initially one, so executing this function the
first time makes the argument count four. By default, this is not
bound to a key.
@end ftable
@node Commands For Completion
@subsection Letting Readline Type For You
@ftable @code
@item complete (TAB)
Attempt to do completion on the text before the cursor. This is
application-specific. Generally, if you are typing a filename
argument, you can do filename completion; if you are typing a command,
you can do command completion, if you are typing in a symbol to GDB, you
can do symbol name completion, if you are typing in a variable to Bash,
you can do variable name completion, and so on.
@ifset BashFeatures
See the Bash manual page for a complete list of available completion
functions.
@end ifset
@item possible-completions (M-?)
List the possible completions of the text before the cursor.
@item insert-completions ()
Insert all completions of the text before point that would have
been generated by @code{possible-completions}. By default, this
is not bound to a key.
@end ftable
@node Keyboard Macros
@subsection Keyboard Macros
@ftable @code
@item start-kbd-macro (C-x ()
Begin saving the characters typed into the current keyboard macro.
@item end-kbd-macro (C-x ))
Stop saving the characters typed into the current keyboard macro
and save the definition.
@item call-last-kbd-macro (C-x e)
Re-execute the last keyboard macro defined, by making the characters
in the macro appear as if typed at the keyboard.
@end ftable
@node Miscellaneous Commands
@subsection Some Miscellaneous Commands
@ftable @code
@item re-read-init-file (C-x C-r)
Read in the contents of your init file, and incorporate
any bindings or variable assignments found there.
@item abort (C-g)
Abort the current editing command and
ring the terminal's bell (subject to the setting of
@code{bell-style}).
@item do-uppercase-version (M-a, M-b, ...)
Run the command that is bound to the corresoponding uppercase
character.
@item prefix-meta (ESC)
Make the next character that you type be metafied. This is for people
without a meta key. Typing @samp{ESC f} is equivalent to typing
@samp{M-f}.
@item undo (C-_, C-x C-u)
Incremental undo, separately remembered for each line.
@item revert-line (M-r)
Undo all changes made to this line. This is like typing the @code{undo}
command enough times to get back to the beginning.
@item tilde-expand (M-~)
Perform tilde expansion on the current word.
@item dump-functions ()
Print all of the functions and their key bindings to the
readline output stream. If a numeric argument is supplied,
the output is formatted in such a way that it can be made part
of an @var{inputrc} file.
@ifset BashFeatures
@item display-shell-version (C-x C-v)
Display version information about the current instance of Bash.
@item shell-expand-line (M-C-e)
Expand the line the way the shell does when it reads it. This
performs alias and history expansion as well as all of the shell
word expansions.
@item history-expand-line (M-^)
Perform history expansion on the current line.
@item insert-last-argument (M-., M-_)
A synonym for @code{yank-last-arg}.
@item operate-and-get-next (C-o)
Accept the current line for execution and fetch the next line
relative to the current line from the history for editing. Any
argument is ignored.
@item emacs-editing-mode (C-e)
When in @code{vi} editing mode, this causes a switch back to
emacs editing mode, as if the command @code{set -o emacs} had
been executed.
@end ifset
@end ftable
@node Readline vi Mode
@section Readline vi Mode
While the Readline library does not have a full set of @code{vi}
editing functions, it does contain enough to allow simple editing
of the line. The Readline @code{vi} mode behaves as specified in
the Posix 1003.2 standard.
@ifset BashFeatures
In order to switch interactively between @code{Emacs} and @code{Vi}
editing modes, use the @code{set -o emacs} and @code{set -o vi}
commands (@pxref{The Set Builtin}).
@end ifset
@ifclear BashFeatures
In order to switch interactively between @code{Emacs} and @code{Vi}
editing modes, use the command M-C-j (toggle-editing-mode).
@end ifclear
The Readline default is @code{emacs} mode.
When you enter a line in @code{vi} mode, you are already placed in
`insertion' mode, as if you had typed an @samp{i}. Pressing @key{ESC}
switches you into `command' mode, where you can edit the text of the
line with the standard @code{vi} movement keys, move to previous
history lines with @samp{k}, and following lines with @samp{j}, and
so forth.

1666
lib/readline/doc/texindex.c Normal file

File diff suppressed because it is too large Load diff

885
lib/readline/emacs_keymap.c Normal file
View file

@ -0,0 +1,885 @@
/* emacs_keymap.c -- the keymap for emacs_mode in readline (). */
/* Copyright (C) 1987, 1989, 1992 Free Software Foundation, Inc.
This file is part of the GNU Readline Library, a library for
reading lines of text with interactive input and history editing.
The GNU Readline Library is free software; you can redistribute it
and/or modify it under the terms of the GNU General Public License
as published by the Free Software Foundation; either version 1, or
(at your option) any later version.
The GNU Readline Library is distributed in the hope that it will be
useful, but WITHOUT ANY WARRANTY; without even the implied warranty
of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
The GNU General Public License is often shipped with GNU software, and
is generally kept in a file called COPYING or LICENSE. If you do not
have a copy of the license, write to the Free Software Foundation,
675 Mass Ave, Cambridge, MA 02139, USA. */
#if !defined (BUFSIZ)
#include <stdio.h>
#endif /* !BUFSIZ */
#include "readline.h"
/* An array of function pointers, one for each possible key.
If the type byte is ISKMAP, then the pointer is the address of
a keymap. */
KEYMAP_ENTRY_ARRAY emacs_standard_keymap = {
/* Control keys. */
{ ISFUNC, (Function *)0x0 }, /* Control-@ */
{ ISFUNC, rl_beg_of_line }, /* Control-a */
{ ISFUNC, rl_backward }, /* Control-b */
{ ISFUNC, (Function *)0x0 }, /* Control-c */
{ ISFUNC, rl_delete }, /* Control-d */
{ ISFUNC, rl_end_of_line }, /* Control-e */
{ ISFUNC, rl_forward }, /* Control-f */
{ ISFUNC, rl_abort }, /* Control-g */
{ ISFUNC, rl_rubout }, /* Control-h */
{ ISFUNC, rl_complete }, /* Control-i */
{ ISFUNC, rl_newline }, /* Control-j */
{ ISFUNC, rl_kill_line }, /* Control-k */
{ ISFUNC, rl_clear_screen }, /* Control-l */
{ ISFUNC, rl_newline }, /* Control-m */
{ ISFUNC, rl_get_next_history }, /* Control-n */
{ ISFUNC, (Function *)0x0 }, /* Control-o */
{ ISFUNC, rl_get_previous_history }, /* Control-p */
{ ISFUNC, rl_quoted_insert }, /* Control-q */
{ ISFUNC, rl_reverse_search_history }, /* Control-r */
{ ISFUNC, rl_forward_search_history }, /* Control-s */
{ ISFUNC, rl_transpose_chars }, /* Control-t */
{ ISFUNC, rl_unix_line_discard }, /* Control-u */
{ ISFUNC, rl_quoted_insert }, /* Control-v */
{ ISFUNC, rl_unix_word_rubout }, /* Control-w */
{ ISKMAP, (Function *)emacs_ctlx_keymap }, /* Control-x */
{ ISFUNC, rl_yank }, /* Control-y */
{ ISFUNC, (Function *)0x0 }, /* Control-z */
{ ISKMAP, (Function *)emacs_meta_keymap }, /* Control-[ */
{ ISFUNC, (Function *)0x0 }, /* Control-\ */
{ ISFUNC, (Function *)0x0 }, /* Control-] */
{ ISFUNC, (Function *)0x0 }, /* Control-^ */
{ ISFUNC, rl_undo_command }, /* Control-_ */
/* The start of printing characters. */
{ ISFUNC, rl_insert }, /* SPACE */
{ ISFUNC, rl_insert }, /* ! */
{ ISFUNC, rl_insert }, /* " */
{ ISFUNC, rl_insert }, /* # */
{ ISFUNC, rl_insert }, /* $ */
{ ISFUNC, rl_insert }, /* % */
{ ISFUNC, rl_insert }, /* & */
{ ISFUNC, rl_insert }, /* ' */
{ ISFUNC, rl_insert }, /* ( */
#if defined (PAREN_MATCHING)
{ ISFUNC, rl_insert_close }, /* ) */
#else
{ ISFUNC, rl_insert }, /* ) */
#endif /* !PAREN_MATCHING */
{ ISFUNC, rl_insert }, /* * */
{ ISFUNC, rl_insert }, /* + */
{ ISFUNC, rl_insert }, /* , */
{ ISFUNC, rl_insert }, /* - */
{ ISFUNC, rl_insert }, /* . */
{ ISFUNC, rl_insert }, /* / */
/* Regular digits. */
{ ISFUNC, rl_insert }, /* 0 */
{ ISFUNC, rl_insert }, /* 1 */
{ ISFUNC, rl_insert }, /* 2 */
{ ISFUNC, rl_insert }, /* 3 */
{ ISFUNC, rl_insert }, /* 4 */
{ ISFUNC, rl_insert }, /* 5 */
{ ISFUNC, rl_insert }, /* 6 */
{ ISFUNC, rl_insert }, /* 7 */
{ ISFUNC, rl_insert }, /* 8 */
{ ISFUNC, rl_insert }, /* 9 */
/* A little more punctuation. */
{ ISFUNC, rl_insert }, /* : */
{ ISFUNC, rl_insert }, /* ; */
{ ISFUNC, rl_insert }, /* < */
{ ISFUNC, rl_insert }, /* = */
{ ISFUNC, rl_insert }, /* > */
{ ISFUNC, rl_insert }, /* ? */
{ ISFUNC, rl_insert }, /* @ */
/* Uppercase alphabet. */
{ ISFUNC, rl_insert }, /* A */
{ ISFUNC, rl_insert }, /* B */
{ ISFUNC, rl_insert }, /* C */
{ ISFUNC, rl_insert }, /* D */
{ ISFUNC, rl_insert }, /* E */
{ ISFUNC, rl_insert }, /* F */
{ ISFUNC, rl_insert }, /* G */
{ ISFUNC, rl_insert }, /* H */
{ ISFUNC, rl_insert }, /* I */
{ ISFUNC, rl_insert }, /* J */
{ ISFUNC, rl_insert }, /* K */
{ ISFUNC, rl_insert }, /* L */
{ ISFUNC, rl_insert }, /* M */
{ ISFUNC, rl_insert }, /* N */
{ ISFUNC, rl_insert }, /* O */
{ ISFUNC, rl_insert }, /* P */
{ ISFUNC, rl_insert }, /* Q */
{ ISFUNC, rl_insert }, /* R */
{ ISFUNC, rl_insert }, /* S */
{ ISFUNC, rl_insert }, /* T */
{ ISFUNC, rl_insert }, /* U */
{ ISFUNC, rl_insert }, /* V */
{ ISFUNC, rl_insert }, /* W */
{ ISFUNC, rl_insert }, /* X */
{ ISFUNC, rl_insert }, /* Y */
{ ISFUNC, rl_insert }, /* Z */
/* Some more punctuation. */
{ ISFUNC, rl_insert }, /* [ */
{ ISFUNC, rl_insert }, /* \ */
#if defined (PAREN_MATCHING)
{ ISFUNC, rl_insert_close }, /* ] */
#else
{ ISFUNC, rl_insert }, /* ] */
#endif /* !PAREN_MATCHING */
{ ISFUNC, rl_insert }, /* ^ */
{ ISFUNC, rl_insert }, /* _ */
{ ISFUNC, rl_insert }, /* ` */
/* Lowercase alphabet. */
{ ISFUNC, rl_insert }, /* a */
{ ISFUNC, rl_insert }, /* b */
{ ISFUNC, rl_insert }, /* c */
{ ISFUNC, rl_insert }, /* d */
{ ISFUNC, rl_insert }, /* e */
{ ISFUNC, rl_insert }, /* f */
{ ISFUNC, rl_insert }, /* g */
{ ISFUNC, rl_insert }, /* h */
{ ISFUNC, rl_insert }, /* i */
{ ISFUNC, rl_insert }, /* j */
{ ISFUNC, rl_insert }, /* k */
{ ISFUNC, rl_insert }, /* l */
{ ISFUNC, rl_insert }, /* m */
{ ISFUNC, rl_insert }, /* n */
{ ISFUNC, rl_insert }, /* o */
{ ISFUNC, rl_insert }, /* p */
{ ISFUNC, rl_insert }, /* q */
{ ISFUNC, rl_insert }, /* r */
{ ISFUNC, rl_insert }, /* s */
{ ISFUNC, rl_insert }, /* t */
{ ISFUNC, rl_insert }, /* u */
{ ISFUNC, rl_insert }, /* v */
{ ISFUNC, rl_insert }, /* w */
{ ISFUNC, rl_insert }, /* x */
{ ISFUNC, rl_insert }, /* y */
{ ISFUNC, rl_insert }, /* z */
/* Final punctuation. */
{ ISFUNC, rl_insert }, /* { */
{ ISFUNC, rl_insert }, /* | */
#if defined (PAREN_MATCHING)
{ ISFUNC, rl_insert_close }, /* } */
#else
{ ISFUNC, rl_insert }, /* } */
#endif /* !PAREN_MATCHING */
{ ISFUNC, rl_insert }, /* ~ */
{ ISFUNC, rl_rubout }, /* RUBOUT */
#if KEYMAP_SIZE > 128
/* Pure 8-bit characters (128 - 159).
These might be used in some
character sets. */
{ ISFUNC, rl_insert }, /* ? */
{ ISFUNC, rl_insert }, /* ? */
{ ISFUNC, rl_insert }, /* ? */
{ ISFUNC, rl_insert }, /* ? */
{ ISFUNC, rl_insert }, /* ? */
{ ISFUNC, rl_insert }, /* ? */
{ ISFUNC, rl_insert }, /* ? */
{ ISFUNC, rl_insert }, /* ? */
{ ISFUNC, rl_insert }, /* ? */
{ ISFUNC, rl_insert }, /* ? */
{ ISFUNC, rl_insert }, /* ? */
{ ISFUNC, rl_insert }, /* ? */
{ ISFUNC, rl_insert }, /* ? */
{ ISFUNC, rl_insert }, /* ? */
{ ISFUNC, rl_insert }, /* ? */
{ ISFUNC, rl_insert }, /* ? */
{ ISFUNC, rl_insert }, /* ? */
{ ISFUNC, rl_insert }, /* ? */
{ ISFUNC, rl_insert }, /* ? */
{ ISFUNC, rl_insert }, /* ? */
{ ISFUNC, rl_insert }, /* ? */
{ ISFUNC, rl_insert }, /* ? */
{ ISFUNC, rl_insert }, /* ? */
{ ISFUNC, rl_insert }, /* ? */
{ ISFUNC, rl_insert }, /* ? */
{ ISFUNC, rl_insert }, /* ? */
{ ISFUNC, rl_insert }, /* ? */
{ ISFUNC, rl_insert }, /* ? */
{ ISFUNC, rl_insert }, /* ? */
{ ISFUNC, rl_insert }, /* ? */
{ ISFUNC, rl_insert }, /* ? */
{ ISFUNC, rl_insert }, /* ? */
/* ISO Latin-1 characters (160 - 255) */
{ ISFUNC, rl_insert }, /* No-break space */
{ ISFUNC, rl_insert }, /* Inverted exclamation mark */
{ ISFUNC, rl_insert }, /* Cent sign */
{ ISFUNC, rl_insert }, /* Pound sign */
{ ISFUNC, rl_insert }, /* Currency sign */
{ ISFUNC, rl_insert }, /* Yen sign */
{ ISFUNC, rl_insert }, /* Broken bar */
{ ISFUNC, rl_insert }, /* Section sign */
{ ISFUNC, rl_insert }, /* Diaeresis */
{ ISFUNC, rl_insert }, /* Copyright sign */
{ ISFUNC, rl_insert }, /* Feminine ordinal indicator */
{ ISFUNC, rl_insert }, /* Left pointing double angle quotation mark */
{ ISFUNC, rl_insert }, /* Not sign */
{ ISFUNC, rl_insert }, /* Soft hyphen */
{ ISFUNC, rl_insert }, /* Registered sign */
{ ISFUNC, rl_insert }, /* Macron */
{ ISFUNC, rl_insert }, /* Degree sign */
{ ISFUNC, rl_insert }, /* Plus-minus sign */
{ ISFUNC, rl_insert }, /* Superscript two */
{ ISFUNC, rl_insert }, /* Superscript three */
{ ISFUNC, rl_insert }, /* Acute accent */
{ ISFUNC, rl_insert }, /* Micro sign */
{ ISFUNC, rl_insert }, /* Pilcrow sign */
{ ISFUNC, rl_insert }, /* Middle dot */
{ ISFUNC, rl_insert }, /* Cedilla */
{ ISFUNC, rl_insert }, /* Superscript one */
{ ISFUNC, rl_insert }, /* Masculine ordinal indicator */
{ ISFUNC, rl_insert }, /* Right pointing double angle quotation mark */
{ ISFUNC, rl_insert }, /* Vulgar fraction one quarter */
{ ISFUNC, rl_insert }, /* Vulgar fraction one half */
{ ISFUNC, rl_insert }, /* Vulgar fraction three quarters */
{ ISFUNC, rl_insert }, /* Inverted questionk mark */
{ ISFUNC, rl_insert }, /* Latin capital letter a with grave */
{ ISFUNC, rl_insert }, /* Latin capital letter a with acute */
{ ISFUNC, rl_insert }, /* Latin capital letter a with circumflex */
{ ISFUNC, rl_insert }, /* Latin capital letter a with tilde */
{ ISFUNC, rl_insert }, /* Latin capital letter a with diaeresis */
{ ISFUNC, rl_insert }, /* Latin capital letter a with ring above */
{ ISFUNC, rl_insert }, /* Latin capital letter ae */
{ ISFUNC, rl_insert }, /* Latin capital letter c with cedilla */
{ ISFUNC, rl_insert }, /* Latin capital letter e with grave */
{ ISFUNC, rl_insert }, /* Latin capital letter e with acute */
{ ISFUNC, rl_insert }, /* Latin capital letter e with circumflex */
{ ISFUNC, rl_insert }, /* Latin capital letter e with diaeresis */
{ ISFUNC, rl_insert }, /* Latin capital letter i with grave */
{ ISFUNC, rl_insert }, /* Latin capital letter i with acute */
{ ISFUNC, rl_insert }, /* Latin capital letter i with circumflex */
{ ISFUNC, rl_insert }, /* Latin capital letter i with diaeresis */
{ ISFUNC, rl_insert }, /* Latin capital letter eth (Icelandic) */
{ ISFUNC, rl_insert }, /* Latin capital letter n with tilde */
{ ISFUNC, rl_insert }, /* Latin capital letter o with grave */
{ ISFUNC, rl_insert }, /* Latin capital letter o with acute */
{ ISFUNC, rl_insert }, /* Latin capital letter o with circumflex */
{ ISFUNC, rl_insert }, /* Latin capital letter o with tilde */
{ ISFUNC, rl_insert }, /* Latin capital letter o with diaeresis */
{ ISFUNC, rl_insert }, /* Multiplication sign */
{ ISFUNC, rl_insert }, /* Latin capital letter o with stroke */
{ ISFUNC, rl_insert }, /* Latin capital letter u with grave */
{ ISFUNC, rl_insert }, /* Latin capital letter u with acute */
{ ISFUNC, rl_insert }, /* Latin capital letter u with circumflex */
{ ISFUNC, rl_insert }, /* Latin capital letter u with diaeresis */
{ ISFUNC, rl_insert }, /* Latin capital letter Y with acute */
{ ISFUNC, rl_insert }, /* Latin capital letter thorn (Icelandic) */
{ ISFUNC, rl_insert }, /* Latin small letter sharp s (German) */
{ ISFUNC, rl_insert }, /* Latin small letter a with grave */
{ ISFUNC, rl_insert }, /* Latin small letter a with acute */
{ ISFUNC, rl_insert }, /* Latin small letter a with circumflex */
{ ISFUNC, rl_insert }, /* Latin small letter a with tilde */
{ ISFUNC, rl_insert }, /* Latin small letter a with diaeresis */
{ ISFUNC, rl_insert }, /* Latin small letter a with ring above */
{ ISFUNC, rl_insert }, /* Latin small letter ae */
{ ISFUNC, rl_insert }, /* Latin small letter c with cedilla */
{ ISFUNC, rl_insert }, /* Latin small letter e with grave */
{ ISFUNC, rl_insert }, /* Latin small letter e with acute */
{ ISFUNC, rl_insert }, /* Latin small letter e with circumflex */
{ ISFUNC, rl_insert }, /* Latin small letter e with diaeresis */
{ ISFUNC, rl_insert }, /* Latin small letter i with grave */
{ ISFUNC, rl_insert }, /* Latin small letter i with acute */
{ ISFUNC, rl_insert }, /* Latin small letter i with circumflex */
{ ISFUNC, rl_insert }, /* Latin small letter i with diaeresis */
{ ISFUNC, rl_insert }, /* Latin small letter eth (Icelandic) */
{ ISFUNC, rl_insert }, /* Latin small letter n with tilde */
{ ISFUNC, rl_insert }, /* Latin small letter o with grave */
{ ISFUNC, rl_insert }, /* Latin small letter o with acute */
{ ISFUNC, rl_insert }, /* Latin small letter o with circumflex */
{ ISFUNC, rl_insert }, /* Latin small letter o with tilde */
{ ISFUNC, rl_insert }, /* Latin small letter o with diaeresis */
{ ISFUNC, rl_insert }, /* Division sign */
{ ISFUNC, rl_insert }, /* Latin small letter o with stroke */
{ ISFUNC, rl_insert }, /* Latin small letter u with grave */
{ ISFUNC, rl_insert }, /* Latin small letter u with acute */
{ ISFUNC, rl_insert }, /* Latin small letter u with circumflex */
{ ISFUNC, rl_insert }, /* Latin small letter u with diaeresis */
{ ISFUNC, rl_insert }, /* Latin small letter y with acute */
{ ISFUNC, rl_insert }, /* Latin small letter thorn (Icelandic) */
{ ISFUNC, rl_insert } /* Latin small letter y with diaeresis */
#endif /* KEYMAP_SIZE > 128 */
};
KEYMAP_ENTRY_ARRAY emacs_meta_keymap = {
/* Meta keys. Just like above, but the high bit is set. */
{ ISFUNC, (Function *)0x0 }, /* Meta-Control-@ */
{ ISFUNC, (Function *)0x0 }, /* Meta-Control-a */
{ ISFUNC, (Function *)0x0 }, /* Meta-Control-b */
{ ISFUNC, (Function *)0x0 }, /* Meta-Control-c */
{ ISFUNC, (Function *)0x0 }, /* Meta-Control-d */
{ ISFUNC, (Function *)0x0 }, /* Meta-Control-e */
{ ISFUNC, (Function *)0x0 }, /* Meta-Control-f */
{ ISFUNC, rl_abort }, /* Meta-Control-g */
{ ISFUNC, rl_backward_kill_word }, /* Meta-Control-h */
{ ISFUNC, rl_tab_insert }, /* Meta-Control-i */
{ ISFUNC, rl_vi_editing_mode }, /* Meta-Control-j */
{ ISFUNC, (Function *)0x0 }, /* Meta-Control-k */
{ ISFUNC, (Function *)0x0 }, /* Meta-Control-l */
{ ISFUNC, rl_vi_editing_mode }, /* Meta-Control-m */
{ ISFUNC, (Function *)0x0 }, /* Meta-Control-n */
{ ISFUNC, (Function *)0x0 }, /* Meta-Control-o */
{ ISFUNC, (Function *)0x0 }, /* Meta-Control-p */
{ ISFUNC, (Function *)0x0 }, /* Meta-Control-q */
{ ISFUNC, rl_revert_line }, /* Meta-Control-r */
{ ISFUNC, (Function *)0x0 }, /* Meta-Control-s */
{ ISFUNC, (Function *)0x0 }, /* Meta-Control-t */
{ ISFUNC, (Function *)0x0 }, /* Meta-Control-u */
{ ISFUNC, (Function *)0x0 }, /* Meta-Control-v */
{ ISFUNC, (Function *)0x0 }, /* Meta-Control-w */
{ ISFUNC, (Function *)0x0 }, /* Meta-Control-x */
{ ISFUNC, rl_yank_nth_arg }, /* Meta-Control-y */
{ ISFUNC, (Function *)0x0 }, /* Meta-Control-z */
{ ISFUNC, rl_complete }, /* Meta-Control-[ */
{ ISFUNC, (Function *)0x0 }, /* Meta-Control-\ */
{ ISFUNC, (Function *)0x0 }, /* Meta-Control-] */
{ ISFUNC, (Function *)0x0 }, /* Meta-Control-^ */
{ ISFUNC, (Function *)0x0 }, /* Meta-Control-_ */
/* The start of printing characters. */
{ ISFUNC, (Function *)0x0 }, /* Meta-SPACE */
{ ISFUNC, (Function *)0x0 }, /* Meta-! */
{ ISFUNC, (Function *)0x0 }, /* Meta-" */
{ ISFUNC, (Function *)0x0 }, /* Meta-# */
{ ISFUNC, (Function *)0x0 }, /* Meta-$ */
{ ISFUNC, (Function *)0x0 }, /* Meta-% */
{ ISFUNC, rl_tilde_expand }, /* Meta-& */
{ ISFUNC, (Function *)0x0 }, /* Meta-' */
{ ISFUNC, (Function *)0x0 }, /* Meta-( */
{ ISFUNC, (Function *)0x0 }, /* Meta-) */
{ ISFUNC, (Function *)0x0 }, /* Meta-* */
{ ISFUNC, (Function *)0x0 }, /* Meta-+ */
{ ISFUNC, (Function *)0x0 }, /* Meta-, */
{ ISFUNC, rl_digit_argument }, /* Meta-- */
{ ISFUNC, rl_yank_last_arg}, /* Meta-. */
{ ISFUNC, (Function *)0x0 }, /* Meta-/ */
/* Regular digits. */
{ ISFUNC, rl_digit_argument }, /* Meta-0 */
{ ISFUNC, rl_digit_argument }, /* Meta-1 */
{ ISFUNC, rl_digit_argument }, /* Meta-2 */
{ ISFUNC, rl_digit_argument }, /* Meta-3 */
{ ISFUNC, rl_digit_argument }, /* Meta-4 */
{ ISFUNC, rl_digit_argument }, /* Meta-5 */
{ ISFUNC, rl_digit_argument }, /* Meta-6 */
{ ISFUNC, rl_digit_argument }, /* Meta-7 */
{ ISFUNC, rl_digit_argument }, /* Meta-8 */
{ ISFUNC, rl_digit_argument }, /* Meta-9 */
/* A little more punctuation. */
{ ISFUNC, (Function *)0x0 }, /* Meta-: */
{ ISFUNC, (Function *)0x0 }, /* Meta-; */
{ ISFUNC, rl_beginning_of_history }, /* Meta-< */
{ ISFUNC, (Function *)0x0 }, /* Meta-= */
{ ISFUNC, rl_end_of_history }, /* Meta-> */
{ ISFUNC, rl_possible_completions }, /* Meta-? */
{ ISFUNC, (Function *)0x0 }, /* Meta-@ */
/* Uppercase alphabet. */
{ ISFUNC, rl_do_lowercase_version }, /* Meta-A */
{ ISFUNC, rl_do_lowercase_version }, /* Meta-B */
{ ISFUNC, rl_do_lowercase_version }, /* Meta-C */
{ ISFUNC, rl_do_lowercase_version }, /* Meta-D */
{ ISFUNC, rl_do_lowercase_version }, /* Meta-E */
{ ISFUNC, rl_do_lowercase_version }, /* Meta-F */
{ ISFUNC, rl_do_lowercase_version }, /* Meta-G */
{ ISFUNC, rl_do_lowercase_version }, /* Meta-H */
{ ISFUNC, rl_do_lowercase_version }, /* Meta-I */
{ ISFUNC, rl_do_lowercase_version }, /* Meta-J */
{ ISFUNC, rl_do_lowercase_version }, /* Meta-K */
{ ISFUNC, rl_do_lowercase_version }, /* Meta-L */
{ ISFUNC, rl_do_lowercase_version }, /* Meta-M */
{ ISFUNC, rl_do_lowercase_version }, /* Meta-N */
{ ISFUNC, rl_do_lowercase_version }, /* Meta-O */
{ ISFUNC, rl_do_lowercase_version }, /* Meta-P */
{ ISFUNC, rl_do_lowercase_version }, /* Meta-Q */
{ ISFUNC, rl_do_lowercase_version }, /* Meta-R */
{ ISFUNC, rl_do_lowercase_version }, /* Meta-S */
{ ISFUNC, rl_do_lowercase_version }, /* Meta-T */
{ ISFUNC, rl_do_lowercase_version }, /* Meta-U */
{ ISFUNC, rl_do_lowercase_version }, /* Meta-V */
{ ISFUNC, rl_do_lowercase_version }, /* Meta-W */
{ ISFUNC, rl_do_lowercase_version }, /* Meta-X */
{ ISFUNC, rl_do_lowercase_version }, /* Meta-Y */
{ ISFUNC, rl_do_lowercase_version }, /* Meta-Z */
/* Some more punctuation. */
{ ISFUNC, (Function *)0x0 }, /* Meta-[ */ /* was rl_arrow_keys */
{ ISFUNC, rl_delete_horizontal_space }, /* Meta-\ */
{ ISFUNC, (Function *)0x0 }, /* Meta-] */
{ ISFUNC, (Function *)0x0 }, /* Meta-^ */
{ ISFUNC, rl_yank_last_arg }, /* Meta-_ */
{ ISFUNC, (Function *)0x0 }, /* Meta-` */
/* Lowercase alphabet. */
{ ISFUNC, (Function *)0x0 }, /* Meta-a */
{ ISFUNC, rl_backward_word }, /* Meta-b */
{ ISFUNC, rl_capitalize_word }, /* Meta-c */
{ ISFUNC, rl_kill_word }, /* Meta-d */
{ ISFUNC, (Function *)0x0 }, /* Meta-e */
{ ISFUNC, rl_forward_word }, /* Meta-f */
{ ISFUNC, (Function *)0x0 }, /* Meta-g */
{ ISFUNC, (Function *)0x0 }, /* Meta-h */
{ ISFUNC, (Function *)0x0 }, /* Meta-i */
{ ISFUNC, (Function *)0x0 }, /* Meta-j */
{ ISFUNC, (Function *)0x0 }, /* Meta-k */
{ ISFUNC, rl_downcase_word }, /* Meta-l */
{ ISFUNC, (Function *)0x0 }, /* Meta-m */
{ ISFUNC, rl_noninc_forward_search }, /* Meta-n */
{ ISFUNC, (Function *)0x0 }, /* Meta-o */ /* was rl_arrow_keys */
{ ISFUNC, rl_noninc_reverse_search }, /* Meta-p */
{ ISFUNC, (Function *)0x0 }, /* Meta-q */
{ ISFUNC, rl_revert_line }, /* Meta-r */
{ ISFUNC, (Function *)0x0 }, /* Meta-s */
{ ISFUNC, rl_transpose_words }, /* Meta-t */
{ ISFUNC, rl_upcase_word }, /* Meta-u */
{ ISFUNC, (Function *)0x0 }, /* Meta-v */
{ ISFUNC, (Function *)0x0 }, /* Meta-w */
{ ISFUNC, (Function *)0x0 }, /* Meta-x */
{ ISFUNC, rl_yank_pop }, /* Meta-y */
{ ISFUNC, (Function *)0x0 }, /* Meta-z */
/* Final punctuation. */
{ ISFUNC, (Function *)0x0 }, /* Meta-{ */
{ ISFUNC, (Function *)0x0 }, /* Meta-| */
{ ISFUNC, (Function *)0x0 }, /* Meta-} */
{ ISFUNC, rl_tilde_expand }, /* Meta-~ */
{ ISFUNC, rl_backward_kill_word }, /* Meta-rubout */
#if KEYMAP_SIZE > 128
/* Undefined keys. */
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 }
#endif /* KEYMAP_SIZE > 128 */
};
KEYMAP_ENTRY_ARRAY emacs_ctlx_keymap = {
/* Control keys. */
{ ISFUNC, (Function *)0x0 }, /* Control-@ */
{ ISFUNC, (Function *)0x0 }, /* Control-a */
{ ISFUNC, (Function *)0x0 }, /* Control-b */
{ ISFUNC, (Function *)0x0 }, /* Control-c */
{ ISFUNC, (Function *)0x0 }, /* Control-d */
{ ISFUNC, (Function *)0x0 }, /* Control-e */
{ ISFUNC, (Function *)0x0 }, /* Control-f */
{ ISFUNC, rl_abort }, /* Control-g */
{ ISFUNC, (Function *)0x0 }, /* Control-h */
{ ISFUNC, (Function *)0x0 }, /* Control-i */
{ ISFUNC, (Function *)0x0 }, /* Control-j */
{ ISFUNC, (Function *)0x0 }, /* Control-k */
{ ISFUNC, (Function *)0x0 }, /* Control-l */
{ ISFUNC, (Function *)0x0 }, /* Control-m */
{ ISFUNC, (Function *)0x0 }, /* Control-n */
{ ISFUNC, (Function *)0x0 }, /* Control-o */
{ ISFUNC, (Function *)0x0 }, /* Control-p */
{ ISFUNC, (Function *)0x0 }, /* Control-q */
{ ISFUNC, rl_re_read_init_file }, /* Control-r */
{ ISFUNC, (Function *)0x0 }, /* Control-s */
{ ISFUNC, (Function *)0x0 }, /* Control-t */
{ ISFUNC, rl_undo_command }, /* Control-u */
{ ISFUNC, (Function *)0x0 }, /* Control-v */
{ ISFUNC, (Function *)0x0 }, /* Control-w */
{ ISFUNC, (Function *)0x0 }, /* Control-x */
{ ISFUNC, (Function *)0x0 }, /* Control-y */
{ ISFUNC, (Function *)0x0 }, /* Control-z */
{ ISFUNC, (Function *)0x0 }, /* Control-[ */
{ ISFUNC, (Function *)0x0 }, /* Control-\ */
{ ISFUNC, (Function *)0x0 }, /* Control-] */
{ ISFUNC, (Function *)0x0 }, /* Control-^ */
{ ISFUNC, (Function *)0x0 }, /* Control-_ */
/* The start of printing characters. */
{ ISFUNC, (Function *)0x0 }, /* SPACE */
{ ISFUNC, (Function *)0x0 }, /* ! */
{ ISFUNC, (Function *)0x0 }, /* " */
{ ISFUNC, (Function *)0x0 }, /* # */
{ ISFUNC, (Function *)0x0 }, /* $ */
{ ISFUNC, (Function *)0x0 }, /* % */
{ ISFUNC, (Function *)0x0 }, /* & */
{ ISFUNC, (Function *)0x0 }, /* ' */
{ ISFUNC, rl_start_kbd_macro }, /* ( */
{ ISFUNC, rl_end_kbd_macro }, /* ) */
{ ISFUNC, (Function *)0x0 }, /* * */
{ ISFUNC, (Function *)0x0 }, /* + */
{ ISFUNC, (Function *)0x0 }, /* , */
{ ISFUNC, (Function *)0x0 }, /* - */
{ ISFUNC, (Function *)0x0 }, /* . */
{ ISFUNC, (Function *)0x0 }, /* / */
/* Regular digits. */
{ ISFUNC, (Function *)0x0 }, /* 0 */
{ ISFUNC, (Function *)0x0 }, /* 1 */
{ ISFUNC, (Function *)0x0 }, /* 2 */
{ ISFUNC, (Function *)0x0 }, /* 3 */
{ ISFUNC, (Function *)0x0 }, /* 4 */
{ ISFUNC, (Function *)0x0 }, /* 5 */
{ ISFUNC, (Function *)0x0 }, /* 6 */
{ ISFUNC, (Function *)0x0 }, /* 7 */
{ ISFUNC, (Function *)0x0 }, /* 8 */
{ ISFUNC, (Function *)0x0 }, /* 9 */
/* A little more punctuation. */
{ ISFUNC, (Function *)0x0 }, /* : */
{ ISFUNC, (Function *)0x0 }, /* ; */
{ ISFUNC, (Function *)0x0 }, /* < */
{ ISFUNC, (Function *)0x0 }, /* = */
{ ISFUNC, (Function *)0x0 }, /* > */
{ ISFUNC, (Function *)0x0 }, /* ? */
{ ISFUNC, (Function *)0x0 }, /* @ */
/* Uppercase alphabet. */
{ ISFUNC, rl_do_lowercase_version }, /* A */
{ ISFUNC, rl_do_lowercase_version }, /* B */
{ ISFUNC, rl_do_lowercase_version }, /* C */
{ ISFUNC, rl_do_lowercase_version }, /* D */
{ ISFUNC, rl_do_lowercase_version }, /* E */
{ ISFUNC, rl_do_lowercase_version }, /* F */
{ ISFUNC, rl_do_lowercase_version }, /* G */
{ ISFUNC, rl_do_lowercase_version }, /* H */
{ ISFUNC, rl_do_lowercase_version }, /* I */
{ ISFUNC, rl_do_lowercase_version }, /* J */
{ ISFUNC, rl_do_lowercase_version }, /* K */
{ ISFUNC, rl_do_lowercase_version }, /* L */
{ ISFUNC, rl_do_lowercase_version }, /* M */
{ ISFUNC, rl_do_lowercase_version }, /* N */
{ ISFUNC, rl_do_lowercase_version }, /* O */
{ ISFUNC, rl_do_lowercase_version }, /* P */
{ ISFUNC, rl_do_lowercase_version }, /* Q */
{ ISFUNC, rl_do_lowercase_version }, /* R */
{ ISFUNC, rl_do_lowercase_version }, /* S */
{ ISFUNC, rl_do_lowercase_version }, /* T */
{ ISFUNC, rl_do_lowercase_version }, /* U */
{ ISFUNC, rl_do_lowercase_version }, /* V */
{ ISFUNC, rl_do_lowercase_version }, /* W */
{ ISFUNC, rl_do_lowercase_version }, /* X */
{ ISFUNC, rl_do_lowercase_version }, /* Y */
{ ISFUNC, rl_do_lowercase_version }, /* Z */
/* Some more punctuation. */
{ ISFUNC, (Function *)0x0 }, /* [ */
{ ISFUNC, (Function *)0x0 }, /* \ */
{ ISFUNC, (Function *)0x0 }, /* ] */
{ ISFUNC, (Function *)0x0 }, /* ^ */
{ ISFUNC, (Function *)0x0 }, /* _ */
{ ISFUNC, (Function *)0x0 }, /* ` */
/* Lowercase alphabet. */
{ ISFUNC, (Function *)0x0 }, /* a */
{ ISFUNC, (Function *)0x0 }, /* b */
{ ISFUNC, (Function *)0x0 }, /* c */
{ ISFUNC, (Function *)0x0 }, /* d */
{ ISFUNC, rl_call_last_kbd_macro }, /* e */
{ ISFUNC, (Function *)0x0 }, /* f */
{ ISFUNC, (Function *)0x0 }, /* g */
{ ISFUNC, (Function *)0x0 }, /* h */
{ ISFUNC, (Function *)0x0 }, /* i */
{ ISFUNC, (Function *)0x0 }, /* j */
{ ISFUNC, (Function *)0x0 }, /* k */
{ ISFUNC, (Function *)0x0 }, /* l */
{ ISFUNC, (Function *)0x0 }, /* m */
{ ISFUNC, (Function *)0x0 }, /* n */
{ ISFUNC, (Function *)0x0 }, /* o */
{ ISFUNC, (Function *)0x0 }, /* p */
{ ISFUNC, (Function *)0x0 }, /* q */
{ ISFUNC, (Function *)0x0 }, /* r */
{ ISFUNC, (Function *)0x0 }, /* s */
{ ISFUNC, (Function *)0x0 }, /* t */
{ ISFUNC, (Function *)0x0 }, /* u */
{ ISFUNC, (Function *)0x0 }, /* v */
{ ISFUNC, (Function *)0x0 }, /* w */
{ ISFUNC, (Function *)0x0 }, /* x */
{ ISFUNC, (Function *)0x0 }, /* y */
{ ISFUNC, (Function *)0x0 }, /* z */
/* Final punctuation. */
{ ISFUNC, (Function *)0x0 }, /* { */
{ ISFUNC, (Function *)0x0 }, /* | */
{ ISFUNC, (Function *)0x0 }, /* } */
{ ISFUNC, (Function *)0x0 }, /* ~ */
{ ISFUNC, rl_backward_kill_line }, /* RUBOUT */
#if KEYMAP_SIZE > 128
/* Undefined keys. */
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 }
#endif /* KEYMAP_SIZE > 128 */
};

View file

@ -0,0 +1,65 @@
# My ~/.inputrc file is in -*- text -*- for easy editing with Emacs.
#
# Notice the various bindings which are conditionalized depending
# on which program is running, or what terminal is active.
#
# In all programs, all terminals, make sure this is bound.
"\C-x\C-r": re-read-init-file
# Hp terminals (and some others) have ugly default behaviour for C-h.
"\C-h": backward-delete-char
"\e\C-h": backward-kill-word
"\C-xd": dump-functions
# In xterm windows, make the arrow keys do the right thing.
$if TERM=xterm
"\e[A": previous-history
"\e[B": next-history
"\e[C": forward-char
"\e[D": backward-char
# alternate arrow key prefix
"\eOA": previous-history
"\eOB": next-history
"\eOC": forward-char
"\eOD": backward-char
# Under Xterm in Bash, we bind local Function keys to do something useful.
$if Bash
"\e[11~": "Function Key 1"
"\e[12~": "Function Key 2"
"\e[13~": "Function Key 3"
"\e[14~": "Function Key 4"
"\e[15~": "Function Key 5"
# I know the following escape sequence numbers are 1 greater than
# the function key. Don't ask me why, I didn't design the xterm terminal.
"\e[17~": "Function Key 6"
"\e[18~": "Function Key 7"
"\e[19~": "Function Key 8"
"\e[20~": "Function Key 9"
"\e[21~": "Function Key 10"
$endif
$endif
# For Bash, all terminals, add some Bash specific hacks.
$if Bash
"\C-xv": show-bash-version
"\C-x\C-e": shell-expand-line
# Here is one for editing my path.
"\C-xp": "$PATH\C-x\C-e\C-e\"\C-aPATH=\":\C-b"
# Make C-x r read my mail in emacs.
# "\C-xr": "emacs -f rmail\C-j"
$endif
# For FTP, different hacks:
$if Ftp
"\C-xg": "get \M-?"
"\C-xt": "put \M-?"
"\M-.": yank-last-arg
$endif
" ": self-insert

View file

@ -0,0 +1,12 @@
# This is the Makefile for the examples subdirectory of readline. -*- text -*-
#
EXECUTABLES = fileman
CFLAGS = -g -I../..
LDFLAGS = -g -L..
fileman: fileman.o
$(CC) $(LDFLAGS) -o fileman fileman.o -lreadline -ltermcap
fileman.o: fileman.c

View file

@ -0,0 +1,425 @@
/* fileman.c -- A tiny application which demonstrates how to use the
GNU Readline library. This application interactively allows users
to manipulate files and their modes. */
#include <stdio.h>
#include <sys/types.h>
#include <sys/file.h>
#include <sys/stat.h>
#include <sys/errno.h>
#include <readline/readline.h>
#include <readline/history.h>
extern char *getwd ();
extern char *xmalloc ();
/* The names of functions that actually do the manipulation. */
int com_list (), com_view (), com_rename (), com_stat (), com_pwd ();
int com_delete (), com_help (), com_cd (), com_quit ();
/* A structure which contains information on the commands this program
can understand. */
typedef struct {
char *name; /* User printable name of the function. */
Function *func; /* Function to call to do the job. */
char *doc; /* Documentation for this function. */
} COMMAND;
COMMAND commands[] = {
{ "cd", com_cd, "Change to directory DIR" },
{ "delete", com_delete, "Delete FILE" },
{ "help", com_help, "Display this text" },
{ "?", com_help, "Synonym for `help'" },
{ "list", com_list, "List files in DIR" },
{ "ls", com_list, "Synonym for `list'" },
{ "pwd", com_pwd, "Print the current working directory" },
{ "quit", com_quit, "Quit using Fileman" },
{ "rename", com_rename, "Rename FILE to NEWNAME" },
{ "stat", com_stat, "Print out statistics on FILE" },
{ "view", com_view, "View the contents of FILE" },
{ (char *)NULL, (Function *)NULL, (char *)NULL }
};
/* Forward declarations. */
char *stripwhite ();
COMMAND *find_command ();
/* The name of this program, as taken from argv[0]. */
char *progname;
/* When non-zero, this global means the user is done using this program. */
int done;
char *
dupstr (s)
int s;
{
char *r;
r = xmalloc (strlen (s) + 1);
strcpy (r, s);
return (r);
}
main (argc, argv)
int argc;
char **argv;
{
char *line, *s;
progname = argv[0];
initialize_readline (); /* Bind our completer. */
/* Loop reading and executing lines until the user quits. */
for ( ; done == 0; )
{
line = readline ("FileMan: ");
if (!line)
break;
/* Remove leading and trailing whitespace from the line.
Then, if there is anything left, add it to the history list
and execute it. */
s = stripwhite (line);
if (*s)
{
add_history (s);
execute_line (s);
}
free (line);
}
exit (0);
}
/* Execute a command line. */
int
execute_line (line)
char *line;
{
register int i;
COMMAND *command;
char *word;
/* Isolate the command word. */
i = 0;
while (line[i] && whitespace (line[i]))
i++;
word = line + i;
while (line[i] && !whitespace (line[i]))
i++;
if (line[i])
line[i++] = '\0';
command = find_command (word);
if (!command)
{
fprintf (stderr, "%s: No such command for FileMan.\n", word);
return (-1);
}
/* Get argument to command, if any. */
while (whitespace (line[i]))
i++;
word = line + i;
/* Call the function. */
return ((*(command->func)) (word));
}
/* Look up NAME as the name of a command, and return a pointer to that
command. Return a NULL pointer if NAME isn't a command name. */
COMMAND *
find_command (name)
char *name;
{
register int i;
for (i = 0; commands[i].name; i++)
if (strcmp (name, commands[i].name) == 0)
return (&commands[i]);
return ((COMMAND *)NULL);
}
/* Strip whitespace from the start and end of STRING. Return a pointer
into STRING. */
char *
stripwhite (string)
char *string;
{
register char *s, *t;
for (s = string; whitespace (*s); s++)
;
if (*s == 0)
return (s);
t = s + strlen (s) - 1;
while (t > s && whitespace (*t))
t--;
*++t = '\0';
return s;
}
/* **************************************************************** */
/* */
/* Interface to Readline Completion */
/* */
/* **************************************************************** */
char *command_generator ();
char **fileman_completion ();
/* Tell the GNU Readline library how to complete. We want to try to complete
on command names if this is the first word in the line, or on filenames
if not. */
initialize_readline ()
{
/* Allow conditional parsing of the ~/.inputrc file. */
rl_readline_name = "FileMan";
/* Tell the completer that we want a crack first. */
rl_attempted_completion_function = (CPPFunction *)fileman_completion;
}
/* Attempt to complete on the contents of TEXT. START and END show the
region of TEXT that contains the word to complete. We can use the
entire line in case we want to do some simple parsing. Return the
array of matches, or NULL if there aren't any. */
char **
fileman_completion (text, start, end)
char *text;
int start, end;
{
char **matches;
matches = (char **)NULL;
/* If this word is at the start of the line, then it is a command
to complete. Otherwise it is the name of a file in the current
directory. */
if (start == 0)
matches = completion_matches (text, command_generator);
return (matches);
}
/* Generator function for command completion. STATE lets us know whether
to start from scratch; without any state (i.e. STATE == 0), then we
start at the top of the list. */
char *
command_generator (text, state)
char *text;
int state;
{
static int list_index, len;
char *name;
/* If this is a new word to complete, initialize now. This includes
saving the length of TEXT for efficiency, and initializing the index
variable to 0. */
if (!state)
{
list_index = 0;
len = strlen (text);
}
/* Return the next name which partially matches from the command list. */
while (name = commands[list_index].name)
{
list_index++;
if (strncmp (name, text, len) == 0)
return (dupstr(name));
}
/* If no names matched, then return NULL. */
return ((char *)NULL);
}
/* **************************************************************** */
/* */
/* FileMan Commands */
/* */
/* **************************************************************** */
/* String to pass to system (). This is for the LIST, VIEW and RENAME
commands. */
static char syscom[1024];
/* List the file(s) named in arg. */
com_list (arg)
char *arg;
{
if (!arg)
arg = "";
sprintf (syscom, "ls -FClg %s", arg);
return (system (syscom));
}
com_view (arg)
char *arg;
{
if (!valid_argument ("view", arg))
return 1;
sprintf (syscom, "more %s", arg);
return (system (syscom));
}
com_rename (arg)
char *arg;
{
too_dangerous ("rename");
return (1);
}
com_stat (arg)
char *arg;
{
struct stat finfo;
if (!valid_argument ("stat", arg))
return (1);
if (stat (arg, &finfo) == -1)
{
perror (arg);
return (1);
}
printf ("Statistics for `%s':\n", arg);
printf ("%s has %d link%s, and is %d byte%s in length.\n", arg,
finfo.st_nlink,
(finfo.st_nlink == 1) ? "" : "s",
finfo.st_size,
(finfo.st_size == 1) ? "" : "s");
printf ("Inode Last Change at: %s", ctime (&finfo.st_ctime));
printf (" Last access at: %s", ctime (&finfo.st_atime));
printf (" Last modified at: %s", ctime (&finfo.st_mtime));
return (0);
}
com_delete (arg)
char *arg;
{
too_dangerous ("delete");
return (1);
}
/* Print out help for ARG, or for all of the commands if ARG is
not present. */
com_help (arg)
char *arg;
{
register int i;
int printed = 0;
for (i = 0; commands[i].name; i++)
{
if (!*arg || (strcmp (arg, commands[i].name) == 0))
{
printf ("%s\t\t%s.\n", commands[i].name, commands[i].doc);
printed++;
}
}
if (!printed)
{
printf ("No commands match `%s'. Possibilties are:\n", arg);
for (i = 0; commands[i].name; i++)
{
/* Print in six columns. */
if (printed == 6)
{
printed = 0;
printf ("\n");
}
printf ("%s\t", commands[i].name);
printed++;
}
if (printed)
printf ("\n");
}
return (0);
}
/* Change to the directory ARG. */
com_cd (arg)
char *arg;
{
if (chdir (arg) == -1)
{
perror (arg);
return 1;
}
com_pwd ("");
return (0);
}
/* Print out the current working directory. */
com_pwd (ignore)
char *ignore;
{
char dir[1024], *s;
s = getwd (dir);
if (s == 0)
{
printf ("Error getting pwd: %s\n", dir);
return 1;
}
printf ("Current directory is %s\n", dir);
return 0;
}
/* The user wishes to quit using this program. Just set DONE non-zero. */
com_quit (arg)
char *arg;
{
done = 1;
return (0);
}
/* Function which tells you that you can't do this. */
too_dangerous (caller)
char *caller;
{
fprintf (stderr,
"%s: Too dangerous for me to distribute. Write it yourself.\n",
caller);
}
/* Return non-zero if ARG is a valid argument for CALLER, else print
an error message and return zero. */
int
valid_argument (caller, arg)
char *caller, *arg;
{
if (!arg || !*arg)
{
fprintf (stderr, "%s: Argument required.\n", caller);
return (0);
}
return (1);
}

View file

@ -0,0 +1,82 @@
main ()
{
char line[1024], *t;
int len, done = 0;
line[0] = 0;
using_history ();
while (!done)
{
printf ("history$ ");
fflush (stdout);
t = fgets (line, sizeof (line) - 1, stdin);
if (t && *t)
{
len = strlen (t);
if (t[len - 1] == '\n')
t[len - 1] = '\0';
}
if (!t)
strcpy (line, "quit");
if (line[0])
{
char *expansion;
int result;
using_history ();
result = history_expand (line, &expansion);
if (result)
fprintf (stderr, "%s\n", expansion);
if (result < 0 || result == 2)
{
free (expansion);
continue;
}
add_history (expansion);
strncpy (line, expansion, sizeof (line) - 1);
free (expansion);
}
if (strcmp (line, "quit") == 0)
done = 1;
else if (strcmp (line, "save") == 0)
write_history ("history_file");
else if (strcmp (line, "read") == 0)
read_history ("history_file");
else if (strcmp (line, "list") == 0)
{
register HIST_ENTRY **the_list;
register int i;
the_list = history_list ();
if (the_list)
for (i = 0; the_list[i]; i++)
printf ("%d: %s\n", i + history_base, the_list[i]->line);
}
else if (strncmp (line, "delete", 6) == 0)
{
int which;
if ((sscanf (line + 6, "%d", &which)) == 1)
{
HIST_ENTRY *entry = remove_history (which);
if (!entry)
fprintf (stderr, "No such entry %d\n", which);
else
{
free (entry->line);
free (entry);
}
}
else
{
fprintf (stderr, "non-numeric arg given to `delete'\n");
}
}
}
}

View file

@ -0,0 +1,94 @@
/* manexamp.c -- The examples which appear in the documentation are here. */
#include <stdio.h>
#include <readline/readline.h>
/* **************************************************************** */
/* */
* How to Emulate gets () */
/* */
/* **************************************************************** */
/* A static variable for holding the line. */
static char *line_read = (char *)NULL;
/* Read a string, and return a pointer to it. Returns NULL on EOF. */
char *
rl_gets ()
{
/* If the buffer has already been allocated, return the memory
to the free pool. */
if (line_read)
{
free (line_read);
line_read = (char *)NULL;
}
/* Get a line from the user. */
line_read = readline ("");
/* If the line has any text in it, save it on the history. */
if (line_read && *line_read)
add_history (line_read);
return (line_read);
}
/* **************************************************************** */
/* */
/* Writing a Function to be Called by Readline. */
/* */
/* **************************************************************** */
/* Invert the case of the COUNT following characters. */
invert_case_line (count, key)
int count, key;
{
register int start, end;
start = rl_point;
if (count < 0)
{
direction = -1;
count = -count;
}
else
direction = 1;
/* Find the end of the range to modify. */
end = start + (count * direction);
/* Force it to be within range. */
if (end > rl_end)
end = rl_end;
else if (end < 0)
end = -1;
if (start > end)
{
int temp = start;
start = end;
end = temp;
}
if (start == end)
return;
/* Tell readline that we are modifying the line, so save the undo
information. */
rl_modifying (start, end);
for (; start != end; start += direction)
{
if (uppercase_p (rl_line_buffer[start]))
rl_line_buffer[start] = to_lower (rl_line_buffer[start]);
else if (lowercase_p (rl_line_buffer[start]))
rl_line_buffer[start] = to_upper (rl_line_buffer[start]);
}
/* Move point to on top of the last character changed. */
rl_point = end - direction;
}

299
lib/readline/funmap.c Normal file
View file

@ -0,0 +1,299 @@
/* funmap.c -- attach names to functions. */
/* Copyright (C) 1987, 1989, 1992 Free Software Foundation, Inc.
This file is part of the GNU Readline Library, a library for
reading lines of text with interactive input and history editing.
The GNU Readline Library is free software; you can redistribute it
and/or modify it under the terms of the GNU General Public License
as published by the Free Software Foundation; either version 1, or
(at your option) any later version.
The GNU Readline Library is distributed in the hope that it will be
useful, but WITHOUT ANY WARRANTY; without even the implied warranty
of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
The GNU General Public License is often shipped with GNU software, and
is generally kept in a file called COPYING or LICENSE. If you do not
have a copy of the license, write to the Free Software Foundation,
675 Mass Ave, Cambridge, MA 02139, USA. */
#define READLINE_LIBRARY
#if defined (STATIC_MALLOC)
static char *xmalloc (), *xrealloc ();
#else
extern char *xmalloc (), *xrealloc ();
#endif /* STATIC_MALLOC */
#if !defined (BUFSIZ)
#include <stdio.h>
#endif /* BUFSIZ */
#if defined (HAVE_STDLIB_H)
# include <stdlib.h>
#else
# include "ansi_stdlib.h"
#endif /* HAVE_STDLIB_H */
#include "rlconf.h"
#include "readline.h"
static int qsort_string_compare ();
FUNMAP **funmap = (FUNMAP **)NULL;
static int funmap_size = 0;
static int funmap_entry = 0;
/* After initializing the function map, this is the index of the first
program specific function. */
int funmap_program_specific_entry_start;
static FUNMAP default_funmap[] = {
{ "abort", rl_abort },
{ "accept-line", rl_newline },
{ "arrow-key-prefix", rl_arrow_keys },
{ "backward-char", rl_backward },
{ "backward-delete-char", rl_rubout },
{ "backward-kill-line", rl_backward_kill_line },
{ "backward-kill-word", rl_backward_kill_word },
{ "backward-word", rl_backward_word },
{ "beginning-of-history", rl_beginning_of_history },
{ "beginning-of-line", rl_beg_of_line },
{ "call-last-kbd-macro", rl_call_last_kbd_macro },
{ "capitalize-word", rl_capitalize_word },
{ "clear-screen", rl_clear_screen },
{ "complete", rl_complete },
{ "delete-char", rl_delete },
{ "delete-horizontal-space", rl_delete_horizontal_space },
{ "digit-argument", rl_digit_argument },
{ "do-lowercase-version", rl_do_lowercase_version },
{ "downcase-word", rl_downcase_word },
{ "dump-functions", rl_dump_functions },
{ "emacs-editing-mode", rl_emacs_editing_mode },
{ "end-kbd-macro", rl_end_kbd_macro },
{ "end-of-history", rl_end_of_history },
{ "end-of-line", rl_end_of_line },
{ "forward-char", rl_forward },
{ "forward-search-history", rl_forward_search_history },
{ "forward-word", rl_forward_word },
{ "history-search-backward", rl_history_search_backward },
{ "history-search-forward", rl_history_search_forward },
{ "insert-completions", rl_insert_completions },
{ "kill-whole-line", rl_kill_full_line },
{ "kill-line", rl_kill_line },
{ "kill-word", rl_kill_word },
{ "next-history", rl_get_next_history },
{ "non-incremental-forward-search-history", rl_noninc_forward_search },
{ "non-incremental-reverse-search-history", rl_noninc_reverse_search },
{ "non-incremental-forward-search-history-again", rl_noninc_forward_search_again },
{ "non-incremental-reverse-search-history-again", rl_noninc_reverse_search_again },
{ "possible-completions", rl_possible_completions },
{ "previous-history", rl_get_previous_history },
{ "quoted-insert", rl_quoted_insert },
{ "re-read-init-file", rl_re_read_init_file },
{ "redraw-current-line", rl_refresh_line},
{ "reverse-search-history", rl_reverse_search_history },
{ "revert-line", rl_revert_line },
{ "self-insert", rl_insert },
{ "start-kbd-macro", rl_start_kbd_macro },
{ "tab-insert", rl_tab_insert },
{ "tilde-expand", rl_tilde_expand },
{ "transpose-chars", rl_transpose_chars },
{ "transpose-words", rl_transpose_words },
{ "tty-status", rl_tty_status },
{ "undo", rl_undo_command },
{ "universal-argument", rl_universal_argument },
{ "unix-line-discard", rl_unix_line_discard },
{ "unix-word-rubout", rl_unix_word_rubout },
{ "upcase-word", rl_upcase_word },
{ "yank", rl_yank },
{ "yank-last-arg", rl_yank_last_arg },
{ "yank-nth-arg", rl_yank_nth_arg },
{ "yank-pop", rl_yank_pop },
#if defined (VI_MODE)
{ "vi-append-eol", rl_vi_append_eol },
{ "vi-append-mode", rl_vi_append_mode },
{ "vi-arg-digit", rl_vi_arg_digit },
{ "vi-bWord", rl_vi_bWord },
{ "vi-bracktype", rl_vi_bracktype },
{ "vi-bword", rl_vi_bword },
{ "vi-change-case", rl_vi_change_case },
{ "vi-change-char", rl_vi_change_char },
{ "vi-change-to", rl_vi_change_to },
{ "vi-char-search", rl_vi_char_search },
{ "vi-column", rl_vi_column },
{ "vi-comment", rl_vi_comment },
{ "vi-complete", rl_vi_complete },
{ "vi-delete", rl_vi_delete },
{ "vi-delete-to", rl_vi_delete_to },
{ "vi-eWord", rl_vi_eWord },
{ "vi-editing-mode", rl_vi_editing_mode },
{ "vi-end-word", rl_vi_end_word },
{ "vi-eof-maybe", rl_vi_eof_maybe },
{ "vi-eword", rl_vi_eword },
{ "vi-fWord", rl_vi_fWord },
{ "vi-first-print", rl_vi_first_print },
{ "vi-fword", rl_vi_fword },
{ "vi-insert-beg", rl_vi_insert_beg },
{ "vi-insertion-mode", rl_vi_insertion_mode },
{ "vi-match", rl_vi_match },
{ "vi-movement-mode", rl_vi_movement_mode },
{ "vi-next-word", rl_vi_next_word },
{ "vi-overstrike", rl_vi_overstrike },
{ "vi-overstrike-delete", rl_vi_overstrike_delete },
{ "vi-prev-word", rl_vi_prev_word },
{ "vi-put", rl_vi_put },
{ "vi-redo", rl_vi_redo },
{ "vi-replace", rl_vi_replace },
{ "vi-search", rl_vi_search },
{ "vi-search-again", rl_vi_search_again },
{ "vi-subst", rl_vi_subst },
{ "vi-tilde-expand", rl_vi_tilde_expand },
{ "vi-yank-arg", rl_vi_yank_arg },
{ "vi-yank-to", rl_vi_yank_to },
#endif /* VI_MODE */
{(char *)NULL, (Function *)NULL }
};
rl_add_funmap_entry (name, function)
char *name;
Function *function;
{
if (funmap_entry + 2 >= funmap_size)
if (!funmap)
funmap = (FUNMAP **)xmalloc ((funmap_size = 80) * sizeof (FUNMAP *));
else
funmap =
(FUNMAP **)xrealloc (funmap, (funmap_size += 80) * sizeof (FUNMAP *));
funmap[funmap_entry] = (FUNMAP *)xmalloc (sizeof (FUNMAP));
funmap[funmap_entry]->name = name;
funmap[funmap_entry]->function = function;
funmap[++funmap_entry] = (FUNMAP *)NULL;
return funmap_entry;
}
static int funmap_initialized = 0;
/* Make the funmap contain all of the default entries. */
void
rl_initialize_funmap ()
{
register int i;
if (funmap_initialized)
return;
for (i = 0; default_funmap[i].name; i++)
rl_add_funmap_entry (default_funmap[i].name, default_funmap[i].function);
funmap_initialized = 1;
funmap_program_specific_entry_start = i;
}
/* Produce a NULL terminated array of known function names. The array
is sorted. The array itself is allocated, but not the strings inside.
You should free () the array when you done, but not the pointrs. */
char **
rl_funmap_names ()
{
char **result = (char **)NULL;
int result_size, result_index;
result_size = result_index = 0;
/* Make sure that the function map has been initialized. */
rl_initialize_funmap ();
for (result_index = 0; funmap[result_index]; result_index++)
{
if (result_index + 2 > result_size)
{
if (!result)
result = (char **)xmalloc ((result_size = 20) * sizeof (char *));
else
result = (char **)
xrealloc (result, (result_size += 20) * sizeof (char *));
}
result[result_index] = funmap[result_index]->name;
result[result_index + 1] = (char *)NULL;
}
qsort (result, result_index, sizeof (char *), qsort_string_compare);
return (result);
}
/* Stupid comparison routine for qsort () ing strings. */
static int
qsort_string_compare (s1, s2)
register char **s1, **s2;
{
int r;
r = **s1 - **s2;
if (r == 0)
r = strcmp (*s1, *s2);
return r;
}
/* Things that mean `Control'. */
char *possible_control_prefixes[] = {
"Control-", "C-", "CTRL-", (char *)NULL
};
char *possible_meta_prefixes[] = {
"Meta", "M-", (char *)NULL
};
#if defined (STATIC_MALLOC)
/* **************************************************************** */
/* */
/* xmalloc and xrealloc () */
/* */
/* **************************************************************** */
static void memory_error_and_abort ();
static char *
xmalloc (bytes)
int bytes;
{
char *temp = (char *)malloc (bytes);
if (!temp)
memory_error_and_abort ();
return (temp);
}
static char *
xrealloc (pointer, bytes)
char *pointer;
int bytes;
{
char *temp;
if (!pointer)
temp = (char *)malloc (bytes);
else
temp = (char *)realloc (pointer, bytes);
if (!temp)
memory_error_and_abort ();
return (temp);
}
static void
memory_error_and_abort ()
{
fprintf (stderr, "history: Out of virtual memory!\n");
abort ();
}
#endif /* STATIC_MALLOC */

2218
lib/readline/history.c Normal file

File diff suppressed because it is too large Load diff

181
lib/readline/history.h Normal file
View file

@ -0,0 +1,181 @@
/* History.h -- the names of functions that you can call in history. */
/* The structure used to store a history entry. */
typedef struct _hist_entry {
char *line;
char *data;
} HIST_ENTRY;
/* A structure used to pass the current state of the history stuff around. */
typedef struct _hist_state {
HIST_ENTRY **entries; /* Pointer to the entries themselves. */
int offset; /* The location pointer within this array. */
int length; /* Number of elements within this array. */
int size; /* Number of slots allocated to this array. */
int flags;
} HISTORY_STATE;
/* Flag values for the `flags' member of HISTORY_STATE. */
#define HS_STIFLED 0x01
/* Initialization and state management. */
/* Begin a session in which the history functions might be used. This
just initializes the interactive variables. */
extern void using_history ();
/* Return the current HISTORY_STATE of the history. */
extern HISTORY_STATE *history_get_history_state ();
/* Set the state of the current history array to STATE. */
extern void history_set_history_state ();
/* Manage the history list. */
/* Place STRING at the end of the history list.
The associated data field (if any) is set to NULL. */
extern void add_history ();
/* A reasonably useless function, only here for completeness. WHICH
is the magic number that tells us which element to delete. The
elements are numbered from 0. */
extern HIST_ENTRY *remove_history ();
/* Make the history entry at WHICH have LINE and DATA. This returns
the old entry so you can dispose of the data. In the case of an
invalid WHICH, a NULL pointer is returned. */
extern HIST_ENTRY *replace_history_entry ();
/* Stifle the history list, remembering only MAX number of entries. */
extern void stifle_history ();
/* Stop stifling the history. This returns the previous amount the
history was stifled by. The value is positive if the history was
stifled, negative if it wasn't. */
extern int unstifle_history ();
/* Return 1 if the history is stifled, 0 if it is not. */
extern int history_is_stifled ();
/* Information about the history list. */
/* Return a NULL terminated array of HIST_ENTRY which is the current input
history. Element 0 of this list is the beginning of time. If there
is no history, return NULL. */
extern HIST_ENTRY **history_list ();
/* Returns the number which says what history element we are now
looking at. */
extern int where_history ();
/* Return the history entry at the current position, as determined by
history_offset. If there is no entry there, return a NULL pointer. */
HIST_ENTRY *current_history ();
/* Return the history entry which is logically at OFFSET in the history
array. OFFSET is relative to history_base. */
extern HIST_ENTRY *history_get ();
/* Return the number of bytes that the primary history entries are using.
This just adds up the lengths of the_history->lines. */
extern int history_total_bytes ();
/* Moving around the history list. */
/* Set the position in the history list to POS. */
int history_set_pos ();
/* Back up history_offset to the previous history entry, and return
a pointer to that entry. If there is no previous entry, return
a NULL pointer. */
extern HIST_ENTRY *previous_history ();
/* Move history_offset forward to the next item in the input_history,
and return the a pointer to that entry. If there is no next entry,
return a NULL pointer. */
extern HIST_ENTRY *next_history ();
/* Searching the history list. */
/* Search the history for STRING, starting at history_offset.
If DIRECTION < 0, then the search is through previous entries,
else through subsequent. If the string is found, then
current_history () is the history entry, and the value of this function
is the offset in the line of that history entry that the string was
found in. Otherwise, nothing is changed, and a -1 is returned. */
extern int history_search ();
/* Search the history for STRING, starting at history_offset.
The search is anchored: matching lines must begin with string. */
extern int history_search_prefix ();
/* Search for STRING in the history list, starting at POS, an
absolute index into the list. DIR, if negative, says to search
backwards from POS, else forwards.
Returns the absolute index of the history element where STRING
was found, or -1 otherwise. */
extern int history_search_pos ();
/* Managing the history file. */
/* Add the contents of FILENAME to the history list, a line at a time.
If FILENAME is NULL, then read from ~/.history. Returns 0 if
successful, or errno if not. */
extern int read_history ();
/* Read a range of lines from FILENAME, adding them to the history list.
Start reading at the FROM'th line and end at the TO'th. If FROM
is zero, start at the beginning. If TO is less than FROM, read
until the end of the file. If FILENAME is NULL, then read from
~/.history. Returns 0 if successful, or errno if not. */
extern int read_history_range ();
/* Write the current history to FILENAME. If FILENAME is NULL,
then write the history list to ~/.history. Values returned
are as in read_history (). */
extern int write_history ();
/* Append NELEMENT entries to FILENAME. The entries appended are from
the end of the list minus NELEMENTs up to the end of the list. */
int append_history ();
/* Truncate the history file, leaving only the last NLINES lines. */
extern int history_truncate_file ();
/* History expansion. */
/* Expand the string STRING, placing the result into OUTPUT, a pointer
to a string. Returns:
0) If no expansions took place (or, if the only change in
the text was the de-slashifying of the history expansion
character)
1) If expansions did take place
-1) If there was an error in expansion.
2) If the returned line should just be printed.
If an error ocurred in expansion, then OUTPUT contains a descriptive
error message. */
extern int history_expand ();
/* Extract a string segment consisting of the FIRST through LAST
arguments present in STRING. Arguments are broken up as in
the shell. */
extern char *history_arg_extract ();
/* Return the text of the history event beginning at the current
offset into STRING. */
extern char *get_history_event ();
/* Return an array of tokens, much as the shell might. The tokens are
parsed out of STRING. */
extern char **history_tokenize ();
/* Exported history variables. */
extern int history_base;
extern int history_length;
extern int max_input_history;
extern char history_expansion_char;
extern char history_subst_char;
extern char history_comment_char;
extern char *history_no_expand_chars;

378
lib/readline/isearch.c Normal file
View file

@ -0,0 +1,378 @@
/* **************************************************************** */
/* */
/* I-Search and Searching */
/* */
/* **************************************************************** */
/* Copyright (C) 1987,1989 Free Software Foundation, Inc.
This file contains the Readline Library (the Library), a set of
routines for providing Emacs style line input to programs that ask
for it.
The Library is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 1, or (at your option)
any later version.
The Library is distributed in the hope that it will be useful, but
WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
General Public License for more details.
The GNU General Public License is often shipped with GNU software, and
is generally kept in a file called COPYING or LICENSE. If you do not
have a copy of the license, write to the Free Software Foundation,
675 Mass Ave, Cambridge, MA 02139, USA. */
#define READLINE_LIBRARY
#include <stdio.h>
#if defined (HAVE_UNISTD_H)
# include <unistd.h>
#endif
#include "memalloc.h"
#include "readline.h"
#include "history.h"
#define STREQ(a, b) (((a)[0] == (b)[0]) && (strcmp ((a), (b)) == 0))
#define STREQN(a, b, n) (((a)[0] == (b)[0]) && (strncmp ((a), (b), (n)) == 0))
/* Variables imported from other files in the readline library. */
extern Keymap _rl_keymap;
extern HIST_ENTRY *saved_line_for_history;
extern int rl_line_buffer_len;
extern int rl_point, rl_end;
extern char *rl_line_buffer;
extern char *xmalloc (), *xrealloc ();
static int rl_search_history ();
/* Last line found by the current incremental search, so we don't `find'
identical lines many times in a row. */
static char *prev_line_found;
/* Search backwards through the history looking for a string which is typed
interactively. Start with the current line. */
rl_reverse_search_history (sign, key)
int sign;
int key;
{
return (rl_search_history (-sign, key));
}
/* Search forwards through the history looking for a string which is typed
interactively. Start with the current line. */
rl_forward_search_history (sign, key)
int sign;
int key;
{
return (rl_search_history (sign, key));
}
/* Display the current state of the search in the echo-area.
SEARCH_STRING contains the string that is being searched for,
DIRECTION is zero for forward, or 1 for reverse,
WHERE is the history list number of the current line. If it is
-1, then this line is the starting one. */
static void
rl_display_search (search_string, reverse_p, where)
char *search_string;
int reverse_p, where;
{
char *message;
message = xmalloc (1 + (search_string ? strlen (search_string) : 0) + 30);
*message = '\0';
#if defined (NOTDEF)
if (where != -1)
sprintf (message, "[%d]", where + history_base);
#endif /* NOTDEF */
strcat (message, "(");
if (reverse_p)
strcat (message, "reverse-");
strcat (message, "i-search)`");
if (search_string)
strcat (message, search_string);
strcat (message, "': ");
rl_message ("%s", message, 0);
free (message);
rl_redisplay ();
}
/* Search through the history looking for an interactively typed string.
This is analogous to i-search. We start the search in the current line.
DIRECTION is which direction to search; >= 0 means forward, < 0 means
backwards. */
static int
rl_search_history (direction, invoking_key)
int direction;
int invoking_key;
{
/* The string that the user types in to search for. */
char *search_string;
/* The current length of SEARCH_STRING. */
int search_string_index;
/* The amount of space that SEARCH_STRING has allocated to it. */
int search_string_size;
/* The list of lines to search through. */
char **lines, *allocated_line = (char *)NULL;
/* The length of LINES. */
int hlen;
/* Where we get LINES from. */
HIST_ENTRY **hlist = history_list ();
register int i = 0;
int orig_point = rl_point;
int orig_line = where_history ();
int last_found_line = orig_line;
int c, done = 0, found, failed, sline_len;
/* The line currently being searched. */
char *sline;
/* Offset in that line. */
int line_index;
/* Non-zero if we are doing a reverse search. */
int reverse = (direction < 0);
/* Create an arrary of pointers to the lines that we want to search. */
maybe_replace_line ();
if (hlist)
for (i = 0; hlist[i]; i++);
/* Allocate space for this many lines, +1 for the current input line,
and remember those lines. */
lines = (char **)xmalloc ((1 + (hlen = i)) * sizeof (char *));
for (i = 0; i < hlen; i++)
lines[i] = hlist[i]->line;
if (saved_line_for_history)
lines[i] = saved_line_for_history->line;
else
{
/* Keep track of this so we can free it. */
allocated_line = xmalloc (1 + strlen (rl_line_buffer));
strcpy (allocated_line, &rl_line_buffer[0]);
lines[i] = allocated_line;
}
hlen++;
/* The line where we start the search. */
i = orig_line;
/* Initialize search parameters. */
search_string = xmalloc (search_string_size = 128);
*search_string = '\0';
search_string_index = 0;
prev_line_found = (char *)0; /* XXX */
/* Normalize DIRECTION into 1 or -1. */
direction = (direction >= 0) ? 1 : -1;
rl_display_search (search_string, reverse, -1);
sline = rl_line_buffer;
sline_len = strlen (sline);
line_index = rl_point;
found = failed = 0;
while (!done)
{
Function *f = (Function *)NULL;
/* Read a key and decide how to proceed. */
c = rl_read_key ();
/* Hack C to Do What I Mean. */
if (_rl_keymap[c].type == ISFUNC)
{
f = _rl_keymap[c].function;
if (f == rl_reverse_search_history)
c = reverse ? -1 : -2;
else if (f == rl_forward_search_history)
c = !reverse ? -1 : -2;
}
switch (c)
{
case ESC:
done = 1;
continue;
case -1:
if (!search_string_index)
continue;
else
{
if (reverse)
--line_index;
else
{
if (line_index != sline_len)
++line_index;
else
ding ();
}
}
break;
/* switch directions */
case -2:
direction = -direction;
reverse = (direction < 0);
break;
case CTRL ('G'):
strcpy (rl_line_buffer, lines[orig_line]);
rl_point = orig_point;
rl_end = strlen (rl_line_buffer);
rl_clear_message ();
free (allocated_line);
free (lines);
return 0;
default:
if (CTRL_CHAR (c) || META_CHAR (c) || c == RUBOUT)
{
rl_execute_next (c);
done = 1;
continue;
}
else
{
/* Add character to search string and continue search. */
if (search_string_index + 2 >= search_string_size)
{
search_string_size += 128;
search_string = xrealloc (search_string, search_string_size);
}
search_string[search_string_index++] = c;
search_string[search_string_index] = '\0';
break;
}
}
found = failed = 0;
while (1)
{
int limit = sline_len - search_string_index + 1;
/* Search the current line. */
while (reverse ? (line_index >= 0) : (line_index < limit))
{
if (STREQN(search_string, sline + line_index, search_string_index))
{
found++;
break;
}
else
line_index += direction;
}
if (found)
break;
/* Move to the next line, but skip new copies of the line
we just found and lines shorter than the string we're
searching for. */
do
{
/* Move to the next line. */
i += direction;
/* At limit for direction? */
if (reverse ? (i < 0) : (i == hlen))
{
failed++;
break;
}
/* We will need these later. */
sline = lines[i];
sline_len = strlen (sline);
}
while ((prev_line_found && STREQ (prev_line_found, lines[i])) ||
(search_string_index > sline_len));
if (failed)
break;
/* Now set up the line for searching... */
if (reverse)
line_index = sline_len - search_string_index;
else
line_index = 0;
}
if (failed)
{
/* We cannot find the search string. Ding the bell. */
ding ();
i = last_found_line;
continue; /* XXX - was break */
}
/* We have found the search string. Just display it. But don't
actually move there in the history list until the user accepts
the location. */
if (found)
{
int line_len;
prev_line_found = lines[i];
line_len = strlen (lines[i]);
if (line_len >= rl_line_buffer_len)
rl_extend_line_buffer (line_len);
strcpy (rl_line_buffer, lines[i]);
rl_point = line_index;
rl_end = line_len;
last_found_line = i;
rl_display_search (search_string, reverse, (i == orig_line) ? -1 : i);
}
}
/* The searching is over. The user may have found the string that she
was looking for, or else she may have exited a failing search. If
LINE_INDEX is -1, then that shows that the string searched for was
not found. We use this to determine where to place rl_point. */
/* First put back the original state. */
strcpy (rl_line_buffer, lines[orig_line]);
/* Free the search string. */
free (search_string);
if (last_found_line < orig_line)
rl_get_previous_history (orig_line - last_found_line);
else
rl_get_next_history (last_found_line - orig_line);
/* If the string was not found, put point at the end of the line. */
if (line_index < 0)
line_index = strlen (rl_line_buffer);
rl_point = line_index;
rl_clear_message ();
free (allocated_line);
free (lines);
return 0;
}

200
lib/readline/keymaps.c Normal file
View file

@ -0,0 +1,200 @@
/* keymaps.c -- Functions and keymaps for the GNU Readline library. */
/* Copyright (C) 1988,1989 Free Software Foundation, Inc.
This file is part of GNU Readline, a library for reading lines
of text with interactive input and history editing.
Readline is free software; you can redistribute it and/or modify it
under the terms of the GNU General Public License as published by the
Free Software Foundation; either version 1, or (at your option) any
later version.
Readline is distributed in the hope that it will be useful, but
WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
General Public License for more details.
You should have received a copy of the GNU General Public License
along with Readline; see the file COPYING. If not, write to the Free
Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA. */
#define READLINE_LIBRARY
#if defined (HAVE_CONFIG_H)
# include "config.h"
#endif
#if defined (HAVE_STDLIB_H)
# include <stdlib.h>
#else
# include "ansi_stdlib.h"
#endif /* HAVE_STDLIB_H */
#include "rlconf.h"
#include "keymaps.h"
#include "emacs_keymap.c"
#if defined (VI_MODE)
#include "vi_keymap.c"
#endif
extern int rl_do_lowercase_version ();
extern int rl_rubout (), rl_insert ();
#if defined (STATIC_MALLOC)
static char *xmalloc (), *xrealloc ();
#else
extern char *xmalloc (), *xrealloc ();
#endif /* STATIC_MALLOC */
/* **************************************************************** */
/* */
/* Functions for manipulating Keymaps. */
/* */
/* **************************************************************** */
/* Return a new, empty keymap.
Free it with free() when you are done. */
Keymap
rl_make_bare_keymap ()
{
register int i;
Keymap keymap = (Keymap)xmalloc (KEYMAP_SIZE * sizeof (KEYMAP_ENTRY));
for (i = 0; i < KEYMAP_SIZE; i++)
{
keymap[i].type = ISFUNC;
keymap[i].function = (Function *)NULL;
}
for (i = 'A'; i < ('Z' + 1); i++)
{
keymap[i].type = ISFUNC;
keymap[i].function = rl_do_lowercase_version;
}
return (keymap);
}
/* Return a new keymap which is a copy of MAP. */
Keymap
rl_copy_keymap (map)
Keymap map;
{
register int i;
Keymap temp = rl_make_bare_keymap ();
for (i = 0; i < KEYMAP_SIZE; i++)
{
temp[i].type = map[i].type;
temp[i].function = map[i].function;
}
return (temp);
}
/* Return a new keymap with the printing characters bound to rl_insert,
the uppercase Meta characters bound to run their lowercase equivalents,
and the Meta digits bound to produce numeric arguments. */
Keymap
rl_make_keymap ()
{
register int i;
Keymap newmap;
newmap = rl_make_bare_keymap ();
/* All ASCII printing characters are self-inserting. */
for (i = ' '; i < 127; i++)
newmap[i].function = rl_insert;
newmap[TAB].function = rl_insert;
newmap[RUBOUT].function = rl_rubout;
newmap[CTRL('H')].function = rl_rubout;
#if KEYMAP_SIZE > 128
/* Printing characters in some 8-bit character sets. */
for (i = 128; i < 160; i++)
newmap[i].function = rl_insert;
/* ISO Latin-1 printing characters should self-insert. */
for (i = 160; i < 256; i++)
newmap[i].function = rl_insert;
#endif /* KEYMAP_SIZE > 128 */
return (newmap);
}
/* Free the storage associated with MAP. */
void
rl_discard_keymap (map)
Keymap (map);
{
int i;
if (!map)
return;
for (i = 0; i < KEYMAP_SIZE; i++)
{
switch (map[i].type)
{
case ISFUNC:
break;
case ISKMAP:
rl_discard_keymap ((Keymap)map[i].function);
break;
case ISMACR:
free ((char *)map[i].function);
break;
}
}
}
#if defined (STATIC_MALLOC)
/* **************************************************************** */
/* */
/* xmalloc and xrealloc () */
/* */
/* **************************************************************** */
static void memory_error_and_abort ();
static char *
xmalloc (bytes)
int bytes;
{
char *temp = (char *)malloc (bytes);
if (!temp)
memory_error_and_abort ();
return (temp);
}
static char *
xrealloc (pointer, bytes)
char *pointer;
int bytes;
{
char *temp;
if (!pointer)
temp = (char *)malloc (bytes);
else
temp = (char *)realloc (pointer, bytes);
if (!temp)
memory_error_and_abort ();
return (temp);
}
static void
memory_error_and_abort ()
{
fprintf (stderr, "readline: Out of virtual memory!\n");
abort ();
}
#endif /* STATIC_MALLOC */

95
lib/readline/keymaps.h Normal file
View file

@ -0,0 +1,95 @@
/* keymaps.h -- Manipulation of readline keymaps. */
/* Copyright (C) 1987, 1989, 1992 Free Software Foundation, Inc.
This file is part of the GNU Readline Library, a library for
reading lines of text with interactive input and history editing.
The GNU Readline Library is free software; you can redistribute it
and/or modify it under the terms of the GNU General Public License
as published by the Free Software Foundation; either version 1, or
(at your option) any later version.
The GNU Readline Library is distributed in the hope that it will be
useful, but WITHOUT ANY WARRANTY; without even the implied warranty
of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
The GNU General Public License is often shipped with GNU software, and
is generally kept in a file called COPYING or LICENSE. If you do not
have a copy of the license, write to the Free Software Foundation,
675 Mass Ave, Cambridge, MA 02139, USA. */
#ifndef _KEYMAPS_H_
#define _KEYMAPS_H_
#if defined (READLINE_LIBRARY)
# include "chardefs.h"
#else
# include <readline/chardefs.h>
#endif
#if !defined (__FUNCTION_DEF)
# define __FUNCTION_DEF
typedef int Function ();
typedef void VFunction ();
typedef char *CPFunction ();
typedef char **CPPFunction ();
#endif
/* A keymap contains one entry for each key in the ASCII set.
Each entry consists of a type and a pointer.
POINTER is the address of a function to run, or the
address of a keymap to indirect through.
TYPE says which kind of thing POINTER is. */
typedef struct _keymap_entry {
char type;
Function *function;
} KEYMAP_ENTRY;
/* This must be large enough to hold bindings for all of the characters
in a desired character set (e.g, 128 for ASCII, 256 for ISO Latin-x,
and so on). */
#define KEYMAP_SIZE 256
/* I wanted to make the above structure contain a union of:
union { Function *function; struct _keymap_entry *keymap; } value;
but this made it impossible for me to create a static array.
Maybe I need C lessons. */
typedef KEYMAP_ENTRY KEYMAP_ENTRY_ARRAY[KEYMAP_SIZE];
typedef KEYMAP_ENTRY *Keymap;
/* The values that TYPE can have in a keymap entry. */
#define ISFUNC 0
#define ISKMAP 1
#define ISMACR 2
extern KEYMAP_ENTRY_ARRAY emacs_standard_keymap, emacs_meta_keymap, emacs_ctlx_keymap;
extern KEYMAP_ENTRY_ARRAY vi_insertion_keymap, vi_movement_keymap;
/* Return a new, empty keymap.
Free it with free() when you are done. */
extern Keymap rl_make_bare_keymap ();
/* Return a new keymap which is a copy of MAP. */
extern Keymap rl_copy_keymap ();
/* Return a new keymap with the printing characters bound to rl_insert,
the lowercase Meta characters bound to run their equivalents, and
the Meta digits bound to produce numeric arguments. */
extern Keymap rl_make_keymap ();
extern void rl_discard_keymap ();
/* Return the keymap corresponding to a given name. Names look like
`emacs' or `emacs-meta' or `vi-insert'. */
extern Keymap rl_get_keymap_by_name ();
/* Return the current keymap. */
extern Keymap rl_get_keymap ();
/* Set the current keymap to MAP. */
extern void rl_set_keymap ();
#endif /* _KEYMAPS_H_ */

56
lib/readline/memalloc.h Normal file
View file

@ -0,0 +1,56 @@
/* memalloc.h -- consolidate code for including alloca.h or malloc.h and
defining alloca. */
/* Copyright (C) 1993 Free Software Foundation, Inc.
This file is part of GNU Bash, the Bourne Again SHell.
Bash is free software; you can redistribute it and/or modify it under
the terms of the GNU General Public License as published by the Free
Software Foundation; either version 2, or (at your option) any later
version.
Bash is distributed in the hope that it will be useful, but WITHOUT ANY
WARRANTY; without even the implied warranty of MERCHANTABILITY or
FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
for more details.
You should have received a copy of the GNU General Public License along
with Bash; see the file COPYING. If not, write to the Free Software
Foundation, 675 Mass Ave, Cambridge, MA 02139, USA. */
#if !defined (__MEMALLOC_H__)
# define __MEMALLOC_H__
#if defined (sparc) && defined (sun) && !defined (HAVE_ALLOCA_H)
# define HAVE_ALLOCA_H
#endif
#if defined (__GNUC__) && !defined (HAVE_ALLOCA)
# define HAVE_ALLOCA
#endif
#if defined (HAVE_ALLOCA_H) && !defined (HAVE_ALLOCA)
# define HAVE_ALLOCA
#endif /* HAVE_ALLOCA_H && !HAVE_ALLOCA */
#if !defined (BUILDING_MAKEFILE)
#if defined (__GNUC__)
# undef alloca
# define alloca __builtin_alloca
#else /* !__GNUC__ */
# if defined (HAVE_ALLOCA_H)
# if defined (IBMESA)
# include <malloc.h>
# else /* !IBMESA */
# include <alloca.h>
# endif /* !IBMESA */
# else
extern char *alloca ();
# endif /* !HAVE_ALLOCA_H */
#endif /* !__GNUC__ */
#endif /* !BUILDING_MAKEFILE */
#endif /* __MEMALLOC_H__ */

130
lib/readline/parens.c Normal file
View file

@ -0,0 +1,130 @@
/* parens.c -- Implemenation of matching parenthesis feature. */
/* Copyright (C) 1987, 1989, 1992 Free Software Foundation, Inc.
This file is part of the GNU Readline Library, a library for
reading lines of text with interactive input and history editing.
The GNU Readline Library is free software; you can redistribute it
and/or modify it under the terms of the GNU General Public License
as published by the Free Software Foundation; either version 1, or
(at your option) any later version.
The GNU Readline Library is distributed in the hope that it will be
useful, but WITHOUT ANY WARRANTY; without even the implied warranty
of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
The GNU General Public License is often shipped with GNU software, and
is generally kept in a file called COPYING or LICENSE. If you do not
have a copy of the license, write to the Free Software Foundation,
675 Mass Ave, Cambridge, MA 02139, USA. */
#define READLINE_LIBRARY
#include "rlconf.h"
#if !defined (PAREN_MATCHING)
rl_insert_close (count, invoking_key)
int count, invoking_key;
{
return (rl_insert (count, invoking_key));
}
#else /* PAREN_MATCHING */
#include <stdio.h>
#include <sys/types.h>
#if defined (FD_SET)
# include <sys/time.h>
#endif /* FD_SET */
#include "readline.h"
extern int rl_explicit_arg;
/* Non-zero means try to blink the matching open parenthesis when the
close parenthesis is inserted. */
#if defined (FD_SET)
int rl_blink_matching_paren = 1;
#else /* !FD_SET */
int rl_blink_matching_paren = 0;
#endif /* !FD_SET */
static int find_matching_open ();
rl_insert_close (count, invoking_key)
int count, invoking_key;
{
if (rl_explicit_arg || !rl_blink_matching_paren)
rl_insert (count, invoking_key);
else
{
#if defined (FD_SET)
int orig_point, match_point, ready;
struct timeval timer;
fd_set readfds;
rl_insert (1, invoking_key);
rl_redisplay ();
match_point =
find_matching_open (rl_line_buffer, rl_point - 2, invoking_key);
/* Emacs might message or ring the bell here, but I don't. */
if (match_point < 0)
return -1;
FD_ZERO (&readfds);
FD_SET (fileno (rl_instream), &readfds);
timer.tv_sec = 1;
timer.tv_usec = 500;
orig_point = rl_point;
rl_point = match_point;
rl_redisplay ();
ready = select (1, &readfds, (fd_set *)NULL, (fd_set *)NULL, &timer);
rl_point = orig_point;
#else /* !FD_SET */
rl_insert (count, invoking_key);
#endif /* !FD_SET */
}
return 0;
}
static int
find_matching_open (string, from, closer)
char *string;
int from, closer;
{
register int i;
int opener, level, delimiter;
switch (closer)
{
case ']': opener = '['; break;
case '}': opener = '{'; break;
case ')': opener = '('; break;
default:
return (-1);
}
level = 1; /* The closer passed in counts as 1. */
delimiter = 0; /* Delimited state unknown. */
for (i = from; i > -1; i--)
{
if (delimiter && (string[i] == delimiter))
delimiter = 0;
else if ((string[i] == '\'') || (string[i] == '"'))
delimiter = rl_line_buffer[i];
else if (!delimiter && (string[i] == closer))
level++;
else if (!delimiter && (string[i] == opener))
level--;
if (!level)
break;
}
return (i);
}
#endif /* PAREN_MATCHING */

149
lib/readline/posixstat.h Normal file
View file

@ -0,0 +1,149 @@
/* posixstat.h -- Posix stat(2) definitions for systems that
don't have them. */
/* Copyright (C) 1987,1991 Free Software Foundation, Inc.
This file is part of GNU Bash, the Bourne Again SHell.
Bash is free software; you can redistribute it and/or modify it
under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 1, or (at your option)
any later version.
Bash is distributed in the hope that it will be useful, but WITHOUT
ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public
License for more details.
You should have received a copy of the GNU General Public License
along with Bash; see the file COPYING. If not, write to the Free
Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA. */
/* This file should be included instead of <sys/stat.h>.
It relies on the local sys/stat.h to work though. */
#if !defined (_POSIXSTAT_H)
#define _POSIXSTAT_H
#include <sys/stat.h>
#if defined (isc386)
# if !defined (S_IFDIR)
# define S_IFDIR 0040000
# endif /* !S_IFDIR */
# if !defined (S_IFMT)
# define S_IFMT 0170000
# endif /* !S_IFMT */
#endif /* isc386 */
/* This text is taken directly from the Cadmus I was trying to
compile on:
the following MACROs are defined for X/OPEN compatibility
however, is the param correct ??
#define S_ISBLK(s) ((s.st_mode & S_IFMT) == S_IFBLK)
Well, the answer is no. Thus... */
#if defined (BrainDeath)
# undef S_ISBLK
# undef S_ISCHR
# undef S_ISDIR
# undef S_ISFIFO
# undef S_ISREG
#endif /* BrainDeath */
/* Posix 1003.1 5.6.1.1 <sys/stat.h> file types */
/* Some Posix-wannabe systems define _S_IF* macros instead of S_IF*, but
do not provide the S_IS* macros that Posix requires. */
#if defined (_S_IFMT) && !defined (S_IFMT)
#define S_IFMT _S_IFMT
#endif
#if defined (_S_IFIFO) && !defined (S_IFIFO)
#define S_IFIFO _S_IFIFO
#endif
#if defined (_S_IFCHR) && !defined (S_IFCHR)
#define S_IFCHR _S_IFCHR
#endif
#if defined (_S_IFDIR) && !defined (S_IFDIR)
#define S_IFDIR _S_IFDIR
#endif
#if defined (_S_IFBLK) && !defined (S_IFBLK)
#define S_IFBLK _S_IFBLK
#endif
#if defined (_S_IFREG) && !defined (S_IFREG)
#define S_IFREG _S_IFREG
#endif
#if defined (_S_IFLNK) && !defined (S_IFLNK)
#define S_IFLNK _S_IFLNK
#endif
#if defined (_S_IFSOCK) && !defined (S_IFSOCK)
#define S_IFSOCK _S_IFSOCK
#endif
/* Test for each symbol individually and define the ones necessary (some
systems claiming Posix compatibility define some but not all). */
#if defined (S_IFBLK) && !defined (S_ISBLK)
#define S_ISBLK(m) (((m)&S_IFMT) == S_IFBLK) /* block device */
#endif
#if defined (S_IFCHR) && !defined (S_ISCHR)
#define S_ISCHR(m) (((m)&S_IFMT) == S_IFCHR) /* character device */
#endif
#if defined (S_IFDIR) && !defined (S_ISDIR)
#define S_ISDIR(m) (((m)&S_IFMT) == S_IFDIR) /* directory */
#endif
#if defined (S_IFREG) && !defined (S_ISREG)
#define S_ISREG(m) (((m)&S_IFMT) == S_IFREG) /* file */
#endif
#if defined (S_IFIFO) && !defined (S_ISFIFO)
#define S_ISFIFO(m) (((m)&S_IFMT) == S_IFIFO) /* fifo - named pipe */
#endif
#if defined (S_IFLNK) && !defined (S_ISLNK)
#define S_ISLNK(m) (((m)&S_IFMT) == S_IFLNK) /* symbolic link */
#endif
#if defined (S_IFSOCK) && !defined (S_ISSOCK)
#define S_ISSOCK(m) (((m)&S_IFMT) == S_IFSOCK) /* socket */
#endif
/*
* POSIX 1003.1 5.6.1.2 <sys/stat.h> File Modes
*/
#if !defined (S_IRWXU)
# if !defined (S_IREAD)
# define S_IREAD 00400
# define S_IWRITE 00200
# define S_IEXEC 00100
# endif /* S_IREAD */
# if !defined (S_IRUSR)
# define S_IRUSR S_IREAD /* read, owner */
# define S_IWUSR S_IWRITE /* write, owner */
# define S_IXUSR S_IEXEC /* execute, owner */
# define S_IRGRP (S_IREAD >> 3) /* read, group */
# define S_IWGRP (S_IWRITE >> 3) /* write, group */
# define S_IXGRP (S_IEXEC >> 3) /* execute, group */
# define S_IROTH (S_IREAD >> 6) /* read, other */
# define S_IWOTH (S_IWRITE >> 6) /* write, other */
# define S_IXOTH (S_IEXEC >> 6) /* execute, other */
# endif /* !S_IRUSR */
# define S_IRWXU (S_IRUSR | S_IWUSR | S_IXUSR)
# define S_IRWXG (S_IRGRP | S_IWGRP | S_IXGRP)
# define S_IRWXO (S_IROTH | S_IWOTH | S_IXOTH)
#endif /* !S_IRWXU */
/* These are non-standard, but are used in builtins.c$symbolic_umask() */
#define S_IRUGO (S_IRUSR | S_IRGRP | S_IROTH)
#define S_IWUGO (S_IWUSR | S_IWGRP | S_IWOTH)
#define S_IXUGO (S_IXUSR | S_IXGRP | S_IXOTH)
#endif /* _POSIXSTAT_H */

3539
lib/readline/readline.c Normal file

File diff suppressed because it is too large Load diff

289
lib/readline/readline.h Normal file
View file

@ -0,0 +1,289 @@
/* Readline.h -- the names of functions callable from within readline. */
/* Copyright (C) 1987, 1989, 1992 Free Software Foundation, Inc.
This file is part of the GNU Readline Library, a library for
reading lines of text with interactive input and history editing.
The GNU Readline Library is free software; you can redistribute it
and/or modify it under the terms of the GNU General Public License
as published by the Free Software Foundation; either version 1, or
(at your option) any later version.
The GNU Readline Library is distributed in the hope that it will be
useful, but WITHOUT ANY WARRANTY; without even the implied warranty
of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
The GNU General Public License is often shipped with GNU software, and
is generally kept in a file called COPYING or LICENSE. If you do not
have a copy of the license, write to the Free Software Foundation,
675 Mass Ave, Cambridge, MA 02139, USA. */
#if !defined (_READLINE_H_)
#define _READLINE_H_
#if defined (READLINE_LIBRARY)
# include "keymaps.h"
# include "tilde.h"
#else
# include <readline/keymaps.h>
# include <readline/tilde.h>
#endif
/* The functions for manipulating the text of the line within readline.
Most of these functions are bound to keys by default. */
extern int
rl_tilde_expand (),
rl_beg_of_line (), rl_backward (), rl_delete (), rl_end_of_line (),
rl_forward (), ding (), rl_backward (), rl_newline (), rl_kill_line (),
rl_clear_screen (), rl_get_next_history (), rl_get_previous_history (),
rl_quoted_insert (), rl_reverse_search_history (), rl_transpose_chars (),
rl_unix_line_discard (), rl_quoted_insert (), rl_unix_word_rubout (),
rl_yank (), rl_rubout (), rl_backward_word (), rl_kill_word (),
rl_forward_word (), rl_tab_insert (), rl_yank_pop (), rl_yank_nth_arg (),
rl_backward_kill_word (), rl_backward_kill_line (), rl_transpose_words (),
rl_complete (), rl_possible_completions (), rl_insert_completions (),
rl_do_lowercase_version (), rl_kill_full_line (),
rl_digit_argument (), rl_universal_argument (), rl_abort (),
rl_undo_command (), rl_revert_line (), rl_beginning_of_history (),
rl_end_of_history (), rl_forward_search_history (), rl_insert (),
rl_upcase_word (), rl_downcase_word (), rl_capitalize_word (),
rl_restart_output (), rl_re_read_init_file (), rl_dump_functions (),
rl_delete_horizontal_space (), rl_history_search_forward (),
rl_history_search_backward (), rl_tty_status (), rl_yank_last_arg ();
/* `Public' utility functions. */
extern int rl_insert_text (), rl_delete_text (), rl_kill_text ();
extern int rl_complete_internal ();
extern int rl_expand_prompt ();
extern int rl_initialize ();
extern int rl_set_signals (), rl_clear_signals ();
extern int rl_init_argument (), rl_digit_argument ();
extern int rl_read_key (), rl_getc (), rl_stuff_char ();
extern int maybe_save_line (), maybe_unsave_line (), maybe_replace_line ();
extern int rl_modifying ();
extern int rl_begin_undo_group (), rl_end_undo_group ();
extern void rl_add_undo (), free_undo_list ();
extern int rl_do_undo ();
/* Not available unless readline is compiled -DPAREN_MATCHING. */
extern int rl_insert_close ();
/* These are *both* defined even when VI_MODE is not. */
extern int rl_vi_editing_mode (), rl_emacs_editing_mode ();
/* Non incremental history searching. */
extern int
rl_noninc_forward_search (), rl_noninc_reverse_search (),
rl_noninc_forward_search_again (), rl_noninc_reverse_search_again ();
/* Things for vi mode. Not available unless readline is compiled -DVI_MODE. */
extern int rl_vi_check (), rl_vi_textmod_command ();
extern int
rl_vi_redo (), rl_vi_tilde_expand (),
rl_vi_movement_mode (), rl_vi_insertion_mode (), rl_vi_arg_digit (),
rl_vi_prev_word (), rl_vi_next_word (), rl_vi_char_search (),
rl_vi_eof_maybe (), rl_vi_append_mode (), rl_vi_put (),
rl_vi_append_eol (), rl_vi_insert_beg (), rl_vi_delete (), rl_vi_comment (),
rl_vi_first_print (), rl_vi_fword (), rl_vi_fWord (), rl_vi_bword (),
rl_vi_bWord (), rl_vi_eword (), rl_vi_eWord (), rl_vi_end_word (),
rl_vi_change_case (), rl_vi_match (), rl_vi_bracktype (),
rl_vi_change_char (), rl_vi_yank_arg (), rl_vi_search (),
rl_vi_search_again (), rl_vi_subst (), rl_vi_overstrike (),
rl_vi_overstrike_delete (), rl_vi_replace(), rl_vi_column (),
rl_vi_delete_to (), rl_vi_change_to (), rl_vi_yank_to (),
rl_vi_complete (), rl_vi_fetch_history ();
/* Keyboard macro commands. */
extern int rl_start_kbd_macro (), rl_end_kbd_macro ();
extern int rl_call_last_kbd_macro ();
extern int rl_arrow_keys(), rl_refresh_line ();
/* Maintaining the state of undo. We remember individual deletes and inserts
on a chain of things to do. */
/* The actions that undo knows how to undo. Notice that UNDO_DELETE means
to insert some text, and UNDO_INSERT means to delete some text. I.e.,
the code tells undo what to undo, not how to undo it. */
enum undo_code { UNDO_DELETE, UNDO_INSERT, UNDO_BEGIN, UNDO_END };
/* What an element of THE_UNDO_LIST looks like. */
typedef struct undo_list {
struct undo_list *next;
int start, end; /* Where the change took place. */
char *text; /* The text to insert, if undoing a delete. */
enum undo_code what; /* Delete, Insert, Begin, End. */
} UNDO_LIST;
/* The current undo list for RL_LINE_BUFFER. */
extern UNDO_LIST *rl_undo_list;
/* The data structure for mapping textual names to code addresses. */
typedef struct {
char *name;
Function *function;
} FUNMAP;
extern FUNMAP **funmap;
/* **************************************************************** */
/* */
/* Well Published Variables */
/* */
/* **************************************************************** */
/* The name of the calling program. You should initialize this to
whatever was in argv[0]. It is used when parsing conditionals. */
extern char *rl_readline_name;
/* The line buffer that is in use. */
extern char *rl_line_buffer;
/* The location of point, and end. */
extern int rl_point, rl_end;
/* The name of the terminal to use. */
extern char *rl_terminal_name;
/* The input and output streams. */
extern FILE *rl_instream, *rl_outstream;
/* The basic list of characters that signal a break between words for the
completer routine. The initial contents of this variable is what
breaks words in the shell, i.e. "n\"\\'`@$>". */
extern char *rl_basic_word_break_characters;
/* The list of characters that signal a break between words for
rl_complete_internal. The default list is the contents of
rl_basic_word_break_characters. */
extern char *rl_completer_word_break_characters;
/* List of characters which can be used to quote a substring of the line.
Completion occurs on the entire substring, and within the substring
rl_completer_word_break_characters are treated as any other character,
unless they also appear within this list. */
extern char *rl_completer_quote_characters;
/* List of characters that are word break characters, but should be left
in TEXT when it is passed to the completion function. The shell uses
this to help determine what kind of completing to do. */
extern char *rl_special_prefixes;
/* Pointer to the generator function for completion_matches ().
NULL means to use filename_entry_function (), the default filename
completer. */
extern Function *rl_completion_entry_function;
/* If rl_ignore_some_completions_function is non-NULL it is the address
of a function to call after all of the possible matches have been
generated, but before the actual completion is done to the input line.
The function is called with one argument; a NULL terminated array
of (char *). If your function removes any of the elements, they
must be free()'ed. */
extern Function *rl_ignore_some_completions_function;
/* Pointer to alternative function to create matches.
Function is called with TEXT, START, and END.
START and END are indices in RL_LINE_BUFFER saying what the boundaries
of TEXT are.
If this function exists and returns NULL then call the value of
rl_completion_entry_function to try to match, otherwise use the
array of strings returned. */
extern CPPFunction *rl_attempted_completion_function;
/* If non-zero, then this is the address of a function to call just
before readline_internal () prints the first prompt. */
extern Function *rl_startup_hook;
/* If non-zero, then this is the address of a function to call when
completing on a directory name. The function is called with
the address of a string (the current directory name) as an arg. */
extern Function *rl_directory_completion_hook;
/* Backwards compatibility with previous versions of readline. */
#define rl_symbolic_link_hook rl_directory_completion_hook
/* The address of a function to call periodically while Readline is
awaiting character input, or NULL, for no event handling. */
extern Function *rl_event_hook;
/* Non-zero means that modified history lines are preceded
with an asterisk. */
extern int rl_show_star;
/* Non-zero means that the results of the matches are to be treated
as filenames. This is ALWAYS zero on entry, and can only be changed
within a completion entry finder function. */
extern int rl_filename_completion_desired;
/* Non-zero means that the results of the matches are to be quoted using
double quotes (or an application-specific quoting mechanism) if the
filename contains any characters in rl_word_break_chars. This is
ALWAYS non-zero on entry, and can only be changed within a completion
entry finder function. */
extern int rl_filename_quoting_desired;
/* Non-zero means to suppress normal filename completion after the
user-specified completion function has been called. */
extern int rl_attempted_completion_over;
/* **************************************************************** */
/* */
/* Well Published Functions */
/* */
/* **************************************************************** */
/* Read a line of input. Prompt with PROMPT. A NULL PROMPT means none. */
extern char *readline ();
/* These functions are from complete.c. */
/* Return an array of strings which are the result of repeatadly calling
FUNC with TEXT. */
extern char **completion_matches ();
extern char *username_completion_function ();
extern char *filename_completion_function ();
/* These functions are from bind.c. */
/* rl_add_defun (char *name, Function *function, int key)
Add NAME to the list of named functions. Make FUNCTION
be the function that gets called.
If KEY is not -1, then bind it. */
extern int rl_add_defun ();
extern int rl_bind_key (), rl_bind_key_in_map ();
extern int rl_unbind_key (), rl_unbind_key_in_map ();
extern int rl_set_key ();
extern int rl_macro_bind (), rl_generic_bind (), rl_variable_bind ();
extern int rl_translate_keyseq ();
extern Function *rl_named_function (), *rl_function_of_keyseq ();
extern int rl_parse_and_bind ();
extern Keymap rl_get_keymap (), rl_get_keymap_by_name ();
extern void rl_set_keymap ();
extern char **rl_invoking_keyseqs (), **rl_invoking_keyseqs_in_map ();
extern void rl_function_dumper ();
extern int rl_read_init_file ();
/* Functions in funmap.c */
extern void rl_list_funmap_names ();
extern void rl_initialize_funmap ();
/* Functions in display.c */
extern void rl_redisplay ();
extern int rl_message (), rl_clear_message ();
extern int rl_reset_line_state ();
extern int rl_character_len ();
extern int rl_show_char ();
extern int crlf (), rl_on_new_line ();
extern int rl_forced_update_display ();
/* Definitions available for use by readline clients. */
#define RL_PROMPT_START_IGNORE '\001'
#define RL_PROMPT_END_IGNORE '\002'
#if !defined (savestring)
extern char *savestring (); /* XXX backwards compatibility */
#endif
#endif /* _READLINE_H_ */

57
lib/readline/rlconf.h Normal file
View file

@ -0,0 +1,57 @@
/* rlconf.h -- readline configuration definitions */
/* Copyright (C) 1994 Free Software Foundation, Inc.
This file contains the Readline Library (the Library), a set of
routines for providing Emacs style line input to programs that ask
for it.
The Library is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 1, or (at your option)
any later version.
The Library is distributed in the hope that it will be useful, but
WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
General Public License for more details.
The GNU General Public License is often shipped with GNU software, and
is generally kept in a file called COPYING or LICENSE. If you do not
have a copy of the license, write to the Free Software Foundation,
675 Mass Ave, Cambridge, MA 02139, USA. */
#if !defined (_RLCONF_H_)
#define _RLCONF_H_
/* Define this if you want the vi-mode editing available. */
#define VI_MODE
/* Define this to get an indication of file type when listing completions. */
#define VISIBLE_STATS
/* If defined, readline shows opening parens and braces when closing
paren or brace entered. */
/* #define PAREN_MATCHING */
/* This definition is needed by readline.c, rltty.c, and signals.c. */
/* If on, then readline handles signals in a way that doesn't screw. */
#define HANDLE_SIGNALS
/* Ugly but working hack for binding prefix meta. */
#define PREFIX_META_HACK
/* The final, last-ditch effort file name for an init file. */
#define DEFAULT_INPUTRC "~/.inputrc"
/* If defined, expand tabs to spaces. */
#define DISPLAY_TABS
/* If defined, use the terminal escape sequence to move the cursor forward
over a character when updating the line rather than rewriting it. */
/* #define HACK_TERMCAP_MOTION */
/* The string inserted by the vi-mode `insert comment' command. */
#define VI_COMMENT_BEGIN_DEFAULT "#"
#endif /* _RLCONF_H_ */

212
lib/readline/rldefs.h Normal file
View file

@ -0,0 +1,212 @@
/* rldefs.h -- an attempt to isolate some of the system-specific defines
for readline. This should be included after any files that define
system-specific constants like _POSIX_VERSION or USG. */
/* Copyright (C) 1987,1989 Free Software Foundation, Inc.
This file contains the Readline Library (the Library), a set of
routines for providing Emacs style line input to programs that ask
for it.
The Library is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 1, or (at your option)
any later version.
The Library is distributed in the hope that it will be useful, but
WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
General Public License for more details.
The GNU General Public License is often shipped with GNU software, and
is generally kept in a file called COPYING or LICENSE. If you do not
have a copy of the license, write to the Free Software Foundation,
675 Mass Ave, Cambridge, MA 02139, USA. */
#if !defined (_RLDEFS_H)
#define _RLDEFS_H
#if defined (HAVE_CONFIG_H)
# include "config.h"
#endif
#if !defined (PRAGMA_ALLOCA)
# include "memalloc.h"
#endif
#define NEW_TTY_DRIVER
#define HAVE_BSD_SIGNALS
/* #define USE_XON_XOFF */
#if defined (__linux__) || defined (HAVE_TERMCAP_H)
# include <termcap.h>
#endif /* __linux__ || HAVE_TERMCAP_H */
/* Some USG machines have BSD signal handling (sigblock, sigsetmask, etc.) */
#if defined (USG) && !defined (hpux)
# undef HAVE_BSD_SIGNALS
#endif
/* System V machines use termio. */
#if !defined (_POSIX_VERSION)
# if defined (USG) || defined (hpux) || defined (Xenix) || defined (sgi) || \
defined (DGUX) || defined (HAVE_TERMIO_H)
# undef NEW_TTY_DRIVER
# define TERMIO_TTY_DRIVER
# include <termio.h>
# if !defined (TCOON)
# define TCOON 1
# endif
# endif /* USG || hpux || Xenix || sgi || DUGX || HAVE_TERMIO_H */
#endif /* !_POSIX_VERSION */
/* Posix systems use termios and the Posix signal functions. */
#if defined (_POSIX_VERSION)
# if !defined (TERMIOS_MISSING)
# undef NEW_TTY_DRIVER
# define TERMIOS_TTY_DRIVER
# include <termios.h>
# endif /* !TERMIOS_MISSING */
# define HAVE_POSIX_SIGNALS
# if !defined (O_NDELAY)
# define O_NDELAY O_NONBLOCK /* Posix-style non-blocking i/o */
# endif /* O_NDELAY */
#endif /* _POSIX_VERSION */
/* System V.3 machines have the old 4.1 BSD `reliable' signal interface. */
#if !defined (HAVE_BSD_SIGNALS) && !defined (HAVE_POSIX_SIGNALS)
# if defined (USGr3) && !defined (XENIX_22)
# if !defined (HAVE_USG_SIGHOLD)
# define HAVE_USG_SIGHOLD
# endif /* !HAVE_USG_SIGHOLD */
# endif /* USGr3 && !XENIX_22 */
#endif /* !HAVE_BSD_SIGNALS && !HAVE_POSIX_SIGNALS */
/* Other (BSD) machines use sgtty. */
#if defined (NEW_TTY_DRIVER)
# include <sgtty.h>
#endif
#if !defined (SHELL) && (defined (_POSIX_VERSION) || defined (USGr3))
# if !defined (HAVE_DIRENT_H)
# define HAVE_DIRENT_H
# endif /* !HAVE_DIRENT_H */
#endif /* !SHELL && (_POSIX_VERSION || USGr3) */
#if defined (HAVE_DIRENT_H)
# include <dirent.h>
# define D_NAMLEN(d) strlen ((d)->d_name)
#else /* !HAVE_DIRENT_H */
# define D_NAMLEN(d) ((d)->d_namlen)
# if defined (USG)
# if defined (Xenix)
# include <sys/ndir.h>
# else /* !Xenix (but USG...) */
# include "ndir.h"
# endif /* !Xenix */
# else /* !USG */
# include <sys/dir.h>
# endif /* !USG */
# if !defined (dirent)
# define dirent direct
# endif /* !dirent */
#endif /* !HAVE_DIRENT_H */
#if defined (USG) && defined (TIOCGWINSZ) && !defined (Linux)
# if defined (HAVE_SYS_STREAM_H)
# include <sys/stream.h>
# endif /* HAVE_SYS_STREAM_H */
# if defined (HAVE_SYS_PTEM_H)
# include <sys/ptem.h>
# endif /* HAVE_SYS_PTEM_H */
# if defined (HAVE_SYS_PTE_H)
# include <sys/pte.h>
# endif /* HAVE_SYS_PTE_H */
#endif /* USG && TIOCGWINSZ && !Linux */
/* Posix macro to check file in statbuf for directory-ness.
This requires that <sys/stat.h> be included before this test. */
#if defined (S_IFDIR) && !defined (S_ISDIR)
# define S_ISDIR(m) (((m)&S_IFMT) == S_IFDIR)
#endif
/* Decide which flavor of the header file describing the C library
string functions to include and include it. */
#if defined (USG) || defined (NeXT)
# if !defined (HAVE_STRING_H)
# define HAVE_STRING_H
# endif /* !HAVE_STRING_H */
#endif /* USG || NeXT */
#if defined (HAVE_STRING_H)
# include <string.h>
#else /* !HAVE_STRING_H */
# include <strings.h>
#endif /* !HAVE_STRING_H */
#if !defined (strchr) && !defined (__STDC__)
extern char *strchr (), *strrchr ();
#endif /* !strchr && !__STDC__ */
#if defined (HAVE_VARARGS_H)
# include <varargs.h>
#endif /* HAVE_VARARGS_H */
/* This is needed to include support for TIOCGWINSZ and window resizing. */
#if defined (OSF1) || defined (BSD386) || defined (NetBSD) || \
defined (__BSD_4_4__) || defined (FreeBSD) || defined (_386BSD) || \
defined (AIX)
# define GWINSZ_IN_SYS_IOCTL
#endif
/* Define _POSIX_VDISABLE if we are not using the `new' tty driver and
it is not already defined. It is used both to determine if a
special character is disabled and to disable certain special
characters. Posix systems should set to 0, USG systems to -1. */
#if !defined (NEW_TTY_DRIVER) && !defined (_POSIX_VDISABLE)
# if defined (_SVR4_VDISABLE)
# define _POSIX_VDISABLE _SVR4_VDISABLE
# else
# if defined (_POSIX_VERSION)
# define _POSIX_VDISABLE 0
# else /* !_POSIX_VERSION */
# define _POSIX_VDISABLE -1
# endif /* !_POSIX_VERSION */
# endif /* !_SVR4_VDISABLE */
#endif /* !NEW_TTY_DRIVER && !_POSIX_VDISABLE */
#if !defined (emacs_mode)
# define no_mode -1
# define vi_mode 0
# define emacs_mode 1
#endif
/* If you cast map[key].function to type (Keymap) on a Cray,
the compiler takes the value of map[key].function and
divides it by 4 to convert between pointer types (pointers
to functions and pointers to structs are different sizes).
This is not what is wanted. */
#if defined (CRAY)
# define FUNCTION_TO_KEYMAP(map, key) (Keymap)((int)map[key].function)
# define KEYMAP_TO_FUNCTION(data) (Function *)((int)(data))
#else
# define FUNCTION_TO_KEYMAP(map, key) (Keymap)(map[key].function)
# define KEYMAP_TO_FUNCTION(data) (Function *)(data)
#endif
#ifndef savestring
extern char *xmalloc ();
#define savestring(x) strcpy (xmalloc (1 + strlen (x)), (x))
#endif
/* Possible values for _rl_bell_preference. */
#define NO_BELL 0
#define AUDIBLE_BELL 1
#define VISIBLE_BELL 2
/* CONFIGURATION SECTION */
#include "rlconf.h"
#endif /* !_RLDEFS_H */

705
lib/readline/rltty.c Normal file
View file

@ -0,0 +1,705 @@
/* rltty.c -- functions to prepare and restore the terminal for readline's
use. */
/* Copyright (C) 1992 Free Software Foundation, Inc.
This file is part of the GNU Readline Library, a library for
reading lines of text with interactive input and history editing.
The GNU Readline Library is free software; you can redistribute it
and/or modify it under the terms of the GNU General Public License
as published by the Free Software Foundation; either version 1, or
(at your option) any later version.
The GNU Readline Library is distributed in the hope that it will be
useful, but WITHOUT ANY WARRANTY; without even the implied warranty
of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
The GNU General Public License is often shipped with GNU software, and
is generally kept in a file called COPYING or LICENSE. If you do not
have a copy of the license, write to the Free Software Foundation,
675 Mass Ave, Cambridge, MA 02139, USA. */
#define READLINE_LIBRARY
#if defined (HAVE_CONFIG_H)
# include "config.h"
#endif
#include <sys/types.h>
#include <signal.h>
#include <errno.h>
#include <stdio.h>
#if defined (HAVE_UNISTD_H)
# include <unistd.h>
#endif /* HAVE_UNISTD_H */
#include "rldefs.h"
#include "readline.h"
#if !defined (errno)
extern int errno;
#endif /* !errno */
extern int readline_echoing_p;
extern int _rl_eof_char;
#if defined (__GO32__)
# include <sys/pc.h>
# undef HANDLE_SIGNALS
#endif /* __GO32__ */
/* **************************************************************** */
/* */
/* Signal Management */
/* */
/* **************************************************************** */
#if defined (HAVE_POSIX_SIGNALS)
static sigset_t sigint_set, sigint_oset;
#else /* !HAVE_POSIX_SIGNALS */
# if defined (HAVE_BSD_SIGNALS)
static int sigint_oldmask;
# endif /* HAVE_BSD_SIGNALS */
#endif /* !HAVE_POSIX_SIGNALS */
static int sigint_blocked = 0;
/* Cause SIGINT to not be delivered until the corresponding call to
release_sigint(). */
static void
block_sigint ()
{
if (sigint_blocked)
return;
#if defined (HAVE_POSIX_SIGNALS)
sigemptyset (&sigint_set);
sigemptyset (&sigint_oset);
sigaddset (&sigint_set, SIGINT);
sigprocmask (SIG_BLOCK, &sigint_set, &sigint_oset);
#else /* !HAVE_POSIX_SIGNALS */
# if defined (HAVE_BSD_SIGNALS)
sigint_oldmask = sigblock (sigmask (SIGINT));
# else /* !HAVE_BSD_SIGNALS */
# if defined (HAVE_USG_SIGHOLD)
sighold (SIGINT);
# endif /* HAVE_USG_SIGHOLD */
# endif /* !HAVE_BSD_SIGNALS */
#endif /* !HAVE_POSIX_SIGNALS */
sigint_blocked = 1;
}
/* Allow SIGINT to be delivered. */
static void
release_sigint ()
{
if (!sigint_blocked)
return;
#if defined (HAVE_POSIX_SIGNALS)
sigprocmask (SIG_SETMASK, &sigint_oset, (sigset_t *)NULL);
#else
# if defined (HAVE_BSD_SIGNALS)
sigsetmask (sigint_oldmask);
# else /* !HAVE_BSD_SIGNALS */
# if defined (HAVE_USG_SIGHOLD)
sigrelse (SIGINT);
# endif /* HAVE_USG_SIGHOLD */
# endif /* !HAVE_BSD_SIGNALS */
#endif /* !HAVE_POSIX_SIGNALS */
sigint_blocked = 0;
}
/* **************************************************************** */
/* */
/* Controlling the Meta Key and Keypad */
/* */
/* **************************************************************** */
extern int term_has_meta;
extern char *term_mm;
extern char *term_mo;
extern char *term_ks;
extern char *term_ke;
static int
outchar (c)
int c;
{
return putc (c, rl_outstream);
}
/* Turn on/off the meta key depending on ON. */
static void
control_meta_key (on)
int on;
{
if (term_has_meta)
{
if (on && term_mm)
tputs (term_mm, 1, outchar);
else if (!on && term_mo)
tputs (term_mo, 1, outchar);
}
}
#if 0
static void
control_keypad (on)
int on;
{
if (on && term_ks)
tputs (term_ks, 1, outchar);
else if (!on && term_ke)
tputs (term_ke, 1, outchar);
}
#endif
/* **************************************************************** */
/* */
/* Saving and Restoring the TTY */
/* */
/* **************************************************************** */
/* Non-zero means that the terminal is in a prepped state. */
static int terminal_prepped = 0;
/* If non-zero, means that this process has called tcflow(fd, TCOOFF)
and output is suspended. */
#if defined (__ksr1__)
static int ksrflow = 0;
#endif
#if defined (NEW_TTY_DRIVER)
/* Values for the `flags' field of a struct bsdtty. This tells which
elements of the struct bsdtty have been fetched from the system and
are valid. */
#define SGTTY_SET 0x01
#define LFLAG_SET 0x02
#define TCHARS_SET 0x04
#define LTCHARS_SET 0x08
struct bsdtty {
struct sgttyb sgttyb; /* Basic BSD tty driver information. */
int lflag; /* Local mode flags, like LPASS8. */
#if defined (TIOCGETC)
struct tchars tchars; /* Terminal special characters, including ^S and ^Q. */
#endif
#if defined (TIOCGLTC)
struct ltchars ltchars; /* 4.2 BSD editing characters */
#endif
int flags; /* Bitmap saying which parts of the struct are valid. */
};
#define TIOTYPE struct bsdtty
static TIOTYPE otio;
static int
get_tty_settings (tty, tiop)
int tty;
TIOTYPE *tiop;
{
#if !defined (SHELL) && defined (TIOCGWINSZ)
struct winsize w;
if (ioctl (tty, TIOCGWINSZ, &w) == 0)
(void) ioctl (tty, TIOCSWINSZ, &w);
#endif
tiop->flags = tiop->lflag = 0;
ioctl (tty, TIOCGETP, &(tiop->sgttyb));
tiop->flags |= SGTTY_SET;
#if defined (TIOCLGET)
ioctl (tty, TIOCLGET, &(tiop->lflag));
tiop->flags |= LFLAG_SET;
#endif
#if defined (TIOCGETC)
ioctl (tty, TIOCGETC, &(tiop->tchars));
tiop->flags |= TCHARS_SET;
#endif
#if defined (TIOCGLTC)
ioctl (tty, TIOCGLTC, &(tiop->ltchars));
tiop->flags |= LTCHARS_SET;
#endif
return 0;
}
set_tty_settings (tty, tiop)
int tty;
TIOTYPE *tiop;
{
if (tiop->flags & SGTTY_SET)
{
ioctl (tty, TIOCSETN, &(tiop->sgttyb));
tiop->flags &= ~SGTTY_SET;
}
readline_echoing_p = 1;
#if defined (TIOCLSET)
if (tiop->flags & LFLAG_SET)
{
ioctl (tty, TIOCLSET, &(tiop->lflag));
tiop->flags &= ~LFLAG_SET;
}
#endif
#if defined (TIOCSETC)
if (tiop->flags & TCHARS_SET)
{
ioctl (tty, TIOCSETC, &(tiop->tchars));
tiop->flags &= ~TCHARS_SET;
}
#endif
#if defined (TIOCSLTC)
if (tiop->flags & LTCHARS_SET)
{
ioctl (tty, TIOCSLTC, &(tiop->ltchars));
tiop->flags &= ~LTCHARS_SET;
}
#endif
return 0;
}
static void
prepare_terminal_settings (meta_flag, otio, tiop)
int meta_flag;
TIOTYPE otio, *tiop;
{
#if !defined (__GO32__)
readline_echoing_p = (otio.sgttyb.sg_flags & ECHO);
/* Copy the original settings to the structure we're going to use for
our settings. */
tiop->sgttyb = otio.sgttyb;
tiop->lflag = otio.lflag;
#if defined (TIOCGETC)
tiop->tchars = otio.tchars;
#endif
#if defined (TIOCGLTC)
tiop->ltchars = otio.ltchars;
#endif
tiop->flags = otio.flags;
/* First, the basic settings to put us into character-at-a-time, no-echo
input mode. */
tiop->sgttyb.sg_flags &= ~(ECHO | CRMOD);
tiop->sgttyb.sg_flags |= CBREAK;
/* If this terminal doesn't care how the 8th bit is used, then we can
use it for the meta-key. If only one of even or odd parity is
specified, then the terminal is using parity, and we cannot. */
#if !defined (ANYP)
# define ANYP (EVENP | ODDP)
#endif
if (((otio.sgttyb.sg_flags & ANYP) == ANYP) ||
((otio.sgttyb.sg_flags & ANYP) == 0))
{
tiop->sgttyb.sg_flags |= ANYP;
/* Hack on local mode flags if we can. */
#if defined (TIOCLGET)
# if defined (LPASS8)
tiop->lflag |= LPASS8;
# endif /* LPASS8 */
#endif /* TIOCLGET */
}
#if defined (TIOCGETC)
# if defined (USE_XON_XOFF)
/* Get rid of terminal output start and stop characters. */
tiop->tchars.t_stopc = -1; /* C-s */
tiop->tchars.t_startc = -1; /* C-q */
/* If there is an XON character, bind it to restart the output. */
if (otio.tchars.t_startc != -1)
rl_bind_key (otio.tchars.t_startc, rl_restart_output);
# endif /* USE_XON_XOFF */
/* If there is an EOF char, bind _rl_eof_char to it. */
if (otio.tchars.t_eofc != -1)
_rl_eof_char = otio.tchars.t_eofc;
# if defined (NO_KILL_INTR)
/* Get rid of terminal-generated SIGQUIT and SIGINT. */
tiop->tchars.t_quitc = -1; /* C-\ */
tiop->tchars.t_intrc = -1; /* C-c */
# endif /* NO_KILL_INTR */
#endif /* TIOCGETC */
#if defined (TIOCGLTC)
/* Make the interrupt keys go away. Just enough to make people happy. */
tiop->ltchars.t_dsuspc = -1; /* C-y */
tiop->ltchars.t_lnextc = -1; /* C-v */
#endif /* TIOCGLTC */
#endif /* !__GO32__ */
}
#else /* !defined (NEW_TTY_DRIVER) */
#if !defined (VMIN)
# define VMIN VEOF
#endif
#if !defined (VTIME)
# define VTIME VEOL
#endif
#if defined (TERMIOS_TTY_DRIVER)
# define TIOTYPE struct termios
# define DRAIN_OUTPUT(fd) tcdrain (fd)
# define GETATTR(tty, tiop) (tcgetattr (tty, tiop))
# define SETATTR(tty, tiop) (tcsetattr (tty, TCSANOW, tiop))
#else
# define TIOTYPE struct termio
# define DRAIN_OUTPUT(fd)
# define GETATTR(tty, tiop) (ioctl (tty, TCGETA, tiop))
# define SETATTR(tty, tiop) (ioctl (tty, TCSETA, tiop))
#endif /* !TERMIOS_TTY_DRIVER */
static TIOTYPE otio;
#if defined (FLUSHO)
# define OUTPUT_BEING_FLUSHED(tp) (tp->c_lflag & FLUSHO)
#else
# define OUTPUT_BEING_FLUSHED(tp) 0
#endif
static int
get_tty_settings (tty, tiop)
int tty;
TIOTYPE *tiop;
{
int ioctl_ret;
#if !defined (SHELL) && defined (TIOCGWINSZ)
struct winsize w;
if (ioctl (tty, TIOCGWINSZ, &w) == 0)
(void) ioctl (tty, TIOCSWINSZ, &w);
#endif
/* Keep looping if output is being flushed after a ^O (or whatever
the flush character is). */
while ((ioctl_ret = GETATTR (tty, tiop)) < 0 || OUTPUT_BEING_FLUSHED (tiop))
{
if (ioctl_ret < 0 && errno != EINTR)
return -1;
if (OUTPUT_BEING_FLUSHED (tiop))
continue;
errno = 0;
}
return 0;
}
static int
set_tty_settings (tty, tiop)
int tty;
TIOTYPE *tiop;
{
while (SETATTR (tty, tiop) < 0)
{
if (errno != EINTR)
return -1;
errno = 0;
}
#if 0
#if defined (TERMIOS_TTY_DRIVER)
# if defined (__ksr1__)
if (ksrflow)
{
ksrflow = 0;
tcflow (tty, TCOON);
}
# else /* !ksr1 */
tcflow (tty, TCOON); /* Simulate a ^Q. */
# endif /* !ksr1 */
#else
ioctl (tty, TCXONC, 1); /* Simulate a ^Q. */
#endif /* !TERMIOS_TTY_DRIVER */
#endif
return 0;
}
static void
prepare_terminal_settings (meta_flag, otio, tiop)
int meta_flag;
TIOTYPE otio, *tiop;
{
readline_echoing_p = (otio.c_lflag & ECHO);
tiop->c_lflag &= ~(ICANON | ECHO);
if ((unsigned char) otio.c_cc[VEOF] != (unsigned char) _POSIX_VDISABLE)
_rl_eof_char = otio.c_cc[VEOF];
#if defined (USE_XON_XOFF)
#if defined (IXANY)
tiop->c_iflag &= ~(IXON | IXOFF | IXANY);
#else
/* `strict' Posix systems do not define IXANY. */
tiop->c_iflag &= ~(IXON | IXOFF);
#endif /* IXANY */
#endif /* USE_XON_XOFF */
/* Only turn this off if we are using all 8 bits. */
if (((tiop->c_cflag & CSIZE) == CS8) || meta_flag)
tiop->c_iflag &= ~(ISTRIP | INPCK);
/* Make sure we differentiate between CR and NL on input. */
tiop->c_iflag &= ~(ICRNL | INLCR);
#if !defined (HANDLE_SIGNALS)
tiop->c_lflag &= ~ISIG;
#else
tiop->c_lflag |= ISIG;
#endif
tiop->c_cc[VMIN] = 1;
tiop->c_cc[VTIME] = 0;
#if defined (FLUSHO)
if (OUTPUT_BEING_FLUSHED (tiop))
{
tiop->c_lflag &= ~FLUSHO;
otio.c_lflag &= ~FLUSHO;
}
#endif
/* Turn off characters that we need on Posix systems with job control,
just to be sure. This includes ^Y and ^V. This should not really
be necessary. */
#if defined (TERMIOS_TTY_DRIVER) && defined (_POSIX_VDISABLE)
#if defined (VLNEXT)
tiop->c_cc[VLNEXT] = _POSIX_VDISABLE;
#endif
#if defined (VDSUSP)
tiop->c_cc[VDSUSP] = _POSIX_VDISABLE;
#endif
#endif /* TERMIOS_TTY_DRIVER && _POSIX_VDISABLE */
}
#endif /* NEW_TTY_DRIVER */
/* Put the terminal in CBREAK mode so that we can detect key presses. */
void
rl_prep_terminal (meta_flag)
int meta_flag;
{
#if !defined (__GO32__)
int tty = fileno (rl_instream);
TIOTYPE tio;
if (terminal_prepped)
return;
/* Try to keep this function from being INTerrupted. */
block_sigint ();
if (get_tty_settings (tty, &tio) < 0)
{
release_sigint ();
return;
}
otio = tio;
prepare_terminal_settings (meta_flag, otio, &tio);
if (set_tty_settings (tty, &tio) < 0)
{
release_sigint ();
return;
}
control_meta_key (1);
#if 0
control_keypad (1);
#endif
fflush (rl_outstream);
terminal_prepped = 1;
release_sigint ();
#endif /* !__GO32__ */
}
/* Restore the terminal's normal settings and modes. */
void
rl_deprep_terminal ()
{
#if !defined (__GO32__)
int tty = fileno (rl_instream);
if (!terminal_prepped)
return;
/* Try to keep this function from being INTerrupted. */
block_sigint ();
control_meta_key (0);
#if 0
control_keypad (0);
#endif
fflush (rl_outstream);
if (set_tty_settings (tty, &otio) < 0)
{
release_sigint ();
return;
}
terminal_prepped = 0;
release_sigint ();
#endif /* !__GO32__ */
}
/* **************************************************************** */
/* */
/* Bogus Flow Control */
/* */
/* **************************************************************** */
rl_restart_output (count, key)
int count, key;
{
int fildes = fileno (rl_outstream);
#if defined (TIOCSTART)
#if defined (apollo)
ioctl (&fildes, TIOCSTART, 0);
#else
ioctl (fildes, TIOCSTART, 0);
#endif /* apollo */
#else /* !TIOCSTART */
# if defined (TERMIOS_TTY_DRIVER)
# if defined (__ksr1__)
if (ksrflow)
{
ksrflow = 0;
tcflow (fildes, TCOON);
}
# else /* !ksr1 */
tcflow (fildes, TCOON); /* Simulate a ^Q. */
# endif /* !ksr1 */
# else /* !TERMIOS_TTY_DRIVER */
# if defined (TCXONC)
ioctl (fildes, TCXONC, TCOON);
# endif /* TCXONC */
# endif /* !TERMIOS_TTY_DRIVER */
#endif /* !TIOCSTART */
return 0;
}
rl_stop_output (count, key)
int count, key;
{
int fildes = fileno (rl_instream);
#if defined (TIOCSTOP)
# if defined (apollo)
ioctl (&fildes, TIOCSTOP, 0);
# else
ioctl (fildes, TIOCSTOP, 0);
# endif /* apollo */
#else /* !TIOCSTOP */
# if defined (TERMIOS_TTY_DRIVER)
# if defined (__ksr1__)
ksrflow = 1;
# endif /* ksr1 */
tcflow (fildes, TCOOFF);
# else
# if defined (TCXONC)
ioctl (fildes, TCXONC, TCOON);
# endif /* TCXONC */
# endif /* !TERMIOS_TTY_DRIVER */
#endif /* !TIOCSTOP */
return 0;
}
/* **************************************************************** */
/* */
/* Default Key Bindings */
/* */
/* **************************************************************** */
void
rltty_set_default_bindings (kmap)
Keymap kmap;
{
TIOTYPE ttybuff;
int tty = fileno (rl_instream);
#if defined (NEW_TTY_DRIVER)
#define SET_SPECIAL(sc, func) \
do \
{ \
int ic; \
ic = sc; \
if (ic != -1 && kmap[ic].type == ISFUNC) \
kmap[ic].function = func; \
} \
while (0)
if (get_tty_settings (tty, &ttybuff) == 0)
{
if (ttybuff.flags & SGTTY_SET)
{
SET_SPECIAL (ttybuff.sgttyb.sg_erase, rl_rubout);
SET_SPECIAL (ttybuff.sgttyb.sg_kill, rl_unix_line_discard);
}
# if defined (TIOCGLTC)
if (ttybuff.flags & LTCHARS_SET)
{
SET_SPECIAL (ttybuff.ltchars.t_werasc, rl_unix_word_rubout);
SET_SPECIAL (ttybuff.ltchars.t_lnextc, rl_quoted_insert);
}
# endif /* TIOCGLTC */
}
#else /* !NEW_TTY_DRIVER */
#define SET_SPECIAL(sc, func) \
do \
{ \
unsigned char uc; \
uc = ttybuff.c_cc[sc]; \
if (uc != (unsigned char)_POSIX_VDISABLE && kmap[uc].type == ISFUNC) \
kmap[uc].function = func; \
} \
while (0)
if (get_tty_settings (tty, &ttybuff) == 0)
{
SET_SPECIAL (VERASE, rl_rubout);
SET_SPECIAL (VKILL, rl_unix_line_discard);
# if defined (VLNEXT) && defined (TERMIOS_TTY_DRIVER)
SET_SPECIAL (VLNEXT, rl_quoted_insert);
# endif /* VLNEXT && TERMIOS_TTY_DRIVER */
# if defined (VWERASE) && defined (TERMIOS_TTY_DRIVER)
SET_SPECIAL (VWERASE, rl_unix_word_rubout);
# endif /* VWERASE && TERMIOS_TTY_DRIVER */
}
#endif /* !NEW_TTY_DRIVER */
}

370
lib/readline/search.c Normal file
View file

@ -0,0 +1,370 @@
/* search.c - code for non-incremental searching in emacs and vi modes. */
/* Copyright (C) 1992 Free Software Foundation, Inc.
This file is part of the Readline Library (the Library), a set of
routines for providing Emacs style line input to programs that ask
for it.
The Library is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 1, or (at your option)
any later version.
The Library is distributed in the hope that it will be useful, but
WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
General Public License for more details.
The GNU General Public License is often shipped with GNU software, and
is generally kept in a file called COPYING or LICENSE. If you do not
have a copy of the license, write to the Free Software Foundation,
675 Mass Ave, Cambridge, MA 02139, USA. */
#define READLINE_LIBRARY
#include <sys/types.h>
#include <stdio.h>
#if defined (HAVE_UNISTD_H)
# include <unistd.h>
#endif
#include "rldefs.h"
#include "readline.h"
#include "history.h"
#define STREQ(a, b) (((a)[0] == (b)[0]) && (strcmp ((a), (b)) == 0))
#define STREQN(a, b, n) (((a)[0] == (b)[0]) && (strncmp ((a), (b), (n)) == 0))
#define abs(x) (((x) > 0) ? (x) : -(x))
extern char *xmalloc (), *xrealloc ();
/* Variables imported from readline.c */
extern int rl_point, rl_end, rl_line_buffer_len;
extern Keymap _rl_keymap;
extern int rl_editing_mode;
extern char *rl_prompt;
extern char *rl_line_buffer;
extern HIST_ENTRY *saved_line_for_history;
extern Function *rl_last_func;
/* Functions imported from the rest of the library. */
extern int _rl_free_history_entry ();
static char *noninc_search_string = (char *) NULL;
static int noninc_history_pos = 0;
static char *prev_line_found = (char *) NULL;
/* Search the history list for STRING starting at absolute history position
POS. If STRING begins with `^', the search must match STRING at the
beginning of a history line, otherwise a full substring match is performed
for STRING. DIR < 0 means to search backwards through the history list,
DIR >= 0 means to search forward. */
static int
noninc_search_from_pos (string, pos, dir)
char *string;
int pos, dir;
{
int ret, old;
old = where_history ();
history_set_pos (pos);
if (*string == '^')
ret = history_search_prefix (string + 1, dir);
else
ret = history_search (string, dir);
if (ret != -1)
ret = where_history ();
history_set_pos (old);
return (ret);
}
/* Search for a line in the history containing STRING. If DIR is < 0, the
search is backwards through previous entries, else through subsequent
entries. */
static void
noninc_dosearch (string, dir)
char *string;
int dir;
{
int oldpos, pos;
HIST_ENTRY *entry;
if (string == 0 || *string == '\0' || noninc_history_pos < 0)
{
ding ();
return;
}
pos = noninc_search_from_pos (string, noninc_history_pos + dir, dir);
if (pos == -1)
{
/* Search failed, current history position unchanged. */
maybe_unsave_line ();
rl_clear_message ();
rl_point = 0;
ding ();
return;
}
noninc_history_pos = pos;
oldpos = where_history ();
history_set_pos (noninc_history_pos);
entry = current_history ();
#if defined (VI_MODE)
if (rl_editing_mode != vi_mode)
#endif
history_set_pos (oldpos);
{
int line_len;
line_len = strlen (entry->line);
if (line_len >= rl_line_buffer_len)
rl_extend_line_buffer (line_len);
strcpy (rl_line_buffer, entry->line);
}
rl_undo_list = (UNDO_LIST *)entry->data;
rl_end = strlen (rl_line_buffer);
rl_point = 0;
rl_clear_message ();
if (saved_line_for_history)
_rl_free_history_entry (saved_line_for_history);
saved_line_for_history = (HIST_ENTRY *)NULL;
}
/* Search non-interactively through the history list. DIR < 0 means to
search backwards through the history of previous commands; otherwise
the search is for commands subsequent to the current position in the
history list. PCHAR is the character to use for prompting when reading
the search string; if not specified (0), it defaults to `:'. */
static void
noninc_search (dir, pchar)
int dir;
int pchar;
{
int saved_point, c, pmtlen;
char *p;
maybe_save_line ();
saved_point = rl_point;
/* Use the line buffer to read the search string. */
rl_line_buffer[0] = 0;
rl_end = rl_point = 0;
/* XXX - this needs fixing to work with the prompt expansion stuff - XXX */
pmtlen = (rl_prompt && *rl_prompt) ? strlen (rl_prompt) : 0;
p = xmalloc (2 + pmtlen);
if (pmtlen)
strcpy (p, rl_prompt);
p[pmtlen] = pchar ? pchar : ':';
p[pmtlen + 1] = '\0';
rl_message (p, 0, 0);
free (p);
/* Read the search string. */
while (c = rl_read_key ())
{
switch (c)
{
case CTRL('H'):
case RUBOUT:
if (rl_point == 0)
{
maybe_unsave_line ();
rl_clear_message ();
rl_point = saved_point;
return;
}
rl_rubout (1);
break;
case CTRL('W'):
rl_unix_word_rubout (1, c);
break;
case CTRL('U'):
rl_unix_line_discard (1, c);
break;
case RETURN:
case NEWLINE:
goto dosearch;
/* NOTREACHED */
break;
case CTRL('C'):
case CTRL('G'):
maybe_unsave_line ();
rl_clear_message ();
rl_point = saved_point;
ding ();
return;
default:
rl_insert (1, c);
break;
}
rl_redisplay ();
}
dosearch:
/* If rl_point == 0, we want to re-use the previous search string and
start from the saved history position. If there's no previous search
string, punt. */
if (rl_point == 0)
{
if (!noninc_search_string)
{
ding ();
return;
}
}
else
{
/* We want to start the search from the current history position. */
noninc_history_pos = where_history ();
if (noninc_search_string)
free (noninc_search_string);
noninc_search_string = savestring (rl_line_buffer);
}
noninc_dosearch (noninc_search_string, dir);
}
/* Search forward through the history list for a string. If the vi-mode
code calls this, KEY will be `?'. */
rl_noninc_forward_search (count, key)
int count, key;
{
if (key == '?')
noninc_search (1, '?');
else
noninc_search (1, 0);
return 0;
}
/* Reverse search the history list for a string. If the vi-mode code
calls this, KEY will be `/'. */
rl_noninc_reverse_search (count, key)
int count, key;
{
if (key == '/')
noninc_search (-1, '/');
else
noninc_search (-1, 0);
return 0;
}
/* Search forward through the history list for the last string searched
for. If there is no saved search string, abort. */
rl_noninc_forward_search_again (count, key)
int count, key;
{
if (!noninc_search_string)
{
ding ();
return (-1);
}
noninc_dosearch (noninc_search_string, 1);
return 0;
}
/* Reverse search in the history list for the last string searched
for. If there is no saved search string, abort. */
rl_noninc_reverse_search_again (count, key)
int count, key;
{
if (!noninc_search_string)
{
ding ();
return (-1);
}
noninc_dosearch (noninc_search_string, -1);
return 0;
}
static int
rl_history_search_internal (count, direction)
int count, direction;
{
HIST_ENTRY *temp, *old_temp;
int line_len;
maybe_save_line ();
temp = old_temp = (HIST_ENTRY *)NULL;
while (count)
{
temp = (direction < 0) ? previous_history () : next_history ();
if (!temp)
break;
if (STREQN (rl_line_buffer, temp->line, rl_point))
{
/* Don't find multiple instances of the same line. */
if (prev_line_found && STREQ (prev_line_found, temp->line))
continue;
if (direction < 0)
old_temp = temp;
prev_line_found = temp->line;
count--;
}
}
if (!temp)
{
if (direction < 0 && old_temp)
temp = old_temp;
else
{
maybe_unsave_line ();
ding ();
return 1;
}
}
line_len = strlen (temp->line);
if (line_len >= rl_line_buffer_len)
rl_extend_line_buffer (line_len);
strcpy (rl_line_buffer, temp->line);
rl_undo_list = (UNDO_LIST *)temp->data;
rl_end = line_len;
return 0;
}
/* Search forward in the history for the string of characters
from the start of the line to rl_point. This is a non-incremental
search. */
int
rl_history_search_forward (count, ignore)
int count, ignore;
{
if (count == 0)
return (0);
if (rl_last_func != rl_history_search_forward)
prev_line_found = (char *)NULL;
return (rl_history_search_internal (abs (count), (count > 0) ? 1 : -1));
}
/* Search backward through the history for the string of characters
from the start of the line to rl_point. This is a non-incremental
search. */
int
rl_history_search_backward (count, ignore)
int count, ignore;
{
if (count == 0)
return (0);
if (rl_last_func != rl_history_search_backward)
prev_line_found = (char *)NULL;
return (rl_history_search_internal (abs (count), (count > 0) ? -1 : 1));
}

287
lib/readline/signals.c Normal file
View file

@ -0,0 +1,287 @@
/* signals.c -- signal handling support for readline. */
/* Copyright (C) 1987, 1989, 1992 Free Software Foundation, Inc.
This file is part of the GNU Readline Library, a library for
reading lines of text with interactive input and history editing.
The GNU Readline Library is free software; you can redistribute it
and/or modify it under the terms of the GNU General Public License
as published by the Free Software Foundation; either version 1, or
(at your option) any later version.
The GNU Readline Library is distributed in the hope that it will be
useful, but WITHOUT ANY WARRANTY; without even the implied warranty
of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
The GNU General Public License is often shipped with GNU software, and
is generally kept in a file called COPYING or LICENSE. If you do not
have a copy of the license, write to the Free Software Foundation,
675 Mass Ave, Cambridge, MA 02139, USA. */
#define READLINE_LIBRARY
#include <stdio.h>
#include <sys/types.h>
#include <fcntl.h>
#if !defined (NO_SYS_FILE)
# include <sys/file.h>
#endif /* !NO_SYS_FILE */
#include <signal.h>
#if defined (HAVE_UNISTD_H)
# include <unistd.h>
#endif /* HAVE_UNISTD_H */
#if defined (HAVE_STDLIB_H)
# include <stdlib.h>
#else
# include "ansi_stdlib.h"
#endif /* HAVE_STDLIB_H */
#include <errno.h>
/* Not all systems declare ERRNO in errno.h... and some systems #define it! */
#if !defined (errno)
extern int errno;
#endif /* !errno */
#include "posixstat.h"
/* System-specific feature definitions and include files. */
#include "rldefs.h"
#if defined (GWINSZ_IN_SYS_IOCTL)
# include <sys/ioctl.h>
#endif /* GWINSZ_IN_SYS_IOCTL */
/* Some standard library routines. */
#include "readline.h"
#include "history.h"
extern int readline_echoing_p;
extern int rl_pending_input;
extern int _rl_meta_flag;
extern void free_undo_list ();
#if defined (VOID_SIGHANDLER)
# define sighandler void
#else
# define sighandler int
#endif /* VOID_SIGHANDLER */
/* This typedef is equivalant to the one for Function; it allows us
to say SigHandler *foo = signal (SIGKILL, SIG_IGN); */
typedef sighandler SigHandler ();
#if defined (__GO32__)
# undef HANDLE_SIGNALS
#endif /* __GO32__ */
#if defined (STATIC_MALLOC)
static char *xmalloc (), *xrealloc ();
#else
extern char *xmalloc (), *xrealloc ();
#endif /* STATIC_MALLOC */
/* **************************************************************** */
/* */
/* Signal Handling */
/* */
/* **************************************************************** */
#if defined (SIGWINCH)
static SigHandler *old_sigwinch = (SigHandler *)NULL;
static sighandler
rl_handle_sigwinch (sig)
int sig;
{
if (readline_echoing_p)
{
_rl_set_screen_size (fileno (rl_instream), 1);
_rl_redisplay_after_sigwinch ();
}
if (old_sigwinch &&
old_sigwinch != (SigHandler *)SIG_IGN &&
old_sigwinch != (SigHandler *)SIG_DFL)
(*old_sigwinch) (sig);
#if !defined (VOID_SIGHANDLER)
return (0);
#endif /* VOID_SIGHANDLER */
}
#endif /* SIGWINCH */
#if defined (HANDLE_SIGNALS)
/* Interrupt handling. */
static SigHandler
*old_int = (SigHandler *)NULL,
*old_alrm = (SigHandler *)NULL;
#if !defined (SHELL)
static SigHandler
*old_tstp = (SigHandler *)NULL,
*old_ttou = (SigHandler *)NULL,
*old_ttin = (SigHandler *)NULL,
*old_cont = (SigHandler *)NULL;
#endif /* !SHELL */
/* Handle an interrupt character. */
static sighandler
rl_signal_handler (sig)
int sig;
{
#if defined (HAVE_POSIX_SIGNALS)
sigset_t set;
#else /* !HAVE_POSIX_SIGNALS */
# if defined (HAVE_BSD_SIGNALS)
long omask;
# endif /* HAVE_BSD_SIGNALS */
#endif /* !HAVE_POSIX_SIGNALS */
#if !defined (HAVE_BSD_SIGNALS) && !defined (HAVE_POSIX_SIGNALS)
/* Since the signal will not be blocked while we are in the signal
handler, ignore it until rl_clear_signals resets the catcher. */
if (sig == SIGINT)
signal (sig, SIG_IGN);
#endif /* !HAVE_BSD_SIGNALS */
switch (sig)
{
case SIGINT:
{
register HIST_ENTRY *entry;
free_undo_list ();
entry = current_history ();
if (entry)
entry->data = (char *)NULL;
}
_rl_kill_kbd_macro ();
rl_clear_message ();
rl_init_argument ();
#if defined (SIGTSTP)
case SIGTSTP:
case SIGTTOU:
case SIGTTIN:
#endif /* SIGTSTP */
case SIGALRM:
rl_clean_up_for_exit ();
rl_deprep_terminal ();
rl_clear_signals ();
rl_pending_input = 0;
#if defined (HAVE_POSIX_SIGNALS)
sigprocmask (SIG_BLOCK, (sigset_t *)NULL, &set);
sigdelset (&set, sig);
#else /* !HAVE_POSIX_SIGNALS */
# if defined (HAVE_BSD_SIGNALS)
omask = sigblock (0);
# endif /* HAVE_BSD_SIGNALS */
#endif /* !HAVE_POSIX_SIGNALS */
kill (getpid (), sig);
/* Let the signal that we just sent through. */
#if defined (HAVE_POSIX_SIGNALS)
sigprocmask (SIG_SETMASK, &set, (sigset_t *)NULL);
#else /* !HAVE_POSIX_SIGNALS */
# if defined (HAVE_BSD_SIGNALS)
sigsetmask (omask & ~(sigmask (sig)));
# endif /* HAVE_BSD_SIGNALS */
#endif /* !HAVE_POSIX_SIGNALS */
rl_prep_terminal (_rl_meta_flag);
rl_set_signals ();
}
#if !defined (VOID_SIGHANDLER)
return (0);
#endif /* !VOID_SIGHANDLER */
}
#if defined (HAVE_POSIX_SIGNALS)
static SigHandler *
rl_set_sighandler (sig, handler)
int sig;
SigHandler *handler;
{
struct sigaction act, oact;
act.sa_handler = handler;
act.sa_flags = 0;
sigemptyset (&act.sa_mask);
sigemptyset (&oact.sa_mask);
sigaction (sig, &act, &oact);
return (oact.sa_handler);
}
#else /* !HAVE_POSIX_SIGNALS */
# define rl_set_sighandler(sig, handler) (SigHandler *)signal (sig, handler)
#endif /* !HAVE_POSIX_SIGNALS */
rl_set_signals ()
{
old_int = (SigHandler *)rl_set_sighandler (SIGINT, rl_signal_handler);
if (old_int == (SigHandler *)SIG_IGN)
rl_set_sighandler (SIGINT, SIG_IGN);
old_alrm = (SigHandler *)rl_set_sighandler (SIGALRM, rl_signal_handler);
if (old_alrm == (SigHandler *)SIG_IGN)
rl_set_sighandler (SIGALRM, SIG_IGN);
#if !defined (SHELL)
#if defined (SIGTSTP)
old_tstp = (SigHandler *)rl_set_sighandler (SIGTSTP, rl_signal_handler);
if (old_tstp == (SigHandler *)SIG_IGN)
rl_set_sighandler (SIGTSTP, SIG_IGN);
#endif /* SIGTSTP */
#if defined (SIGTTOU)
old_ttou = (SigHandler *)rl_set_sighandler (SIGTTOU, rl_signal_handler);
old_ttin = (SigHandler *)rl_set_sighandler (SIGTTIN, rl_signal_handler);
if (old_tstp == (SigHandler *)SIG_IGN)
{
rl_set_sighandler (SIGTTOU, SIG_IGN);
rl_set_sighandler (SIGTTIN, SIG_IGN);
}
#endif /* SIGTTOU */
#endif /* !SHELL */
#if defined (SIGWINCH)
old_sigwinch =
(SigHandler *) rl_set_sighandler (SIGWINCH, rl_handle_sigwinch);
#endif /* SIGWINCH */
return 0;
}
rl_clear_signals ()
{
rl_set_sighandler (SIGINT, old_int);
rl_set_sighandler (SIGALRM, old_alrm);
#if !defined (SHELL)
#if defined (SIGTSTP)
rl_set_sighandler (SIGTSTP, old_tstp);
#endif
#if defined (SIGTTOU)
rl_set_sighandler (SIGTTOU, old_ttou);
rl_set_sighandler (SIGTTIN, old_ttin);
#endif /* SIGTTOU */
#endif /* !SHELL */
#if defined (SIGWINCH)
rl_set_sighandler (SIGWINCH, old_sigwinch);
#endif
return 0;
}
#endif /* HANDLE_SIGNALS */

380
lib/readline/tilde.c Normal file
View file

@ -0,0 +1,380 @@
/* tilde.c -- Tilde expansion code (~/foo := $HOME/foo). */
/* Copyright (C) 1988,1989 Free Software Foundation, Inc.
This file is part of GNU Readline, a library for reading lines
of text with interactive input and history editing.
Readline is free software; you can redistribute it and/or modify it
under the terms of the GNU General Public License as published by the
Free Software Foundation; either version 1, or (at your option) any
later version.
Readline is distributed in the hope that it will be useful, but
WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
General Public License for more details.
You should have received a copy of the GNU General Public License
along with Readline; see the file COPYING. If not, write to the Free
Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA. */
#if defined (HAVE_STRING_H)
# include <string.h>
#else /* !HAVE_STRING_H */
# include <strings.h>
#endif /* !HAVE_STRING_H */
#if defined (HAVE_STDLIB_H)
# include <stdlib.h>
#else
# include "ansi_stdlib.h"
#endif /* HAVE_STDLIB_H */
#include "tilde.h"
#include <sys/types.h>
#include <pwd.h>
#if defined (USG) && !defined (HAVE_GETPW_DECLS)
extern struct passwd *getpwuid (), *getpwnam ();
#endif /* USG && !defined (HAVE_GETPW_DECLS) */
#if !defined (savestring)
extern char *xmalloc ();
# ifndef strcpy
extern char *strcpy ();
# endif
#define savestring(x) strcpy (xmalloc (1 + strlen (x)), (x))
#endif /* !savestring */
#if !defined (NULL)
# if defined (__STDC__)
# define NULL ((void *) 0)
# else
# define NULL 0x0
# endif /* !__STDC__ */
#endif /* !NULL */
#if defined (TEST) || defined (STATIC_MALLOC)
static char *xmalloc (), *xrealloc ();
#else
extern char *xmalloc (), *xrealloc ();
#endif /* TEST || STATIC_MALLOC */
/* The default value of tilde_additional_prefixes. This is set to
whitespace preceding a tilde so that simple programs which do not
perform any word separation get desired behaviour. */
static char *default_prefixes[] =
{ " ~", "\t~", (char *)NULL };
/* The default value of tilde_additional_suffixes. This is set to
whitespace or newline so that simple programs which do not
perform any word separation get desired behaviour. */
static char *default_suffixes[] =
{ " ", "\n", (char *)NULL };
/* If non-null, this contains the address of a function to call if the
standard meaning for expanding a tilde fails. The function is called
with the text (sans tilde, as in "foo"), and returns a malloc()'ed string
which is the expansion, or a NULL pointer if there is no expansion. */
CPFunction *tilde_expansion_failure_hook = (CPFunction *)NULL;
/* When non-null, this is a NULL terminated array of strings which
are duplicates for a tilde prefix. Bash uses this to expand
`=~' and `:~'. */
char **tilde_additional_prefixes = default_prefixes;
/* When non-null, this is a NULL terminated array of strings which match
the end of a username, instead of just "/". Bash sets this to
`:' and `=~'. */
char **tilde_additional_suffixes = default_suffixes;
/* Find the start of a tilde expansion in STRING, and return the index of
the tilde which starts the expansion. Place the length of the text
which identified this tilde starter in LEN, excluding the tilde itself. */
static int
tilde_find_prefix (string, len)
char *string;
int *len;
{
register int i, j, string_len;
register char **prefixes = tilde_additional_prefixes;
string_len = strlen (string);
*len = 0;
if (!*string || *string == '~')
return (0);
if (prefixes)
{
for (i = 0; i < string_len; i++)
{
for (j = 0; prefixes[j]; j++)
{
if (strncmp (string + i, prefixes[j], strlen (prefixes[j])) == 0)
{
*len = strlen (prefixes[j]) - 1;
return (i + *len);
}
}
}
}
return (string_len);
}
/* Find the end of a tilde expansion in STRING, and return the index of
the character which ends the tilde definition. */
static int
tilde_find_suffix (string)
char *string;
{
register int i, j, string_len;
register char **suffixes = tilde_additional_suffixes;
string_len = strlen (string);
for (i = 0; i < string_len; i++)
{
if (string[i] == '/' || !string[i])
break;
for (j = 0; suffixes && suffixes[j]; j++)
{
if (strncmp (string + i, suffixes[j], strlen (suffixes[j])) == 0)
return (i);
}
}
return (i);
}
/* Return a new string which is the result of tilde expanding STRING. */
char *
tilde_expand (string)
char *string;
{
char *result, *tilde_expand_word ();
int result_size, result_index;
result_size = result_index = 0;
result = (char *)NULL;
/* Scan through STRING expanding tildes as we come to them. */
while (1)
{
register int start, end;
char *tilde_word, *expansion;
int len;
/* Make START point to the tilde which starts the expansion. */
start = tilde_find_prefix (string, &len);
/* Copy the skipped text into the result. */
if ((result_index + start + 1) > result_size)
result = (char *)xrealloc (result, 1 + (result_size += (start + 20)));
strncpy (result + result_index, string, start);
result_index += start;
/* Advance STRING to the starting tilde. */
string += start;
/* Make END be the index of one after the last character of the
username. */
end = tilde_find_suffix (string);
/* If both START and END are zero, we are all done. */
if (!start && !end)
break;
/* Expand the entire tilde word, and copy it into RESULT. */
tilde_word = (char *)xmalloc (1 + end);
strncpy (tilde_word, string, end);
tilde_word[end] = '\0';
string += end;
expansion = tilde_expand_word (tilde_word);
free (tilde_word);
len = strlen (expansion);
if ((result_index + len + 1) > result_size)
result = (char *)xrealloc (result, 1 + (result_size += (len + 20)));
strcpy (result + result_index, expansion);
result_index += len;
free (expansion);
}
result[result_index] = '\0';
return (result);
}
/* Do the work of tilde expansion on FILENAME. FILENAME starts with a
tilde. If there is no expansion, call tilde_expansion_failure_hook. */
char *
tilde_expand_word (filename)
char *filename;
{
char *dirname;
dirname = filename ? savestring (filename) : (char *)NULL;
if (dirname && *dirname == '~')
{
char *temp_name;
if (!dirname[1] || dirname[1] == '/')
{
/* Prepend $HOME to the rest of the string. */
char *temp_home = (char *)getenv ("HOME");
/* If there is no HOME variable, look up the directory in
the password database. */
if (!temp_home)
{
struct passwd *entry;
entry = getpwuid (getuid ());
if (entry)
temp_home = entry->pw_dir;
}
temp_name = xmalloc (1 + strlen (&dirname[1])
+ (temp_home ? strlen (temp_home) : 0));
temp_name[0] = '\0';
if (temp_home)
strcpy (temp_name, temp_home);
strcat (temp_name, dirname + 1);
free (dirname);
dirname = temp_name;
}
else
{
char *username;
struct passwd *user_entry;
int i;
username = xmalloc (strlen (dirname));
for (i = 1; dirname[i] && dirname[i] != '/'; i++)
username[i - 1] = dirname[i];
username[i - 1] = '\0';
if ((user_entry = getpwnam (username)) == 0)
{
/* If the calling program has a special syntax for
expanding tildes, and we couldn't find a standard
expansion, then let them try. */
if (tilde_expansion_failure_hook)
{
char *expansion;
expansion = (*tilde_expansion_failure_hook) (username);
if (expansion)
{
temp_name = xmalloc (1 + strlen (expansion)
+ strlen (&dirname[i]));
strcpy (temp_name, expansion);
strcat (temp_name, &dirname[i]);
free (expansion);
free (dirname);
dirname = temp_name;
}
}
/* We shouldn't report errors. */
}
else
{
temp_name = xmalloc (1 + strlen (user_entry->pw_dir)
+ strlen (&dirname[i]));
strcpy (temp_name, user_entry->pw_dir);
strcat (temp_name, &dirname[i]);
free (dirname);
dirname = temp_name;
}
endpwent ();
free (username);
}
}
return (dirname);
}
#if defined (TEST)
#undef NULL
#include <stdio.h>
main (argc, argv)
int argc;
char **argv;
{
char *result, line[512];
int done = 0;
while (!done)
{
printf ("~expand: ");
fflush (stdout);
if (!gets (line))
strcpy (line, "done");
if ((strcmp (line, "done") == 0) ||
(strcmp (line, "quit") == 0) ||
(strcmp (line, "exit") == 0))
{
done = 1;
break;
}
result = tilde_expand (line);
printf (" --> %s\n", result);
free (result);
}
exit (0);
}
static void memory_error_and_abort ();
static char *
xmalloc (bytes)
int bytes;
{
char *temp = (char *)malloc (bytes);
if (!temp)
memory_error_and_abort ();
return (temp);
}
static char *
xrealloc (pointer, bytes)
char *pointer;
int bytes;
{
char *temp;
if (!pointer)
temp = (char *)malloc (bytes);
else
temp = (char *)realloc (pointer, bytes);
if (!temp)
memory_error_and_abort ();
return (temp);
}
static void
memory_error_and_abort ()
{
fprintf (stderr, "readline: Out of virtual memory!\n");
abort ();
}
/*
* Local variables:
* compile-command: "gcc -g -DTEST -o tilde tilde.c"
* end:
*/
#endif /* TEST */

38
lib/readline/tilde.h Normal file
View file

@ -0,0 +1,38 @@
/* tilde.h: Externally available variables and function in libtilde.a. */
#if !defined (__TILDE_H__)
# define __TILDE_H__
/* Function pointers can be declared as (Function *)foo. */
#if !defined (__FUNCTION_DEF)
# define __FUNCTION_DEF
typedef int Function ();
typedef void VFunction ();
typedef char *CPFunction ();
typedef char **CPPFunction ();
#endif /* _FUNCTION_DEF */
/* If non-null, this contains the address of a function to call if the
standard meaning for expanding a tilde fails. The function is called
with the text (sans tilde, as in "foo"), and returns a malloc()'ed string
which is the expansion, or a NULL pointer if there is no expansion. */
extern CPFunction *tilde_expansion_failure_hook;
/* When non-null, this is a NULL terminated array of strings which
are duplicates for a tilde prefix. Bash uses this to expand
`=~' and `:~'. */
extern char **tilde_additional_prefixes;
/* When non-null, this is a NULL terminated array of strings which match
the end of a username, instead of just "/". Bash sets this to
`:' and `=~'. */
extern char **tilde_additional_suffixes;
/* Return a new string which is the result of tilde expanding STRING. */
extern char *tilde_expand ();
/* Do the work of tilde expansion on FILENAME. FILENAME starts with a
tilde. If there is no expansion, call tilde_expansion_failure_hook. */
extern char *tilde_expand_word ();
#endif /* __TILDE_H__ */

877
lib/readline/vi_keymap.c Normal file
View file

@ -0,0 +1,877 @@
/* vi_keymap.c -- the keymap for vi_mode in readline (). */
/* Copyright (C) 1987, 1989, 1992 Free Software Foundation, Inc.
This file is part of the GNU Readline Library, a library for
reading lines of text with interactive input and history editing.
The GNU Readline Library is free software; you can redistribute it
and/or modify it under the terms of the GNU General Public License
as published by the Free Software Foundation; either version 1, or
(at your option) any later version.
The GNU Readline Library is distributed in the hope that it will be
useful, but WITHOUT ANY WARRANTY; without even the implied warranty
of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
The GNU General Public License is often shipped with GNU software, and
is generally kept in a file called COPYING or LICENSE. If you do not
have a copy of the license, write to the Free Software Foundation,
675 Mass Ave, Cambridge, MA 02139, USA. */
#if !defined (BUFSIZ)
#include <stdio.h>
#endif /* !BUFSIZ */
#include "readline.h"
#if 0
extern KEYMAP_ENTRY_ARRAY vi_escape_keymap;
#endif
/* The keymap arrays for handling vi mode. */
KEYMAP_ENTRY_ARRAY vi_movement_keymap = {
/* The regular control keys come first. */
{ ISFUNC, (Function *)0x0 }, /* Control-@ */
{ ISFUNC, (Function *)0x0 }, /* Control-a */
{ ISFUNC, (Function *)0x0 }, /* Control-b */
{ ISFUNC, (Function *)0x0 }, /* Control-c */
{ ISFUNC, rl_vi_eof_maybe }, /* Control-d */
{ ISFUNC, rl_emacs_editing_mode }, /* Control-e */
{ ISFUNC, (Function *)0x0 }, /* Control-f */
{ ISFUNC, rl_abort }, /* Control-g */
{ ISFUNC, rl_backward }, /* Control-h */
{ ISFUNC, (Function *)0x0 }, /* Control-i */
{ ISFUNC, rl_newline }, /* Control-j */
{ ISFUNC, rl_kill_line }, /* Control-k */
{ ISFUNC, rl_clear_screen }, /* Control-l */
{ ISFUNC, rl_newline }, /* Control-m */
{ ISFUNC, rl_get_next_history }, /* Control-n */
{ ISFUNC, (Function *)0x0 }, /* Control-o */
{ ISFUNC, rl_get_previous_history }, /* Control-p */
{ ISFUNC, rl_quoted_insert }, /* Control-q */
{ ISFUNC, rl_reverse_search_history }, /* Control-r */
{ ISFUNC, rl_forward_search_history }, /* Control-s */
{ ISFUNC, rl_transpose_chars }, /* Control-t */
{ ISFUNC, rl_unix_line_discard }, /* Control-u */
{ ISFUNC, rl_quoted_insert }, /* Control-v */
{ ISFUNC, rl_unix_word_rubout }, /* Control-w */
{ ISFUNC, (Function *)0x0 }, /* Control-x */
{ ISFUNC, rl_yank }, /* Control-y */
{ ISFUNC, (Function *)0x0 }, /* Control-z */
{ ISFUNC, (Function *)0x0 }, /* Control-[ */ /* vi_escape_keymap */
{ ISFUNC, (Function *)0x0 }, /* Control-\ */
{ ISFUNC, (Function *)0x0 }, /* Control-] */
{ ISFUNC, (Function *)0x0 }, /* Control-^ */
{ ISFUNC, rl_undo_command }, /* Control-_ */
/* The start of printing characters. */
{ ISFUNC, rl_forward }, /* SPACE */
{ ISFUNC, (Function *)0x0 }, /* ! */
{ ISFUNC, (Function *)0x0 }, /* " */
{ ISFUNC, rl_vi_comment }, /* # */
{ ISFUNC, rl_end_of_line }, /* $ */
{ ISFUNC, rl_vi_match }, /* % */
{ ISFUNC, rl_vi_tilde_expand }, /* & */
{ ISFUNC, (Function *)0x0 }, /* ' */
{ ISFUNC, (Function *)0x0 }, /* ( */
{ ISFUNC, (Function *)0x0 }, /* ) */
{ ISFUNC, rl_vi_complete }, /* * */
{ ISFUNC, rl_get_next_history}, /* + */
{ ISFUNC, rl_vi_char_search }, /* , */
{ ISFUNC, rl_get_previous_history }, /* - */
{ ISFUNC, rl_vi_redo }, /* . */
{ ISFUNC, rl_vi_search }, /* / */
/* Regular digits. */
{ ISFUNC, rl_beg_of_line }, /* 0 */
{ ISFUNC, rl_vi_arg_digit }, /* 1 */
{ ISFUNC, rl_vi_arg_digit }, /* 2 */
{ ISFUNC, rl_vi_arg_digit }, /* 3 */
{ ISFUNC, rl_vi_arg_digit }, /* 4 */
{ ISFUNC, rl_vi_arg_digit }, /* 5 */
{ ISFUNC, rl_vi_arg_digit }, /* 6 */
{ ISFUNC, rl_vi_arg_digit }, /* 7 */
{ ISFUNC, rl_vi_arg_digit }, /* 8 */
{ ISFUNC, rl_vi_arg_digit }, /* 9 */
/* A little more punctuation. */
{ ISFUNC, (Function *)0x0 }, /* : */
{ ISFUNC, rl_vi_char_search }, /* ; */
{ ISFUNC, (Function *)0x0 }, /* < */
{ ISFUNC, rl_vi_complete }, /* = */
{ ISFUNC, (Function *)0x0 }, /* > */
{ ISFUNC, rl_vi_search }, /* ? */
{ ISFUNC, (Function *)0x0 }, /* @ */
/* Uppercase alphabet. */
{ ISFUNC, rl_vi_append_eol }, /* A */
{ ISFUNC, rl_vi_prev_word}, /* B */
{ ISFUNC, rl_vi_change_to }, /* C */
{ ISFUNC, rl_vi_delete_to }, /* D */
{ ISFUNC, rl_vi_end_word }, /* E */
{ ISFUNC, rl_vi_char_search }, /* F */
{ ISFUNC, rl_vi_fetch_history }, /* G */
{ ISFUNC, (Function *)0x0 }, /* H */
{ ISFUNC, rl_vi_insert_beg }, /* I */
{ ISFUNC, (Function *)0x0 }, /* J */
{ ISFUNC, (Function *)0x0 }, /* K */
{ ISFUNC, (Function *)0x0 }, /* L */
{ ISFUNC, (Function *)0x0 }, /* M */
{ ISFUNC, rl_vi_search_again }, /* N */
{ ISFUNC, (Function *)0x0 }, /* O */
{ ISFUNC, rl_vi_put }, /* P */
{ ISFUNC, (Function *)0x0 }, /* Q */
{ ISFUNC, rl_vi_replace }, /* R */
{ ISFUNC, rl_vi_subst }, /* S */
{ ISFUNC, rl_vi_char_search }, /* T */
{ ISFUNC, rl_revert_line }, /* U */
{ ISFUNC, (Function *)0x0 }, /* V */
{ ISFUNC, rl_vi_next_word }, /* W */
{ ISFUNC, rl_rubout }, /* X */
{ ISFUNC, rl_vi_yank_to }, /* Y */
{ ISFUNC, (Function *)0x0 }, /* Z */
/* Some more punctuation. */
{ ISFUNC, (Function *)0x0 }, /* [ */
{ ISFUNC, rl_vi_complete }, /* \ */
{ ISFUNC, (Function *)0x0 }, /* ] */
{ ISFUNC, rl_vi_first_print }, /* ^ */
{ ISFUNC, rl_vi_yank_arg }, /* _ */
{ ISFUNC, (Function *)0x0 }, /* ` */
/* Lowercase alphabet. */
{ ISFUNC, rl_vi_append_mode }, /* a */
{ ISFUNC, rl_vi_prev_word }, /* b */
{ ISFUNC, rl_vi_change_to }, /* c */
{ ISFUNC, rl_vi_delete_to }, /* d */
{ ISFUNC, rl_vi_end_word }, /* e */
{ ISFUNC, rl_vi_char_search }, /* f */
{ ISFUNC, (Function *)0x0 }, /* g */
{ ISFUNC, rl_backward }, /* h */
{ ISFUNC, rl_vi_insertion_mode }, /* i */
{ ISFUNC, rl_get_next_history }, /* j */
{ ISFUNC, rl_get_previous_history }, /* k */
{ ISFUNC, rl_forward }, /* l */
{ ISFUNC, (Function *)0x0 }, /* m */
{ ISFUNC, rl_vi_search_again }, /* n */
{ ISFUNC, (Function *)0x0 }, /* o */
{ ISFUNC, rl_vi_put }, /* p */
{ ISFUNC, (Function *)0x0 }, /* q */
{ ISFUNC, rl_vi_change_char }, /* r */
{ ISFUNC, rl_vi_subst }, /* s */
{ ISFUNC, rl_vi_char_search }, /* t */
{ ISFUNC, rl_undo_command }, /* u */
{ ISFUNC, (Function *)0x0 }, /* v */
{ ISFUNC, rl_vi_next_word }, /* w */
{ ISFUNC, rl_vi_delete }, /* x */
{ ISFUNC, rl_vi_yank_to }, /* y */
{ ISFUNC, (Function *)0x0 }, /* z */
/* Final punctuation. */
{ ISFUNC, (Function *)0x0 }, /* { */
{ ISFUNC, rl_vi_column }, /* | */
{ ISFUNC, (Function *)0x0 }, /* } */
{ ISFUNC, rl_vi_change_case }, /* ~ */
{ ISFUNC, (Function *)0x0 }, /* RUBOUT */
#if KEYMAP_SIZE > 128
/* Undefined keys. */
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 }
#endif /* KEYMAP_SIZE > 128 */
};
KEYMAP_ENTRY_ARRAY vi_insertion_keymap = {
/* The regular control keys come first. */
{ ISFUNC, (Function *)0x0 }, /* Control-@ */
{ ISFUNC, rl_insert }, /* Control-a */
{ ISFUNC, rl_insert }, /* Control-b */
{ ISFUNC, rl_insert }, /* Control-c */
{ ISFUNC, rl_vi_eof_maybe }, /* Control-d */
{ ISFUNC, rl_insert }, /* Control-e */
{ ISFUNC, rl_insert }, /* Control-f */
{ ISFUNC, rl_insert }, /* Control-g */
{ ISFUNC, rl_rubout }, /* Control-h */
{ ISFUNC, rl_complete }, /* Control-i */
{ ISFUNC, rl_newline }, /* Control-j */
{ ISFUNC, rl_insert }, /* Control-k */
{ ISFUNC, rl_insert }, /* Control-l */
{ ISFUNC, rl_newline }, /* Control-m */
{ ISFUNC, rl_insert }, /* Control-n */
{ ISFUNC, rl_insert }, /* Control-o */
{ ISFUNC, rl_insert }, /* Control-p */
{ ISFUNC, rl_insert }, /* Control-q */
{ ISFUNC, rl_reverse_search_history }, /* Control-r */
{ ISFUNC, rl_forward_search_history }, /* Control-s */
{ ISFUNC, rl_transpose_chars }, /* Control-t */
{ ISFUNC, rl_unix_line_discard }, /* Control-u */
{ ISFUNC, rl_quoted_insert }, /* Control-v */
{ ISFUNC, rl_unix_word_rubout }, /* Control-w */
{ ISFUNC, rl_insert }, /* Control-x */
{ ISFUNC, rl_yank }, /* Control-y */
{ ISFUNC, rl_insert }, /* Control-z */
{ ISFUNC, rl_vi_movement_mode }, /* Control-[ */
{ ISFUNC, rl_insert }, /* Control-\ */
{ ISFUNC, rl_insert }, /* Control-] */
{ ISFUNC, rl_insert }, /* Control-^ */
{ ISFUNC, rl_undo_command }, /* Control-_ */
/* The start of printing characters. */
{ ISFUNC, rl_insert }, /* SPACE */
{ ISFUNC, rl_insert }, /* ! */
{ ISFUNC, rl_insert }, /* " */
{ ISFUNC, rl_insert }, /* # */
{ ISFUNC, rl_insert }, /* $ */
{ ISFUNC, rl_insert }, /* % */
{ ISFUNC, rl_insert }, /* & */
{ ISFUNC, rl_insert }, /* ' */
{ ISFUNC, rl_insert }, /* ( */
{ ISFUNC, rl_insert }, /* ) */
{ ISFUNC, rl_insert }, /* * */
{ ISFUNC, rl_insert }, /* + */
{ ISFUNC, rl_insert }, /* , */
{ ISFUNC, rl_insert }, /* - */
{ ISFUNC, rl_insert }, /* . */
{ ISFUNC, rl_insert }, /* / */
/* Regular digits. */
{ ISFUNC, rl_insert }, /* 0 */
{ ISFUNC, rl_insert }, /* 1 */
{ ISFUNC, rl_insert }, /* 2 */
{ ISFUNC, rl_insert }, /* 3 */
{ ISFUNC, rl_insert }, /* 4 */
{ ISFUNC, rl_insert }, /* 5 */
{ ISFUNC, rl_insert }, /* 6 */
{ ISFUNC, rl_insert }, /* 7 */
{ ISFUNC, rl_insert }, /* 8 */
{ ISFUNC, rl_insert }, /* 9 */
/* A little more punctuation. */
{ ISFUNC, rl_insert }, /* : */
{ ISFUNC, rl_insert }, /* ; */
{ ISFUNC, rl_insert }, /* < */
{ ISFUNC, rl_insert }, /* = */
{ ISFUNC, rl_insert }, /* > */
{ ISFUNC, rl_insert }, /* ? */
{ ISFUNC, rl_insert }, /* @ */
/* Uppercase alphabet. */
{ ISFUNC, rl_insert }, /* A */
{ ISFUNC, rl_insert }, /* B */
{ ISFUNC, rl_insert }, /* C */
{ ISFUNC, rl_insert }, /* D */
{ ISFUNC, rl_insert }, /* E */
{ ISFUNC, rl_insert }, /* F */
{ ISFUNC, rl_insert }, /* G */
{ ISFUNC, rl_insert }, /* H */
{ ISFUNC, rl_insert }, /* I */
{ ISFUNC, rl_insert }, /* J */
{ ISFUNC, rl_insert }, /* K */
{ ISFUNC, rl_insert }, /* L */
{ ISFUNC, rl_insert }, /* M */
{ ISFUNC, rl_insert }, /* N */
{ ISFUNC, rl_insert }, /* O */
{ ISFUNC, rl_insert }, /* P */
{ ISFUNC, rl_insert }, /* Q */
{ ISFUNC, rl_insert }, /* R */
{ ISFUNC, rl_insert }, /* S */
{ ISFUNC, rl_insert }, /* T */
{ ISFUNC, rl_insert }, /* U */
{ ISFUNC, rl_insert }, /* V */
{ ISFUNC, rl_insert }, /* W */
{ ISFUNC, rl_insert }, /* X */
{ ISFUNC, rl_insert }, /* Y */
{ ISFUNC, rl_insert }, /* Z */
/* Some more punctuation. */
{ ISFUNC, rl_insert }, /* [ */
{ ISFUNC, rl_insert }, /* \ */
{ ISFUNC, rl_insert }, /* ] */
{ ISFUNC, rl_insert }, /* ^ */
{ ISFUNC, rl_insert }, /* _ */
{ ISFUNC, rl_insert }, /* ` */
/* Lowercase alphabet. */
{ ISFUNC, rl_insert }, /* a */
{ ISFUNC, rl_insert }, /* b */
{ ISFUNC, rl_insert }, /* c */
{ ISFUNC, rl_insert }, /* d */
{ ISFUNC, rl_insert }, /* e */
{ ISFUNC, rl_insert }, /* f */
{ ISFUNC, rl_insert }, /* g */
{ ISFUNC, rl_insert }, /* h */
{ ISFUNC, rl_insert }, /* i */
{ ISFUNC, rl_insert }, /* j */
{ ISFUNC, rl_insert }, /* k */
{ ISFUNC, rl_insert }, /* l */
{ ISFUNC, rl_insert }, /* m */
{ ISFUNC, rl_insert }, /* n */
{ ISFUNC, rl_insert }, /* o */
{ ISFUNC, rl_insert }, /* p */
{ ISFUNC, rl_insert }, /* q */
{ ISFUNC, rl_insert }, /* r */
{ ISFUNC, rl_insert }, /* s */
{ ISFUNC, rl_insert }, /* t */
{ ISFUNC, rl_insert }, /* u */
{ ISFUNC, rl_insert }, /* v */
{ ISFUNC, rl_insert }, /* w */
{ ISFUNC, rl_insert }, /* x */
{ ISFUNC, rl_insert }, /* y */
{ ISFUNC, rl_insert }, /* z */
/* Final punctuation. */
{ ISFUNC, rl_insert }, /* { */
{ ISFUNC, rl_insert }, /* | */
{ ISFUNC, rl_insert }, /* } */
{ ISFUNC, rl_insert }, /* ~ */
{ ISFUNC, rl_rubout }, /* RUBOUT */
#if KEYMAP_SIZE > 128
/* Pure 8-bit characters (128 - 159).
These might be used in some
character sets. */
{ ISFUNC, rl_insert }, /* ? */
{ ISFUNC, rl_insert }, /* ? */
{ ISFUNC, rl_insert }, /* ? */
{ ISFUNC, rl_insert }, /* ? */
{ ISFUNC, rl_insert }, /* ? */
{ ISFUNC, rl_insert }, /* ? */
{ ISFUNC, rl_insert }, /* ? */
{ ISFUNC, rl_insert }, /* ? */
{ ISFUNC, rl_insert }, /* ? */
{ ISFUNC, rl_insert }, /* ? */
{ ISFUNC, rl_insert }, /* ? */
{ ISFUNC, rl_insert }, /* ? */
{ ISFUNC, rl_insert }, /* ? */
{ ISFUNC, rl_insert }, /* ? */
{ ISFUNC, rl_insert }, /* ? */
{ ISFUNC, rl_insert }, /* ? */
{ ISFUNC, rl_insert }, /* ? */
{ ISFUNC, rl_insert }, /* ? */
{ ISFUNC, rl_insert }, /* ? */
{ ISFUNC, rl_insert }, /* ? */
{ ISFUNC, rl_insert }, /* ? */
{ ISFUNC, rl_insert }, /* ? */
{ ISFUNC, rl_insert }, /* ? */
{ ISFUNC, rl_insert }, /* ? */
{ ISFUNC, rl_insert }, /* ? */
{ ISFUNC, rl_insert }, /* ? */
{ ISFUNC, rl_insert }, /* ? */
{ ISFUNC, rl_insert }, /* ? */
{ ISFUNC, rl_insert }, /* ? */
{ ISFUNC, rl_insert }, /* ? */
{ ISFUNC, rl_insert }, /* ? */
{ ISFUNC, rl_insert }, /* ? */
/* ISO Latin-1 characters (160 - 255) */
{ ISFUNC, rl_insert }, /* No-break space */
{ ISFUNC, rl_insert }, /* Inverted exclamation mark */
{ ISFUNC, rl_insert }, /* Cent sign */
{ ISFUNC, rl_insert }, /* Pound sign */
{ ISFUNC, rl_insert }, /* Currency sign */
{ ISFUNC, rl_insert }, /* Yen sign */
{ ISFUNC, rl_insert }, /* Broken bar */
{ ISFUNC, rl_insert }, /* Section sign */
{ ISFUNC, rl_insert }, /* Diaeresis */
{ ISFUNC, rl_insert }, /* Copyright sign */
{ ISFUNC, rl_insert }, /* Feminine ordinal indicator */
{ ISFUNC, rl_insert }, /* Left pointing double angle quotation mark */
{ ISFUNC, rl_insert }, /* Not sign */
{ ISFUNC, rl_insert }, /* Soft hyphen */
{ ISFUNC, rl_insert }, /* Registered sign */
{ ISFUNC, rl_insert }, /* Macron */
{ ISFUNC, rl_insert }, /* Degree sign */
{ ISFUNC, rl_insert }, /* Plus-minus sign */
{ ISFUNC, rl_insert }, /* Superscript two */
{ ISFUNC, rl_insert }, /* Superscript three */
{ ISFUNC, rl_insert }, /* Acute accent */
{ ISFUNC, rl_insert }, /* Micro sign */
{ ISFUNC, rl_insert }, /* Pilcrow sign */
{ ISFUNC, rl_insert }, /* Middle dot */
{ ISFUNC, rl_insert }, /* Cedilla */
{ ISFUNC, rl_insert }, /* Superscript one */
{ ISFUNC, rl_insert }, /* Masculine ordinal indicator */
{ ISFUNC, rl_insert }, /* Right pointing double angle quotation mark */
{ ISFUNC, rl_insert }, /* Vulgar fraction one quarter */
{ ISFUNC, rl_insert }, /* Vulgar fraction one half */
{ ISFUNC, rl_insert }, /* Vulgar fraction three quarters */
{ ISFUNC, rl_insert }, /* Inverted questionk mark */
{ ISFUNC, rl_insert }, /* Latin capital letter a with grave */
{ ISFUNC, rl_insert }, /* Latin capital letter a with acute */
{ ISFUNC, rl_insert }, /* Latin capital letter a with circumflex */
{ ISFUNC, rl_insert }, /* Latin capital letter a with tilde */
{ ISFUNC, rl_insert }, /* Latin capital letter a with diaeresis */
{ ISFUNC, rl_insert }, /* Latin capital letter a with ring above */
{ ISFUNC, rl_insert }, /* Latin capital letter ae */
{ ISFUNC, rl_insert }, /* Latin capital letter c with cedilla */
{ ISFUNC, rl_insert }, /* Latin capital letter e with grave */
{ ISFUNC, rl_insert }, /* Latin capital letter e with acute */
{ ISFUNC, rl_insert }, /* Latin capital letter e with circumflex */
{ ISFUNC, rl_insert }, /* Latin capital letter e with diaeresis */
{ ISFUNC, rl_insert }, /* Latin capital letter i with grave */
{ ISFUNC, rl_insert }, /* Latin capital letter i with acute */
{ ISFUNC, rl_insert }, /* Latin capital letter i with circumflex */
{ ISFUNC, rl_insert }, /* Latin capital letter i with diaeresis */
{ ISFUNC, rl_insert }, /* Latin capital letter eth (Icelandic) */
{ ISFUNC, rl_insert }, /* Latin capital letter n with tilde */
{ ISFUNC, rl_insert }, /* Latin capital letter o with grave */
{ ISFUNC, rl_insert }, /* Latin capital letter o with acute */
{ ISFUNC, rl_insert }, /* Latin capital letter o with circumflex */
{ ISFUNC, rl_insert }, /* Latin capital letter o with tilde */
{ ISFUNC, rl_insert }, /* Latin capital letter o with diaeresis */
{ ISFUNC, rl_insert }, /* Multiplication sign */
{ ISFUNC, rl_insert }, /* Latin capital letter o with stroke */
{ ISFUNC, rl_insert }, /* Latin capital letter u with grave */
{ ISFUNC, rl_insert }, /* Latin capital letter u with acute */
{ ISFUNC, rl_insert }, /* Latin capital letter u with circumflex */
{ ISFUNC, rl_insert }, /* Latin capital letter u with diaeresis */
{ ISFUNC, rl_insert }, /* Latin capital letter Y with acute */
{ ISFUNC, rl_insert }, /* Latin capital letter thorn (Icelandic) */
{ ISFUNC, rl_insert }, /* Latin small letter sharp s (German) */
{ ISFUNC, rl_insert }, /* Latin small letter a with grave */
{ ISFUNC, rl_insert }, /* Latin small letter a with acute */
{ ISFUNC, rl_insert }, /* Latin small letter a with circumflex */
{ ISFUNC, rl_insert }, /* Latin small letter a with tilde */
{ ISFUNC, rl_insert }, /* Latin small letter a with diaeresis */
{ ISFUNC, rl_insert }, /* Latin small letter a with ring above */
{ ISFUNC, rl_insert }, /* Latin small letter ae */
{ ISFUNC, rl_insert }, /* Latin small letter c with cedilla */
{ ISFUNC, rl_insert }, /* Latin small letter e with grave */
{ ISFUNC, rl_insert }, /* Latin small letter e with acute */
{ ISFUNC, rl_insert }, /* Latin small letter e with circumflex */
{ ISFUNC, rl_insert }, /* Latin small letter e with diaeresis */
{ ISFUNC, rl_insert }, /* Latin small letter i with grave */
{ ISFUNC, rl_insert }, /* Latin small letter i with acute */
{ ISFUNC, rl_insert }, /* Latin small letter i with circumflex */
{ ISFUNC, rl_insert }, /* Latin small letter i with diaeresis */
{ ISFUNC, rl_insert }, /* Latin small letter eth (Icelandic) */
{ ISFUNC, rl_insert }, /* Latin small letter n with tilde */
{ ISFUNC, rl_insert }, /* Latin small letter o with grave */
{ ISFUNC, rl_insert }, /* Latin small letter o with acute */
{ ISFUNC, rl_insert }, /* Latin small letter o with circumflex */
{ ISFUNC, rl_insert }, /* Latin small letter o with tilde */
{ ISFUNC, rl_insert }, /* Latin small letter o with diaeresis */
{ ISFUNC, rl_insert }, /* Division sign */
{ ISFUNC, rl_insert }, /* Latin small letter o with stroke */
{ ISFUNC, rl_insert }, /* Latin small letter u with grave */
{ ISFUNC, rl_insert }, /* Latin small letter u with acute */
{ ISFUNC, rl_insert }, /* Latin small letter u with circumflex */
{ ISFUNC, rl_insert }, /* Latin small letter u with diaeresis */
{ ISFUNC, rl_insert }, /* Latin small letter y with acute */
{ ISFUNC, rl_insert }, /* Latin small letter thorn (Icelandic) */
{ ISFUNC, rl_insert } /* Latin small letter y with diaeresis */
#endif /* KEYMAP_SIZE > 128 */
};
/* Unused for the time being. */
#if 0
KEYMAP_ENTRY_ARRAY vi_escape_keymap = {
/* The regular control keys come first. */
{ ISFUNC, (Function *)0x0 }, /* Control-@ */
{ ISFUNC, (Function *)0x0 }, /* Control-a */
{ ISFUNC, (Function *)0x0 }, /* Control-b */
{ ISFUNC, (Function *)0x0 }, /* Control-c */
{ ISFUNC, (Function *)0x0 }, /* Control-d */
{ ISFUNC, (Function *)0x0 }, /* Control-e */
{ ISFUNC, (Function *)0x0 }, /* Control-f */
{ ISFUNC, (Function *)0x0 }, /* Control-g */
{ ISFUNC, (Function *)0x0 }, /* Control-h */
{ ISFUNC, rl_tab_insert}, /* Control-i */
{ ISFUNC, rl_emacs_editing_mode}, /* Control-j */
{ ISFUNC, rl_kill_line }, /* Control-k */
{ ISFUNC, (Function *)0x0 }, /* Control-l */
{ ISFUNC, rl_emacs_editing_mode}, /* Control-m */
{ ISFUNC, (Function *)0x0 }, /* Control-n */
{ ISFUNC, (Function *)0x0 }, /* Control-o */
{ ISFUNC, (Function *)0x0 }, /* Control-p */
{ ISFUNC, (Function *)0x0 }, /* Control-q */
{ ISFUNC, (Function *)0x0 }, /* Control-r */
{ ISFUNC, (Function *)0x0 }, /* Control-s */
{ ISFUNC, (Function *)0x0 }, /* Control-t */
{ ISFUNC, (Function *)0x0 }, /* Control-u */
{ ISFUNC, (Function *)0x0 }, /* Control-v */
{ ISFUNC, (Function *)0x0 }, /* Control-w */
{ ISFUNC, (Function *)0x0 }, /* Control-x */
{ ISFUNC, (Function *)0x0 }, /* Control-y */
{ ISFUNC, (Function *)0x0 }, /* Control-z */
{ ISFUNC, rl_vi_movement_mode }, /* Control-[ */
{ ISFUNC, (Function *)0x0 }, /* Control-\ */
{ ISFUNC, (Function *)0x0 }, /* Control-] */
{ ISFUNC, (Function *)0x0 }, /* Control-^ */
{ ISFUNC, rl_undo_command }, /* Control-_ */
/* The start of printing characters. */
{ ISFUNC, (Function *)0x0 }, /* SPACE */
{ ISFUNC, (Function *)0x0 }, /* ! */
{ ISFUNC, (Function *)0x0 }, /* " */
{ ISFUNC, (Function *)0x0 }, /* # */
{ ISFUNC, (Function *)0x0 }, /* $ */
{ ISFUNC, (Function *)0x0 }, /* % */
{ ISFUNC, (Function *)0x0 }, /* & */
{ ISFUNC, (Function *)0x0 }, /* ' */
{ ISFUNC, (Function *)0x0 }, /* ( */
{ ISFUNC, (Function *)0x0 }, /* ) */
{ ISFUNC, (Function *)0x0 }, /* * */
{ ISFUNC, (Function *)0x0 }, /* + */
{ ISFUNC, (Function *)0x0 }, /* , */
{ ISFUNC, (Function *)0x0 }, /* - */
{ ISFUNC, (Function *)0x0 }, /* . */
{ ISFUNC, (Function *)0x0 }, /* / */
/* Regular digits. */
{ ISFUNC, rl_vi_arg_digit }, /* 0 */
{ ISFUNC, rl_vi_arg_digit }, /* 1 */
{ ISFUNC, rl_vi_arg_digit }, /* 2 */
{ ISFUNC, rl_vi_arg_digit }, /* 3 */
{ ISFUNC, rl_vi_arg_digit }, /* 4 */
{ ISFUNC, rl_vi_arg_digit }, /* 5 */
{ ISFUNC, rl_vi_arg_digit }, /* 6 */
{ ISFUNC, rl_vi_arg_digit }, /* 7 */
{ ISFUNC, rl_vi_arg_digit }, /* 8 */
{ ISFUNC, rl_vi_arg_digit }, /* 9 */
/* A little more punctuation. */
{ ISFUNC, (Function *)0x0 }, /* : */
{ ISFUNC, (Function *)0x0 }, /* ; */
{ ISFUNC, (Function *)0x0 }, /* < */
{ ISFUNC, (Function *)0x0 }, /* = */
{ ISFUNC, (Function *)0x0 }, /* > */
{ ISFUNC, (Function *)0x0 }, /* ? */
{ ISFUNC, (Function *)0x0 }, /* @ */
/* Uppercase alphabet. */
{ ISFUNC, rl_do_lowercase_version }, /* A */
{ ISFUNC, rl_do_lowercase_version }, /* B */
{ ISFUNC, rl_do_lowercase_version }, /* C */
{ ISFUNC, rl_do_lowercase_version }, /* D */
{ ISFUNC, rl_do_lowercase_version }, /* E */
{ ISFUNC, rl_do_lowercase_version }, /* F */
{ ISFUNC, rl_do_lowercase_version }, /* G */
{ ISFUNC, rl_do_lowercase_version }, /* H */
{ ISFUNC, rl_do_lowercase_version }, /* I */
{ ISFUNC, rl_do_lowercase_version }, /* J */
{ ISFUNC, rl_do_lowercase_version }, /* K */
{ ISFUNC, rl_do_lowercase_version }, /* L */
{ ISFUNC, rl_do_lowercase_version }, /* M */
{ ISFUNC, rl_do_lowercase_version }, /* N */
{ ISFUNC, rl_do_lowercase_version }, /* O */
{ ISFUNC, rl_do_lowercase_version }, /* P */
{ ISFUNC, rl_do_lowercase_version }, /* Q */
{ ISFUNC, rl_do_lowercase_version }, /* R */
{ ISFUNC, rl_do_lowercase_version }, /* S */
{ ISFUNC, rl_do_lowercase_version }, /* T */
{ ISFUNC, rl_do_lowercase_version }, /* U */
{ ISFUNC, rl_do_lowercase_version }, /* V */
{ ISFUNC, rl_do_lowercase_version }, /* W */
{ ISFUNC, rl_do_lowercase_version }, /* X */
{ ISFUNC, rl_do_lowercase_version }, /* Y */
{ ISFUNC, rl_do_lowercase_version }, /* Z */
/* Some more punctuation. */
{ ISFUNC, rl_arrow_keys }, /* [ */
{ ISFUNC, (Function *)0x0 }, /* \ */
{ ISFUNC, (Function *)0x0 }, /* ] */
{ ISFUNC, (Function *)0x0 }, /* ^ */
{ ISFUNC, (Function *)0x0 }, /* _ */
{ ISFUNC, (Function *)0x0 }, /* ` */
/* Lowercase alphabet. */
{ ISFUNC, (Function *)0x0 }, /* a */
{ ISFUNC, (Function *)0x0 }, /* b */
{ ISFUNC, (Function *)0x0 }, /* c */
{ ISFUNC, (Function *)0x0 }, /* d */
{ ISFUNC, (Function *)0x0 }, /* e */
{ ISFUNC, (Function *)0x0 }, /* f */
{ ISFUNC, (Function *)0x0 }, /* g */
{ ISFUNC, (Function *)0x0 }, /* h */
{ ISFUNC, (Function *)0x0 }, /* i */
{ ISFUNC, (Function *)0x0 }, /* j */
{ ISFUNC, (Function *)0x0 }, /* k */
{ ISFUNC, (Function *)0x0 }, /* l */
{ ISFUNC, (Function *)0x0 }, /* m */
{ ISFUNC, (Function *)0x0 }, /* n */
{ ISFUNC, rl_arrow_keys }, /* o */
{ ISFUNC, (Function *)0x0 }, /* p */
{ ISFUNC, (Function *)0x0 }, /* q */
{ ISFUNC, (Function *)0x0 }, /* r */
{ ISFUNC, (Function *)0x0 }, /* s */
{ ISFUNC, (Function *)0x0 }, /* t */
{ ISFUNC, (Function *)0x0 }, /* u */
{ ISFUNC, (Function *)0x0 }, /* v */
{ ISFUNC, (Function *)0x0 }, /* w */
{ ISFUNC, (Function *)0x0 }, /* x */
{ ISFUNC, (Function *)0x0 }, /* y */
{ ISFUNC, (Function *)0x0 }, /* z */
/* Final punctuation. */
{ ISFUNC, (Function *)0x0 }, /* { */
{ ISFUNC, (Function *)0x0 }, /* | */
{ ISFUNC, (Function *)0x0 }, /* } */
{ ISFUNC, (Function *)0x0 }, /* ~ */
{ ISFUNC, rl_backward_kill_word }, /* RUBOUT */
#if KEYMAP_SIZE > 128
/* Undefined keys. */
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 },
{ ISFUNC, (Function *)0x0 }
#endif /* KEYMAP_SIZE > 128 */
};
#endif

1329
lib/readline/vi_mode.c Normal file

File diff suppressed because it is too large Load diff

78
lib/readline/xmalloc.c Normal file
View file

@ -0,0 +1,78 @@
/* xmalloc.c -- safe versions of malloc and realloc */
/* Copyright (C) 1991 Free Software Foundation, Inc.
This file is part of GNU Readline, a library for reading lines
of text with interactive input and history editing.
Readline is free software; you can redistribute it and/or modify it
under the terms of the GNU General Public License as published by the
Free Software Foundation; either version 1, or (at your option) any
later version.
Readline is distributed in the hope that it will be useful, but
WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
General Public License for more details.
You should have received a copy of the GNU General Public License
along with Readline; see the file COPYING. If not, write to the Free
Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA. */
#if defined (ALREADY_HAVE_XMALLOC)
#else
#include <stdio.h>
#if defined (HAVE_STDLIB_H)
# include <stdlib.h>
#else
# include "ansi_stdlib.h"
#endif /* HAVE_STDLIB_H */
static void memory_error_and_abort ();
/* **************************************************************** */
/* */
/* Memory Allocation and Deallocation. */
/* */
/* **************************************************************** */
/* Return a pointer to free()able block of memory large enough
to hold BYTES number of bytes. If the memory cannot be allocated,
print an error message and abort. */
char *
xmalloc (bytes)
int bytes;
{
char *temp = (char *)malloc (bytes);
if (!temp)
memory_error_and_abort ("xmalloc");
return (temp);
}
char *
xrealloc (pointer, bytes)
char *pointer;
int bytes;
{
char *temp;
if (!pointer)
temp = (char *)malloc (bytes);
else
temp = (char *)realloc (pointer, bytes);
if (!temp)
memory_error_and_abort ("xrealloc");
return (temp);
}
static void
memory_error_and_abort (fname)
char *fname;
{
fprintf (stderr, "%s: Out of virtual memory!\n", fname);
abort ();
}
#endif /* !ALREADY_HAVE_XMALLOC */

67
lib/termcap/Makefile Normal file
View file

@ -0,0 +1,67 @@
## -*- text -*- ####################################################
# #
# Makefile for termcap replacement libbrary. #
# #
####################################################################
# Here is a rule for making .o files from .c files that doesn't force
# the type of the machine (like -sun3) into the flags.
.c.o:
$(CC) -c $(CFLAGS) $(LOCAL_INCLUDES) $(CPPFLAGS) $*.c
# Destination installation directory. The libraries are copied to DESTDIR
# when you do a `make install'.
DESTDIR = /usr/local/lib
DEBUG_FLAGS = -g
#OPTIMIZE_FLAGS = -O
LDFLAGS = $(DEBUG_FLAGS)
CFLAGS = $(DEBUG_FLAGS) $(OPTIMIZE_FLAGS)
SHELL = /bin/sh
# A good alternative is gcc -traditional.
#CC = gcc -traditional
CC = cc
RANLIB = ranlib
AR = ar
RM = rm
CP = cp
CSOURCES = termcap.c tparam.c
SOURCES = $(CSOURCES)
OBJECTS = termcap.o tparam.o
DOCUMENTATION = termcap.texinfo
THINGS_TO_TAR = $(SOURCES) $(DOCUMENTATION)
##########################################################################
all: libtermcap.a
libtermcap.a: $(OBJECTS)
$(RM) -f $@
$(AR) clq $@ $(OBJECTS)
-[ -n "$(RANLIB)" ] && $(RANLIB) $@
termcap.tar: $(THINGS_TO_TAR)
tar -cf $@ $(THINGS_TO_TAR)
termcap.tar.Z: termcap.tar
compress -f termcap.tar
install: $(DESTDIR)/libtermcap.a
clean:
rm -f *.o *.a *.log *.cp *.tp *.vr *.fn *.aux *.pg *.toc
maintainer-clean realclean mostlyclean distclean: clean
$(DESTDIR)/libtermcap.a: libtermcap.a
-mv $(DESTDIR)/libtermcap.a $(DESTDIR)/libtermcap.old
cp libtermcap.a $@
-[ -n "$(RANLIB) ] && $(RANLIB) -t $@

339
lib/termcap/grot/COPYING Normal file
View file

@ -0,0 +1,339 @@
GNU GENERAL PUBLIC LICENSE
Version 2, June 1991
Copyright (C) 1989, 1991 Free Software Foundation, Inc.
675 Mass Ave, Cambridge, MA 02139, USA
Everyone is permitted to copy and distribute verbatim copies
of this license document, but changing it is not allowed.
Preamble
The licenses for most software are designed to take away your
freedom to share and change it. By contrast, the GNU General Public
License is intended to guarantee your freedom to share and change free
software--to make sure the software is free for all its users. This
General Public License applies to most of the Free Software
Foundation's software and to any other program whose authors commit to
using it. (Some other Free Software Foundation software is covered by
the GNU Library General Public License instead.) You can apply it to
your programs, too.
When we speak of free software, we are referring to freedom, not
price. Our General Public Licenses are designed to make sure that you
have the freedom to distribute copies of free software (and charge for
this service if you wish), that you receive source code or can get it
if you want it, that you can change the software or use pieces of it
in new free programs; and that you know you can do these things.
To protect your rights, we need to make restrictions that forbid
anyone to deny you these rights or to ask you to surrender the rights.
These restrictions translate to certain responsibilities for you if you
distribute copies of the software, or if you modify it.
For example, if you distribute copies of such a program, whether
gratis or for a fee, you must give the recipients all the rights that
you have. You must make sure that they, too, receive or can get the
source code. And you must show them these terms so they know their
rights.
We protect your rights with two steps: (1) copyright the software, and
(2) offer you this license which gives you legal permission to copy,
distribute and/or modify the software.
Also, for each author's protection and ours, we want to make certain
that everyone understands that there is no warranty for this free
software. If the software is modified by someone else and passed on, we
want its recipients to know that what they have is not the original, so
that any problems introduced by others will not reflect on the original
authors' reputations.
Finally, any free program is threatened constantly by software
patents. We wish to avoid the danger that redistributors of a free
program will individually obtain patent licenses, in effect making the
program proprietary. To prevent this, we have made it clear that any
patent must be licensed for everyone's free use or not licensed at all.
The precise terms and conditions for copying, distribution and
modification follow.
GNU GENERAL PUBLIC LICENSE
TERMS AND CONDITIONS FOR COPYING, DISTRIBUTION AND MODIFICATION
0. This License applies to any program or other work which contains
a notice placed by the copyright holder saying it may be distributed
under the terms of this General Public License. The "Program", below,
refers to any such program or work, and a "work based on the Program"
means either the Program or any derivative work under copyright law:
that is to say, a work containing the Program or a portion of it,
either verbatim or with modifications and/or translated into another
language. (Hereinafter, translation is included without limitation in
the term "modification".) Each licensee is addressed as "you".
Activities other than copying, distribution and modification are not
covered by this License; they are outside its scope. The act of
running the Program is not restricted, and the output from the Program
is covered only if its contents constitute a work based on the
Program (independent of having been made by running the Program).
Whether that is true depends on what the Program does.
1. You may copy and distribute verbatim copies of the Program's
source code as you receive it, in any medium, provided that you
conspicuously and appropriately publish on each copy an appropriate
copyright notice and disclaimer of warranty; keep intact all the
notices that refer to this License and to the absence of any warranty;
and give any other recipients of the Program a copy of this License
along with the Program.
You may charge a fee for the physical act of transferring a copy, and
you may at your option offer warranty protection in exchange for a fee.
2. You may modify your copy or copies of the Program or any portion
of it, thus forming a work based on the Program, and copy and
distribute such modifications or work under the terms of Section 1
above, provided that you also meet all of these conditions:
a) You must cause the modified files to carry prominent notices
stating that you changed the files and the date of any change.
b) You must cause any work that you distribute or publish, that in
whole or in part contains or is derived from the Program or any
part thereof, to be licensed as a whole at no charge to all third
parties under the terms of this License.
c) If the modified program normally reads commands interactively
when run, you must cause it, when started running for such
interactive use in the most ordinary way, to print or display an
announcement including an appropriate copyright notice and a
notice that there is no warranty (or else, saying that you provide
a warranty) and that users may redistribute the program under
these conditions, and telling the user how to view a copy of this
License. (Exception: if the Program itself is interactive but
does not normally print such an announcement, your work based on
the Program is not required to print an announcement.)
These requirements apply to the modified work as a whole. If
identifiable sections of that work are not derived from the Program,
and can be reasonably considered independent and separate works in
themselves, then this License, and its terms, do not apply to those
sections when you distribute them as separate works. But when you
distribute the same sections as part of a whole which is a work based
on the Program, the distribution of the whole must be on the terms of
this License, whose permissions for other licensees extend to the
entire whole, and thus to each and every part regardless of who wrote it.
Thus, it is not the intent of this section to claim rights or contest
your rights to work written entirely by you; rather, the intent is to
exercise the right to control the distribution of derivative or
collective works based on the Program.
In addition, mere aggregation of another work not based on the Program
with the Program (or with a work based on the Program) on a volume of
a storage or distribution medium does not bring the other work under
the scope of this License.
3. You may copy and distribute the Program (or a work based on it,
under Section 2) in object code or executable form under the terms of
Sections 1 and 2 above provided that you also do one of the following:
a) Accompany it with the complete corresponding machine-readable
source code, which must be distributed under the terms of Sections
1 and 2 above on a medium customarily used for software interchange; or,
b) Accompany it with a written offer, valid for at least three
years, to give any third party, for a charge no more than your
cost of physically performing source distribution, a complete
machine-readable copy of the corresponding source code, to be
distributed under the terms of Sections 1 and 2 above on a medium
customarily used for software interchange; or,
c) Accompany it with the information you received as to the offer
to distribute corresponding source code. (This alternative is
allowed only for noncommercial distribution and only if you
received the program in object code or executable form with such
an offer, in accord with Subsection b above.)
The source code for a work means the preferred form of the work for
making modifications to it. For an executable work, complete source
code means all the source code for all modules it contains, plus any
associated interface definition files, plus the scripts used to
control compilation and installation of the executable. However, as a
special exception, the source code distributed need not include
anything that is normally distributed (in either source or binary
form) with the major components (compiler, kernel, and so on) of the
operating system on which the executable runs, unless that component
itself accompanies the executable.
If distribution of executable or object code is made by offering
access to copy from a designated place, then offering equivalent
access to copy the source code from the same place counts as
distribution of the source code, even though third parties are not
compelled to copy the source along with the object code.
4. You may not copy, modify, sublicense, or distribute the Program
except as expressly provided under this License. Any attempt
otherwise to copy, modify, sublicense or distribute the Program is
void, and will automatically terminate your rights under this License.
However, parties who have received copies, or rights, from you under
this License will not have their licenses terminated so long as such
parties remain in full compliance.
5. You are not required to accept this License, since you have not
signed it. However, nothing else grants you permission to modify or
distribute the Program or its derivative works. These actions are
prohibited by law if you do not accept this License. Therefore, by
modifying or distributing the Program (or any work based on the
Program), you indicate your acceptance of this License to do so, and
all its terms and conditions for copying, distributing or modifying
the Program or works based on it.
6. Each time you redistribute the Program (or any work based on the
Program), the recipient automatically receives a license from the
original licensor to copy, distribute or modify the Program subject to
these terms and conditions. You may not impose any further
restrictions on the recipients' exercise of the rights granted herein.
You are not responsible for enforcing compliance by third parties to
this License.
7. If, as a consequence of a court judgment or allegation of patent
infringement or for any other reason (not limited to patent issues),
conditions are imposed on you (whether by court order, agreement or
otherwise) that contradict the conditions of this License, they do not
excuse you from the conditions of this License. If you cannot
distribute so as to satisfy simultaneously your obligations under this
License and any other pertinent obligations, then as a consequence you
may not distribute the Program at all. For example, if a patent
license would not permit royalty-free redistribution of the Program by
all those who receive copies directly or indirectly through you, then
the only way you could satisfy both it and this License would be to
refrain entirely from distribution of the Program.
If any portion of this section is held invalid or unenforceable under
any particular circumstance, the balance of the section is intended to
apply and the section as a whole is intended to apply in other
circumstances.
It is not the purpose of this section to induce you to infringe any
patents or other property right claims or to contest validity of any
such claims; this section has the sole purpose of protecting the
integrity of the free software distribution system, which is
implemented by public license practices. Many people have made
generous contributions to the wide range of software distributed
through that system in reliance on consistent application of that
system; it is up to the author/donor to decide if he or she is willing
to distribute software through any other system and a licensee cannot
impose that choice.
This section is intended to make thoroughly clear what is believed to
be a consequence of the rest of this License.
8. If the distribution and/or use of the Program is restricted in
certain countries either by patents or by copyrighted interfaces, the
original copyright holder who places the Program under this License
may add an explicit geographical distribution limitation excluding
those countries, so that distribution is permitted only in or among
countries not thus excluded. In such case, this License incorporates
the limitation as if written in the body of this License.
9. The Free Software Foundation may publish revised and/or new versions
of the General Public License from time to time. Such new versions will
be similar in spirit to the present version, but may differ in detail to
address new problems or concerns.
Each version is given a distinguishing version number. If the Program
specifies a version number of this License which applies to it and "any
later version", you have the option of following the terms and conditions
either of that version or of any later version published by the Free
Software Foundation. If the Program does not specify a version number of
this License, you may choose any version ever published by the Free Software
Foundation.
10. If you wish to incorporate parts of the Program into other free
programs whose distribution conditions are different, write to the author
to ask for permission. For software which is copyrighted by the Free
Software Foundation, write to the Free Software Foundation; we sometimes
make exceptions for this. Our decision will be guided by the two goals
of preserving the free status of all derivatives of our free software and
of promoting the sharing and reuse of software generally.
NO WARRANTY
11. BECAUSE THE PROGRAM IS LICENSED FREE OF CHARGE, THERE IS NO WARRANTY
FOR THE PROGRAM, TO THE EXTENT PERMITTED BY APPLICABLE LAW. EXCEPT WHEN
OTHERWISE STATED IN WRITING THE COPYRIGHT HOLDERS AND/OR OTHER PARTIES
PROVIDE THE PROGRAM "AS IS" WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESSED
OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. THE ENTIRE RISK AS
TO THE QUALITY AND PERFORMANCE OF THE PROGRAM IS WITH YOU. SHOULD THE
PROGRAM PROVE DEFECTIVE, YOU ASSUME THE COST OF ALL NECESSARY SERVICING,
REPAIR OR CORRECTION.
12. IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED TO IN WRITING
WILL ANY COPYRIGHT HOLDER, OR ANY OTHER PARTY WHO MAY MODIFY AND/OR
REDISTRIBUTE THE PROGRAM AS PERMITTED ABOVE, BE LIABLE TO YOU FOR DAMAGES,
INCLUDING ANY GENERAL, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES ARISING
OUT OF THE USE OR INABILITY TO USE THE PROGRAM (INCLUDING BUT NOT LIMITED
TO LOSS OF DATA OR DATA BEING RENDERED INACCURATE OR LOSSES SUSTAINED BY
YOU OR THIRD PARTIES OR A FAILURE OF THE PROGRAM TO OPERATE WITH ANY OTHER
PROGRAMS), EVEN IF SUCH HOLDER OR OTHER PARTY HAS BEEN ADVISED OF THE
POSSIBILITY OF SUCH DAMAGES.
END OF TERMS AND CONDITIONS
Appendix: How to Apply These Terms to Your New Programs
If you develop a new program, and you want it to be of the greatest
possible use to the public, the best way to achieve this is to make it
free software which everyone can redistribute and change under these terms.
To do so, attach the following notices to the program. It is safest
to attach them to the start of each source file to most effectively
convey the exclusion of warranty; and each file should have at least
the "copyright" line and a pointer to where the full notice is found.
<one line to give the program's name and a brief idea of what it does.>
Copyright (C) 19yy <name of author>
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
Also add information on how to contact you by electronic and paper mail.
If the program is interactive, make it output a short notice like this
when it starts in an interactive mode:
Gnomovision version 69, Copyright (C) 19yy name of author
Gnomovision comes with ABSOLUTELY NO WARRANTY; for details type `show w'.
This is free software, and you are welcome to redistribute it
under certain conditions; type `show c' for details.
The hypothetical commands `show w' and `show c' should show the appropriate
parts of the General Public License. Of course, the commands you use may
be called something other than `show w' and `show c'; they could even be
mouse-clicks or menu items--whatever suits your program.
You should also get your employer (if you work as a programmer) or your
school, if any, to sign a "copyright disclaimer" for the program, if
necessary. Here is a sample; alter the names:
Yoyodyne, Inc., hereby disclaims all copyright interest in the program
`Gnomovision' (which makes passes at compilers) written by James Hacker.
<signature of Ty Coon>, 1 April 1989
Ty Coon, President of Vice
This General Public License does not permit incorporating your program into
proprietary programs. If your program is a subroutine library, you may
consider it more useful to permit linking proprietary applications with the
library. If this is what you want to do, use the GNU Library General
Public License instead of this License.

View file

@ -0,0 +1,48 @@
Thu Apr 15 12:45:10 1993 David J. MacKenzie (djm@kropotkin.gnu.ai.mit.edu)
* Version 1.2.
* tparam.c [!emacs] (xmalloc, xrealloc, memory_out): New functions.
(tparam1): Use them.
* termcap.c, tparam.c: Use NULL or '\0' where appropriate
instead of 0. Rename some vars.
* termcap.c (tgetent): If EOF is reached on termcap file,
free allocated resources before returning.
* termcap.c (tgetent): Use /etc/termcap if TERMCAP is an entry
for a term type other than TERM.
From pjr@jet.UK (Paul J Rippin).
Sat Apr 10 23:55:12 1993 Richard Stallman (rms@mole.gnu.ai.mit.edu)
* tparam.c (tparam1): Don't set the 0200 bit on a non-0 character code.
From junio@twinsun.COM (Junio Hamano).
Tue Dec 8 22:02:15 1992 David J. MacKenzie (djm@kropotkin.gnu.ai.mit.edu)
* termcap.c, tparam.c: Use HAVE_STRING_H instead of USG.
Thu Dec 3 13:47:56 1992 David J. MacKenzie (djm@nutrimat.gnu.ai.mit.edu)
* termcap.c, tparam.c [HAVE_CONFIG_H]: Include config.h.
Fri Oct 23 12:35:29 1992 David J. MacKenzie (djm@goldman.gnu.ai.mit.edu)
* termcap.h [__STDC__]: Add consts. From Franc,ois Pinard.
Tue Oct 13 15:52:21 1992 David J. MacKenzie (djm@goldman.gnu.ai.mit.edu)
* Version 1.1.
Tue Sep 29 21:04:39 1992 David J. MacKenzie (djm@geech.gnu.ai.mit.edu)
* termcap.[ch], tparam.c: Fix some lint.
* version.c: New file.
Local Variables:
mode: indented-text
left-margin: 8
version-control: never
End:

117
lib/termcap/grot/INSTALL Normal file
View file

@ -0,0 +1,117 @@
This is a generic INSTALL file for utilities distributions.
If this package does not come with, e.g., installable documentation or
data files, please ignore the references to them below.
To compile this package:
1. Configure the package for your system. In the directory that this
file is in, type `./configure'. If you're using `csh' on an old
version of System V, you might need to type `sh configure' instead to
prevent `csh' from trying to execute `configure' itself.
The `configure' shell script attempts to guess correct values for
various system-dependent variables used during compilation, and
creates the Makefile(s) (one in each subdirectory of the source
directory). In some packages it creates a C header file containing
system-dependent definitions. It also creates a file `config.status'
that you can run in the future to recreate the current configuration.
Running `configure' takes a minute or two. While it is running, it
prints some messages that tell what it is doing. If you don't want to
see the messages, run `configure' with its standard output redirected
to `/dev/null'; for example, `./configure >/dev/null'.
To compile the package in a different directory from the one
containing the source code, you must use a version of `make' that
supports the VPATH variable, such as GNU `make'. `cd' to the directory
where you want the object files and executables to go and run
`configure'. `configure' automatically checks for the source code in
the directory that `configure' is in and in `..'. If for some reason
`configure' is not in the source code directory that you are
configuring, then it will report that it can't find the source code.
In that case, run `configure' with the option `--srcdir=DIR', where
DIR is the directory that contains the source code.
By default, `make install' will install the package's files in
/usr/local/bin, /usr/local/lib, /usr/local/man, etc. You can specify
an installation prefix other than /usr/local by giving `configure' the
option `--prefix=PATH'. Alternately, you can do so by giving a value
for the `prefix' variable when you run `make', e.g.,
make prefix=/usr/gnu
You can specify separate installation prefixes for
architecture-specific files and architecture-independent files. If
you give `configure' the option `--exec-prefix=PATH' or set the
`make' variable `exec_prefix' to PATH, the package will use PATH as
the prefix for installing programs and libraries. Data files and
documentation will still use the regular prefix. Normally, all files
are installed using the regular prefix.
Another `configure' option is useful mainly in `Makefile' rules for
updating `config.status' and `Makefile'. The `--no-create' option
figures out the configuration for your system and records it in
`config.status', without actually configuring the package (creating
`Makefile's and perhaps a configuration header file). Later, you can
run `./config.status' to actually configure the package. You can also
give `config.status' the `--recheck' option, which makes it re-run
`configure' with the same arguments you used before. This option is
useful if you change `configure'.
Some packages pay attention to `--with-PACKAGE' options to `configure',
where PACKAGE is something like `gnu-libc' or `x' (for the X Window System).
The README should mention any --with- options that the package recognizes.
`configure' ignores any other arguments that you give it.
If your system requires unusual options for compilation or linking
that `configure' doesn't know about, you can give `configure' initial
values for some variables by setting them in the environment. In
Bourne-compatible shells, you can do that on the command line like
this:
CC='gcc -traditional' DEFS=-D_POSIX_SOURCE ./configure
The `make' variables that you might want to override with environment
variables when running `configure' are:
(For these variables, any value given in the environment overrides the
value that `configure' would choose:)
CC C compiler program.
Default is `cc', or `gcc' if `gcc' is in your PATH.
INSTALL Program to use to install files.
Default is `install' if you have it, `cp' otherwise.
(For these variables, any value given in the environment is added to
the value that `configure' chooses:)
DEFS Configuration options, in the form `-Dfoo -Dbar ...'
Do not use this variable in packages that create a
configuration header file.
LIBS Libraries to link with, in the form `-lfoo -lbar ...'
If you need to do unusual things to compile the package, we encourage
you to figure out how `configure' could check whether to do them, and
mail diffs or instructions to the address given in the README so we
can include them in the next release.
2. Type `make' to compile the package. If you want, you can override
the `make' variables CFLAGS and LDFLAGS like this:
make CFLAGS=-O2 LDFLAGS=-s
3. If the package comes with self-tests and you want to run them,
type `make check'. If you're not sure whether there are any, try it;
if `make' responds with something like
make: *** No way to make target `check'. Stop.
then the package does not come with self-tests.
4. Type `make install' to install programs, data files, and
documentation.
5. You can remove the program binaries and object files from the
source directory by typing `make clean'. To also remove the
Makefile(s), the header file containing system-dependent definitions
(if the package uses one), and `config.status' (all the files that
`configure' created), type `make distclean'.
The file `configure.in' is used as a template to create `configure' by
a program called `autoconf'. You will only need it if you want to
regenerate `configure' using a newer version of `autoconf'.

View file

@ -0,0 +1,118 @@
# Makefile for GNU termcap library.
# Copyright (C) 1992, 1993 Free Software Foundation, Inc.
# This program is free software; you can redistribute it and/or modify
# it under the terms of the GNU General Public License as published by
# the Free Software Foundation; either version 2, or (at your option)
# any later version.
# This program is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
# GNU General Public License for more details.
# You should have received a copy of the GNU General Public License
# along with this program; if not, write to the Free Software
# Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
#### Start of system configuration section. ####
srcdir = @srcdir@
VPATH = @srcdir@
CC = @CC@
# If you don't have a BSD or GNU install program, use cp.
INSTALL = @INSTALL@
INSTALL_DATA = @INSTALL_DATA@
MAKEINFO = makeinfo
# Things you might add to DEFS:
# -DHAVE_STRING_H If you have memcpy instead of bcopy.
# -DNO_ARG_ARRAY If you can't take the address of the first of
# a group of arguments and treat it as an array.
# We always define this, because it's not a big loss
# and can't be detected when cross-autoconfiguring.
DEFS = @DEFS@ -DNO_ARG_ARRAY
CFLAGS = -g
prefix = /usr/local
exec_prefix = $(prefix)
# Directory in which to install libtermcap.a.
libdir = $(exec_prefix)/lib
# Directory in which to install termcap.h.
includedir = $(prefix)/include
# Directory in which to optionally also install termcap.h,
# so compilers besides gcc can find it by default.
# If it is empty or not defined, termcap.h will only be installed in
# includedir.
oldincludedir = /usr/include
# Directory in which to install the documentation info files.
infodir = $(prefix)/info
#### End of system configuration section. ####
SHELL = /bin/sh
SRCS = termcap.c tparam.c version.c
OBJS = termcap.o tparam.o version.o
HDRS = termcap.h
DISTFILES = $(SRCS) $(HDRS) ChangeLog COPYING README INSTALL NEWS \
termcap.texi termcap.info* \
texinfo.tex Makefile.in configure configure.in
all: libtermcap.a termcap.info
.c.o:
$(CC) -c $(CPPFLAGS) $(DEFS) -I$(srcdir) $(CFLAGS) $<
install: all
$(INSTALL_DATA) libtermcap.a $(libdir)/libtermcap.a
-ranlib $(libdir)/libtermcap.a
test -d $(includedir) || mkdir $(includedir)
cd $(srcdir); $(INSTALL_DATA) termcap.h $(includedir)/termcap.h
-cd $(srcdir); test -z "$(oldincludedir)" || \
$(INSTALL_DATA) termcap.h $(oldincludedir)/termcap.h
cd $(srcdir); for f in termcap.info*; \
do $(INSTALL_DATA) $$f $(infodir)/$$f; done
uninstall:
rm -f $(libdir)/libtermcap.a $(includedir)/termcap.h
test -z "$(oldincludedir)" || rm -f $(oldincludedir)/termcap.h
rm -f $(infodir)/termcap.info*
libtermcap.a: $(OBJS)
ar rc $@ $(OBJS)
-ranlib $@
termcap.info: termcap.texi
$(MAKEINFO) $(srcdir)/termcap.texi --output=$(srcdir)/termcap.info
TAGS: $(SRCS)
etags $(SRCS)
clean:
rm -f *.a *.o core
mostlyclean: clean
distclean: clean
rm -f Makefile config.status
realclean: distclean
rm -f TAGS *.info*
dist: $(DISTFILES)
echo termcap-`sed -e '/version_string/!d' -e 's/[^0-9]*\([0-9a-z.]*\).*/\1/' -e q version.c` > .fname
rm -rf `cat .fname`
mkdir `cat .fname`
ln $(DISTFILES) `cat .fname`
tar chzf `cat .fname`.tar.z `cat .fname`
rm -rf `cat .fname` .fname

12
lib/termcap/grot/NEWS Normal file
View file

@ -0,0 +1,12 @@
Major changes in release 1.2:
For `%.', only set the high bit on NUL.
Fix a file descriptor and memory leak.
Add const in termcap.h prototypes.
Configuration improvements.
Major changes in release 1.1:
Fix portability problems.
Improve configuration and installation.
Fix compiler warnings.

14
lib/termcap/grot/README Normal file
View file

@ -0,0 +1,14 @@
This is the GNU termcap library -- a library of C functions that
enable programs to send control strings to terminals in a way
independent of the terminal type. Most of this package is also
distributed with GNU Emacs, but it is available in this separate
distribution to make it easier to install as -ltermcap.
The GNU termcap library does not place an arbitrary limit on the size
of termcap entries, unlike most other termcap libraries.
See the file INSTALL for compilation and installation instructions.
Please report any bugs in this library to bug-gnu-emacs@prep.ai.mit.edu.
You can check which version of the library you have by using the RCS
`ident' command on libtermcap.a.

Some files were not shown because too many files have changed in this diff Show more